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 DotAnimatsiya from "@/components/dot/DotAnimatsiya";
|
||||
import { useTranslations } from "next-intl";
|
||||
import ProductCard from "../products/productCard";
|
||||
|
||||
export function Blog() {
|
||||
const t = useTranslations();
|
||||
@@ -40,22 +41,22 @@ export function Blog() {
|
||||
<div className="mb-4 flex items-center justify-center gap-2">
|
||||
<DotAnimatsiya />
|
||||
<span className="font-almarai text-sm font-semibold tracking-wider text-white uppercase">
|
||||
{t("home.blog.title")}
|
||||
{t("products.banner.title")}
|
||||
</span>
|
||||
</div>
|
||||
<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"
|
||||
>
|
||||
{t("home.blog.subtitle")}
|
||||
{t("products.ourproducts")}
|
||||
</h2>
|
||||
</div>
|
||||
|
||||
{/* Blog Cards Grid */}
|
||||
<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">
|
||||
{/* Image Container */}
|
||||
|
||||
<div className="relative mb-6 aspect-4/2 md:aspect-4/3 overflow-hidden rounded-lg">
|
||||
<Image
|
||||
src={post.image || "/placeholder.svg"}
|
||||
@@ -63,7 +64,7 @@ export function Blog() {
|
||||
fill
|
||||
className="object-cover transition-transform duration-300 group-hover:scale-105"
|
||||
/>
|
||||
{/* Category Badge */}
|
||||
|
||||
<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">
|
||||
{post.category}
|
||||
@@ -71,7 +72,6 @@ export function Blog() {
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Content */}
|
||||
<div>
|
||||
<h3 className="font-unbounded uppercase mb-3 text-lg font-bold leading-tight tracking-wide text-white md:text-xl">
|
||||
{post.title}
|
||||
@@ -91,6 +91,18 @@ export function Blog() {
|
||||
</a>
|
||||
</div>
|
||||
</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>
|
||||
|
||||
@@ -1,26 +1,27 @@
|
||||
import { Counter } from "@/components/Counter";
|
||||
import { useTranslations } from "next-intl";
|
||||
|
||||
export function Statistics() {
|
||||
const t = useTranslations();
|
||||
const stats = [
|
||||
{
|
||||
number: '25',
|
||||
symbol: '+',
|
||||
number: "25",
|
||||
symbol: "+",
|
||||
label: t("home.statistics.experience"),
|
||||
},
|
||||
{
|
||||
number: '450',
|
||||
symbol: '+',
|
||||
number: "450",
|
||||
symbol: "+",
|
||||
label: t("home.statistics.projectsCompleted"),
|
||||
},
|
||||
{
|
||||
number: '99',
|
||||
symbol: '+',
|
||||
number: "99",
|
||||
symbol: "+",
|
||||
label: t("home.statistics.trainedSpecialists"),
|
||||
},
|
||||
{
|
||||
number: '93',
|
||||
symbol: '%',
|
||||
number: "93",
|
||||
symbol: "%",
|
||||
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="grid grid-cols-2 md:grid-cols-4 gap-8 lg:gap-12">
|
||||
{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 */}
|
||||
<div className="flex items-baseline gap-2 font-almarai">
|
||||
<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 className="text-4xl sm:text-5xl lg:text-6xl font-bold text-red-600">{stat.symbol}</span>
|
||||
</div>
|
||||
|
||||
{/* Label */}
|
||||
|
||||
@@ -28,18 +28,18 @@ export function ProductBanner() {
|
||||
<div className="spacw-y-4 ">
|
||||
<div className="flex items-center gap-2 w-fit">
|
||||
<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")}
|
||||
</span>
|
||||
</div>
|
||||
<p
|
||||
className=" 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"
|
||||
className="font-unbounded uppercase bg-linear-to-br from-white via-white to-black
|
||||
text-transparent bg-clip-text text-3xl sm:text-4xl lg:text-5xl font-bold leading-tight text-pretty"
|
||||
>
|
||||
{t("products.banner.subtitle")}
|
||||
</p>
|
||||
</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")}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -36,7 +36,7 @@ export default function ProductCard({
|
||||
<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 ">
|
||||
{/* 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
|
||||
src={image || "/placeholder.svg"}
|
||||
alt={title}
|
||||
|
||||
@@ -150,7 +150,8 @@
|
||||
"title": "Products",
|
||||
"subtitle": "Ignum Technology Ready",
|
||||
"description": "We not only supply equipment but become a successful partner for every client."
|
||||
}
|
||||
},
|
||||
"ourproducts": "Our Products"
|
||||
},
|
||||
"faq": {
|
||||
"banner": {
|
||||
|
||||
@@ -150,7 +150,8 @@
|
||||
"title": "Продукты",
|
||||
"subtitle": "Технология Ignum Готова",
|
||||
"description": "Мы не просто поставляем оборудование, мы становимся успешным партнером для каждого клиента."
|
||||
}
|
||||
},
|
||||
"ourproducts": "Наши продукты"
|
||||
},
|
||||
"faq": {
|
||||
"banner": {
|
||||
|
||||
@@ -150,7 +150,8 @@
|
||||
"title": "Mahsulotlar",
|
||||
"subtitle": "Ignum Texnologiyasi Tayyor",
|
||||
"description": "Biz nafaqat uskunalar yetkazib beramiz, balki har bir mijozning muvaffaqiyatli hamkoriga aylanamiz."
|
||||
}
|
||||
},
|
||||
"ourproducts":"Bizning mahsulotlarimiz"
|
||||
},
|
||||
"faq": {
|
||||
"banner": {
|
||||
|
||||
@@ -45,6 +45,7 @@
|
||||
"cmdk": "1.0.4",
|
||||
"date-fns": "4.1.0",
|
||||
"embla-carousel-react": "8.5.1",
|
||||
"framer-motion": "^12.29.2",
|
||||
"input-otp": "1.4.1",
|
||||
"lucide-react": "^0.454.0",
|
||||
"negotiator": "^1.0.0",
|
||||
|
||||
38
pnpm-lock.yaml
generated
38
pnpm-lock.yaml
generated
@@ -116,6 +116,9 @@ importers:
|
||||
embla-carousel-react:
|
||||
specifier: 8.5.1
|
||||
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:
|
||||
specifier: 1.4.1
|
||||
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:
|
||||
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:
|
||||
resolution: {integrity: sha512-FJhYRoDaiatfEkUK8HKlicmu/3SGFD51q3itKDGoSTysQJBnfOcxU5GxnhE1E6soB76MbT0MBtnKJuXyAx+96Q==}
|
||||
engines: {node: '>=6'}
|
||||
@@ -1687,6 +1704,12 @@ packages:
|
||||
magic-string@0.30.21:
|
||||
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:
|
||||
resolution: {integrity: sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w==}
|
||||
engines: {node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1}
|
||||
@@ -3251,6 +3274,15 @@ snapshots:
|
||||
|
||||
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: {}
|
||||
|
||||
graceful-fs@4.2.11: {}
|
||||
@@ -3342,6 +3374,12 @@ snapshots:
|
||||
dependencies:
|
||||
'@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: {}
|
||||
|
||||
negotiator@1.0.0: {}
|
||||
|
||||
Reference in New Issue
Block a user