change blog sectio from home page
This commit is contained in:
23
components/Counter.tsx
Normal file
23
components/Counter.tsx
Normal file
@@ -0,0 +1,23 @@
|
|||||||
|
"use client";
|
||||||
|
import { useEffect, useState } from "react";
|
||||||
|
import { animate, motion, useMotionValue, useTransform } from "framer-motion";
|
||||||
|
|
||||||
|
export function Counter({ countNum }: { countNum: number }) {
|
||||||
|
const count = useMotionValue(0);
|
||||||
|
const rounded = useTransform(count, (latest:any) => Math.round(latest));
|
||||||
|
const [displayValue, setDisplayValue] = useState(0);
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
const controls = animate(count, countNum, {
|
||||||
|
duration: 2,
|
||||||
|
ease: "easeOut",
|
||||||
|
onUpdate: (latest:any) => {
|
||||||
|
setDisplayValue(Math.round(latest));
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
return () => controls.stop();
|
||||||
|
}, [countNum]); // countNum dependency qo'shildi
|
||||||
|
|
||||||
|
return <motion.span>{displayValue}</motion.span>;
|
||||||
|
}
|
||||||
@@ -2,6 +2,7 @@ import Image from "next/image";
|
|||||||
import { ChevronRight } from "lucide-react";
|
import { ChevronRight } from "lucide-react";
|
||||||
import DotAnimatsiya from "@/components/dot/DotAnimatsiya";
|
import DotAnimatsiya from "@/components/dot/DotAnimatsiya";
|
||||||
import { useTranslations } from "next-intl";
|
import { useTranslations } from "next-intl";
|
||||||
|
import ProductCard from "../products/productCard";
|
||||||
|
|
||||||
export function Blog() {
|
export function Blog() {
|
||||||
const t = useTranslations();
|
const t = useTranslations();
|
||||||
@@ -40,22 +41,22 @@ export function Blog() {
|
|||||||
<div className="mb-4 flex items-center justify-center gap-2">
|
<div className="mb-4 flex items-center justify-center gap-2">
|
||||||
<DotAnimatsiya />
|
<DotAnimatsiya />
|
||||||
<span className="font-almarai text-sm font-semibold tracking-wider text-white uppercase">
|
<span className="font-almarai text-sm font-semibold tracking-wider text-white uppercase">
|
||||||
{t("home.blog.title")}
|
{t("products.banner.title")}
|
||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
<h2
|
<h2
|
||||||
className="font-unbounded bg-linear-to-br from-white via-white to-black
|
className="font-unbounded bg-linear-to-br from-white py-2 via-white to-black
|
||||||
text-transparent bg-clip-text text-4xl font-bold tracking-tight md:text-5xl lg:text-6xl"
|
text-transparent bg-clip-text text-4xl font-bold tracking-tight md:text-5xl lg:text-6xl"
|
||||||
>
|
>
|
||||||
{t("home.blog.subtitle")}
|
{t("products.ourproducts")}
|
||||||
</h2>
|
</h2>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
{/* Blog Cards Grid */}
|
{/* Blog Cards Grid */}
|
||||||
<div className="grid gap-8 md:grid-cols-2 lg:grid-cols-3 max-sm:place-items-center">
|
<div className="grid gap-8 md:grid-cols-2 lg:grid-cols-3 max-sm:place-items-center">
|
||||||
{blogPosts.map((post) => (
|
{/* {blogPosts.map((post) => (
|
||||||
<article key={post.id} className="group">
|
<article key={post.id} className="group">
|
||||||
{/* Image Container */}
|
|
||||||
<div className="relative mb-6 aspect-4/2 md:aspect-4/3 overflow-hidden rounded-lg">
|
<div className="relative mb-6 aspect-4/2 md:aspect-4/3 overflow-hidden rounded-lg">
|
||||||
<Image
|
<Image
|
||||||
src={post.image || "/placeholder.svg"}
|
src={post.image || "/placeholder.svg"}
|
||||||
@@ -63,7 +64,7 @@ export function Blog() {
|
|||||||
fill
|
fill
|
||||||
className="object-cover transition-transform duration-300 group-hover:scale-105"
|
className="object-cover transition-transform duration-300 group-hover:scale-105"
|
||||||
/>
|
/>
|
||||||
{/* Category Badge */}
|
|
||||||
<div className="absolute bottom-4 left-4">
|
<div className="absolute bottom-4 left-4">
|
||||||
<span className="font-almarai rounded bg-red-600 px-4 py-2 text-sm font-medium text-white">
|
<span className="font-almarai rounded bg-red-600 px-4 py-2 text-sm font-medium text-white">
|
||||||
{post.category}
|
{post.category}
|
||||||
@@ -71,7 +72,6 @@ export function Blog() {
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
{/* Content */}
|
|
||||||
<div>
|
<div>
|
||||||
<h3 className="font-unbounded uppercase mb-3 text-lg font-bold leading-tight tracking-wide text-white md:text-xl">
|
<h3 className="font-unbounded uppercase mb-3 text-lg font-bold leading-tight tracking-wide text-white md:text-xl">
|
||||||
{post.title}
|
{post.title}
|
||||||
@@ -91,7 +91,19 @@ export function Blog() {
|
|||||||
</a>
|
</a>
|
||||||
</div>
|
</div>
|
||||||
</article>
|
</article>
|
||||||
))}
|
))} */}
|
||||||
|
{Array(3)
|
||||||
|
.fill(null)
|
||||||
|
.map((_, index) => (
|
||||||
|
<ProductCard
|
||||||
|
key={index}
|
||||||
|
title="Elektr yong'in detektori-Ypres ver.2"
|
||||||
|
name="P-0834404"
|
||||||
|
image="/images/products/products.webp"
|
||||||
|
slug="P_0834404"
|
||||||
|
status="full"
|
||||||
|
/>
|
||||||
|
))}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</section>
|
</section>
|
||||||
|
|||||||
@@ -1,26 +1,27 @@
|
|||||||
|
import { Counter } from "@/components/Counter";
|
||||||
import { useTranslations } from "next-intl";
|
import { useTranslations } from "next-intl";
|
||||||
|
|
||||||
export function Statistics() {
|
export function Statistics() {
|
||||||
const t = useTranslations();
|
const t = useTranslations();
|
||||||
const stats = [
|
const stats = [
|
||||||
{
|
{
|
||||||
number: '25',
|
number: "25",
|
||||||
symbol: '+',
|
symbol: "+",
|
||||||
label: t("home.statistics.experience"),
|
label: t("home.statistics.experience"),
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
number: '450',
|
number: "450",
|
||||||
symbol: '+',
|
symbol: "+",
|
||||||
label: t("home.statistics.projectsCompleted"),
|
label: t("home.statistics.projectsCompleted"),
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
number: '99',
|
number: "99",
|
||||||
symbol: '+',
|
symbol: "+",
|
||||||
label: t("home.statistics.trainedSpecialists"),
|
label: t("home.statistics.trainedSpecialists"),
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
number: '93',
|
number: "93",
|
||||||
symbol: '%',
|
symbol: "%",
|
||||||
label: t("home.statistics.trustedClients"),
|
label: t("home.statistics.trustedClients"),
|
||||||
},
|
},
|
||||||
];
|
];
|
||||||
@@ -30,13 +31,18 @@ export function Statistics() {
|
|||||||
<div className="max-w-7xl mx-auto px-4 sm:px-6 lg:px-8">
|
<div className="max-w-7xl mx-auto px-4 sm:px-6 lg:px-8">
|
||||||
<div className="grid grid-cols-2 md:grid-cols-4 gap-8 lg:gap-12">
|
<div className="grid grid-cols-2 md:grid-cols-4 gap-8 lg:gap-12">
|
||||||
{stats.map((stat, index) => (
|
{stats.map((stat, index) => (
|
||||||
<div key={index} className="flex flex-col items-center justify-center py-10 sm:py-20 lg:py-15 border-b-red-600 border-b">
|
<div
|
||||||
|
key={index}
|
||||||
|
className="flex flex-col items-center justify-center py-10 sm:py-20 lg:py-15 border-b-red-600 border-b"
|
||||||
|
>
|
||||||
{/* Number and Symbol */}
|
{/* Number and Symbol */}
|
||||||
<div className="flex items-baseline gap-2 font-almarai">
|
<div className="flex items-baseline gap-2 font-almarai">
|
||||||
<span className="text-4xl sm:text-5xl lg:text-6xl font-bold text-white">
|
<span className="text-4xl sm:text-5xl lg:text-6xl font-bold text-white">
|
||||||
{stat.number}
|
<Counter countNum={Number(stat.number)} />
|
||||||
|
</span>
|
||||||
|
<span className="text-4xl sm:text-5xl lg:text-6xl font-bold text-red-600">
|
||||||
|
{stat.symbol}
|
||||||
</span>
|
</span>
|
||||||
<span className="text-4xl sm:text-5xl lg:text-6xl font-bold text-red-600">{stat.symbol}</span>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
{/* Label */}
|
{/* Label */}
|
||||||
|
|||||||
@@ -28,18 +28,18 @@ export function ProductBanner() {
|
|||||||
<div className="spacw-y-4 ">
|
<div className="spacw-y-4 ">
|
||||||
<div className="flex items-center gap-2 w-fit">
|
<div className="flex items-center gap-2 w-fit">
|
||||||
<DotAnimatsiya />
|
<DotAnimatsiya />
|
||||||
<span className="text-sm font-semibold tracking-wide">
|
<span className="font-almarai text-white text-sm font-semibold tracking-wide">
|
||||||
{t("products.banner.title")}
|
{t("products.banner.title")}
|
||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
<p
|
<p
|
||||||
className=" bg-linear-to-br from-white via-white to-black
|
className="font-unbounded uppercase bg-linear-to-br from-white via-white to-black
|
||||||
text-transparent bg-clip-text text-4xl sm:text-5xl lg:text-6xl font-bold leading-tight text-pretty"
|
text-transparent bg-clip-text text-3xl sm:text-4xl lg:text-5xl font-bold leading-tight text-pretty"
|
||||||
>
|
>
|
||||||
{t("products.banner.subtitle")}
|
{t("products.banner.subtitle")}
|
||||||
</p>
|
</p>
|
||||||
</div>
|
</div>
|
||||||
<div className="lg:w-[40%] text-gray-300 lg:mt-20 md:mt-10 sm:mt-5 ">
|
<div className="font-almarai lg:w-[40%] text-gray-300 lg:mt-20 md:mt-10 sm:mt-5 ">
|
||||||
{t("products.banner.description")}
|
{t("products.banner.description")}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@@ -36,7 +36,7 @@ export default function ProductCard({
|
|||||||
<Link href={`/products/${slug}`}>
|
<Link href={`/products/${slug}`}>
|
||||||
<article className="group transition-all duration-300 hover:cursor-pointer max-sm:max-w-100 max-sm:mx-auto max-sm:w-full ">
|
<article className="group transition-all duration-300 hover:cursor-pointer max-sm:max-w-100 max-sm:mx-auto max-sm:w-full ">
|
||||||
{/* Image Container */}
|
{/* Image Container */}
|
||||||
<div className="relative rounded-2xl h-45 sm:h-55 md:h-65 lg:w-70 w-[90%] mx-auto overflow-hidden bg-white">
|
<div className="relative rounded-2xl h-45 sm:h-55 md:h-65 lg:w-[95%] w-[90%] mx-auto overflow-hidden bg-white">
|
||||||
<Image
|
<Image
|
||||||
src={image || "/placeholder.svg"}
|
src={image || "/placeholder.svg"}
|
||||||
alt={title}
|
alt={title}
|
||||||
|
|||||||
@@ -150,7 +150,8 @@
|
|||||||
"title": "Products",
|
"title": "Products",
|
||||||
"subtitle": "Ignum Technology Ready",
|
"subtitle": "Ignum Technology Ready",
|
||||||
"description": "We not only supply equipment but become a successful partner for every client."
|
"description": "We not only supply equipment but become a successful partner for every client."
|
||||||
}
|
},
|
||||||
|
"ourproducts": "Our Products"
|
||||||
},
|
},
|
||||||
"faq": {
|
"faq": {
|
||||||
"banner": {
|
"banner": {
|
||||||
|
|||||||
@@ -150,7 +150,8 @@
|
|||||||
"title": "Продукты",
|
"title": "Продукты",
|
||||||
"subtitle": "Технология Ignum Готова",
|
"subtitle": "Технология Ignum Готова",
|
||||||
"description": "Мы не просто поставляем оборудование, мы становимся успешным партнером для каждого клиента."
|
"description": "Мы не просто поставляем оборудование, мы становимся успешным партнером для каждого клиента."
|
||||||
}
|
},
|
||||||
|
"ourproducts": "Наши продукты"
|
||||||
},
|
},
|
||||||
"faq": {
|
"faq": {
|
||||||
"banner": {
|
"banner": {
|
||||||
|
|||||||
@@ -150,7 +150,8 @@
|
|||||||
"title": "Mahsulotlar",
|
"title": "Mahsulotlar",
|
||||||
"subtitle": "Ignum Texnologiyasi Tayyor",
|
"subtitle": "Ignum Texnologiyasi Tayyor",
|
||||||
"description": "Biz nafaqat uskunalar yetkazib beramiz, balki har bir mijozning muvaffaqiyatli hamkoriga aylanamiz."
|
"description": "Biz nafaqat uskunalar yetkazib beramiz, balki har bir mijozning muvaffaqiyatli hamkoriga aylanamiz."
|
||||||
}
|
},
|
||||||
|
"ourproducts":"Bizning mahsulotlarimiz"
|
||||||
},
|
},
|
||||||
"faq": {
|
"faq": {
|
||||||
"banner": {
|
"banner": {
|
||||||
|
|||||||
@@ -45,6 +45,7 @@
|
|||||||
"cmdk": "1.0.4",
|
"cmdk": "1.0.4",
|
||||||
"date-fns": "4.1.0",
|
"date-fns": "4.1.0",
|
||||||
"embla-carousel-react": "8.5.1",
|
"embla-carousel-react": "8.5.1",
|
||||||
|
"framer-motion": "^12.29.2",
|
||||||
"input-otp": "1.4.1",
|
"input-otp": "1.4.1",
|
||||||
"lucide-react": "^0.454.0",
|
"lucide-react": "^0.454.0",
|
||||||
"negotiator": "^1.0.0",
|
"negotiator": "^1.0.0",
|
||||||
|
|||||||
38
pnpm-lock.yaml
generated
38
pnpm-lock.yaml
generated
@@ -116,6 +116,9 @@ importers:
|
|||||||
embla-carousel-react:
|
embla-carousel-react:
|
||||||
specifier: 8.5.1
|
specifier: 8.5.1
|
||||||
version: 8.5.1(react@19.2.0)
|
version: 8.5.1(react@19.2.0)
|
||||||
|
framer-motion:
|
||||||
|
specifier: ^12.29.2
|
||||||
|
version: 12.29.2(react-dom@19.2.0(react@19.2.0))(react@19.2.0)
|
||||||
input-otp:
|
input-otp:
|
||||||
specifier: 1.4.1
|
specifier: 1.4.1
|
||||||
version: 1.4.1(react-dom@19.2.0(react@19.2.0))(react@19.2.0)
|
version: 1.4.1(react-dom@19.2.0(react@19.2.0))(react@19.2.0)
|
||||||
@@ -1567,6 +1570,20 @@ packages:
|
|||||||
fraction.js@5.3.4:
|
fraction.js@5.3.4:
|
||||||
resolution: {integrity: sha512-1X1NTtiJphryn/uLQz3whtY6jK3fTqoE3ohKs0tT+Ujr1W59oopxmoEh7Lu5p6vBaPbgoM0bzveAW4Qi5RyWDQ==}
|
resolution: {integrity: sha512-1X1NTtiJphryn/uLQz3whtY6jK3fTqoE3ohKs0tT+Ujr1W59oopxmoEh7Lu5p6vBaPbgoM0bzveAW4Qi5RyWDQ==}
|
||||||
|
|
||||||
|
framer-motion@12.29.2:
|
||||||
|
resolution: {integrity: sha512-lSNRzBJk4wuIy0emYQ/nfZ7eWhqud2umPKw2QAQki6uKhZPKm2hRQHeQoHTG9MIvfobb+A/LbEWPJU794ZUKrg==}
|
||||||
|
peerDependencies:
|
||||||
|
'@emotion/is-prop-valid': '*'
|
||||||
|
react: ^18.0.0 || ^19.0.0
|
||||||
|
react-dom: ^18.0.0 || ^19.0.0
|
||||||
|
peerDependenciesMeta:
|
||||||
|
'@emotion/is-prop-valid':
|
||||||
|
optional: true
|
||||||
|
react:
|
||||||
|
optional: true
|
||||||
|
react-dom:
|
||||||
|
optional: true
|
||||||
|
|
||||||
get-nonce@1.0.1:
|
get-nonce@1.0.1:
|
||||||
resolution: {integrity: sha512-FJhYRoDaiatfEkUK8HKlicmu/3SGFD51q3itKDGoSTysQJBnfOcxU5GxnhE1E6soB76MbT0MBtnKJuXyAx+96Q==}
|
resolution: {integrity: sha512-FJhYRoDaiatfEkUK8HKlicmu/3SGFD51q3itKDGoSTysQJBnfOcxU5GxnhE1E6soB76MbT0MBtnKJuXyAx+96Q==}
|
||||||
engines: {node: '>=6'}
|
engines: {node: '>=6'}
|
||||||
@@ -1687,6 +1704,12 @@ packages:
|
|||||||
magic-string@0.30.21:
|
magic-string@0.30.21:
|
||||||
resolution: {integrity: sha512-vd2F4YUyEXKGcLHoq+TEyCjxueSeHnFxyyjNp80yg0XV4vUhnDer/lvvlqM/arB5bXQN5K2/3oinyCRyx8T2CQ==}
|
resolution: {integrity: sha512-vd2F4YUyEXKGcLHoq+TEyCjxueSeHnFxyyjNp80yg0XV4vUhnDer/lvvlqM/arB5bXQN5K2/3oinyCRyx8T2CQ==}
|
||||||
|
|
||||||
|
motion-dom@12.29.2:
|
||||||
|
resolution: {integrity: sha512-/k+NuycVV8pykxyiTCoFzIVLA95Nb1BFIVvfSu9L50/6K6qNeAYtkxXILy/LRutt7AzaYDc2myj0wkCVVYAPPA==}
|
||||||
|
|
||||||
|
motion-utils@12.29.2:
|
||||||
|
resolution: {integrity: sha512-G3kc34H2cX2gI63RqU+cZq+zWRRPSsNIOjpdl9TN4AQwC4sgwYPl/Q/Obf/d53nOm569T0fYK+tcoSV50BWx8A==}
|
||||||
|
|
||||||
nanoid@3.3.11:
|
nanoid@3.3.11:
|
||||||
resolution: {integrity: sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w==}
|
resolution: {integrity: sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w==}
|
||||||
engines: {node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1}
|
engines: {node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1}
|
||||||
@@ -3251,6 +3274,15 @@ snapshots:
|
|||||||
|
|
||||||
fraction.js@5.3.4: {}
|
fraction.js@5.3.4: {}
|
||||||
|
|
||||||
|
framer-motion@12.29.2(react-dom@19.2.0(react@19.2.0))(react@19.2.0):
|
||||||
|
dependencies:
|
||||||
|
motion-dom: 12.29.2
|
||||||
|
motion-utils: 12.29.2
|
||||||
|
tslib: 2.8.1
|
||||||
|
optionalDependencies:
|
||||||
|
react: 19.2.0
|
||||||
|
react-dom: 19.2.0(react@19.2.0)
|
||||||
|
|
||||||
get-nonce@1.0.1: {}
|
get-nonce@1.0.1: {}
|
||||||
|
|
||||||
graceful-fs@4.2.11: {}
|
graceful-fs@4.2.11: {}
|
||||||
@@ -3342,6 +3374,12 @@ snapshots:
|
|||||||
dependencies:
|
dependencies:
|
||||||
'@jridgewell/sourcemap-codec': 1.5.5
|
'@jridgewell/sourcemap-codec': 1.5.5
|
||||||
|
|
||||||
|
motion-dom@12.29.2:
|
||||||
|
dependencies:
|
||||||
|
motion-utils: 12.29.2
|
||||||
|
|
||||||
|
motion-utils@12.29.2: {}
|
||||||
|
|
||||||
nanoid@3.3.11: {}
|
nanoid@3.3.11: {}
|
||||||
|
|
||||||
negotiator@1.0.0: {}
|
negotiator@1.0.0: {}
|
||||||
|
|||||||
Reference in New Issue
Block a user