From c970d9c6d03688dc050916fb27d631ac351b6fec Mon Sep 17 00:00:00 2001 From: Ilia Mashkov Date: Thu, 20 Nov 2025 16:07:18 +0300 Subject: [PATCH] =?UTF-8?q?refactor:=20=D0=9B=D0=BE=D0=B3=D0=B8=D0=BA?= =?UTF-8?q?=D0=B0=20=D0=BA=D0=BE=D0=BE=D1=80=D0=B4=D0=B8=D0=BD=D0=B0=D1=82?= =?UTF-8?q?=20=D1=82=D0=BE=D1=87=D0=BA=D0=B8=20=D0=BD=D0=B0=20=D0=BA=D1=80?= =?UTF-8?q?=D1=83=D0=B3=D0=B5=20=D0=B2=D1=8B=D0=BD=D0=B5=D1=81=D0=B5=D0=BD?= =?UTF-8?q?=D0=B0=20=D0=B2=20=D0=BE=D1=82=D0=B5=D0=BB=D1=8C=D0=BD=D1=83?= =?UTF-8?q?=D1=8E=20=D1=84=D1=83=D0=BD=D0=BA=D1=86=D0=B8=D1=8E,=20=D0=B8?= =?UTF-8?q?=D1=81=D0=BF=D1=80=D0=B0=D0=B2=D0=BB=D0=B5=D0=BD=D1=8B=20=D1=81?= =?UTF-8?q?=D1=82=D0=B8=D0=BB=D0=B8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/app/styles/variables.scss | 2 +- .../CircleTimeline/CircleTimeline.module.scss | 46 +++++++++---------- .../ui/CircleTimeline/CircleTimeline.tsx | 32 ++++--------- 3 files changed, 34 insertions(+), 46 deletions(-) diff --git a/src/app/styles/variables.scss b/src/app/styles/variables.scss index c0e24c7..5ee1974 100644 --- a/src/app/styles/variables.scss +++ b/src/app/styles/variables.scss @@ -6,7 +6,7 @@ --color-bg: #F4F5F9; --color-border: rgb(66 86 122 / 10%); --color-blue: #3877EE; - --color-white: #FFFFFF; + --color-white: #FFF; // Градиенты --gradient-primary: linear-gradient(to right, #3877EE, #EF5DA8); diff --git a/src/widgets/TimeFrameSlider/ui/CircleTimeline/CircleTimeline.module.scss b/src/widgets/TimeFrameSlider/ui/CircleTimeline/CircleTimeline.module.scss index a5e26ad..2863715 100644 --- a/src/widgets/TimeFrameSlider/ui/CircleTimeline/CircleTimeline.module.scss +++ b/src/widgets/TimeFrameSlider/ui/CircleTimeline/CircleTimeline.module.scss @@ -1,6 +1,4 @@ .circleContainer { - $border-color: var(--color-primary); - position: absolute; top: 50%; left: 50%; @@ -8,7 +6,7 @@ width: calc(var(--circle-radius, 265px) * 2); height: calc(var(--circle-radius, 265px) * 2); - border: 1px solid rgb($border-color / 20%); + border: 1px solid rgba(#42567A, 0.2); border-radius: 50%; transform: translate(-50%, -50%); @@ -17,46 +15,48 @@ .point { position: absolute; - width: 6px; - height: 6px; - margin-top: -3px; - margin-left: -3px; + width: 56px; + height: 56px; + margin-top: -28px; + margin-left: -28px; + + border: 25px solid transparent; + + border-radius: 50%; + + background: var(--color-text); + background-clip: content-box; cursor: pointer; - background: var(--color-text); - border-radius: 50%; + transform-origin: center; transition: all 0.3s ease; - transform-origin: center; &:hover, &.active { z-index: 10; display: flex; - align-items: center; justify-content: center; + align-items: center; - width: 56px; - height: 56px; - margin-top: -28px; - margin-left: -28px; - - border: 1px solid rgb(48 62 88 / 50%); + border: 1px solid rgba(#303E58, 0.5); background: #F4F5F9; - } - .label { - display: none; - - font-size: 20px; - color: var(--color-text); + background-clip: padding-box; } &:hover .label, &.active .label { display: block; } + + .label { + display: none; + + color: var(--color-text); + font-size: 20px; + } } \ No newline at end of file diff --git a/src/widgets/TimeFrameSlider/ui/CircleTimeline/CircleTimeline.tsx b/src/widgets/TimeFrameSlider/ui/CircleTimeline/CircleTimeline.tsx index 6b908a0..e72302c 100644 --- a/src/widgets/TimeFrameSlider/ui/CircleTimeline/CircleTimeline.tsx +++ b/src/widgets/TimeFrameSlider/ui/CircleTimeline/CircleTimeline.tsx @@ -8,17 +8,13 @@ * Поддерживает клик по точкам для переключения периодов. */ +import classNames from 'classnames' import gsap from 'gsap' import { memo, useCallback, useEffect, useMemo, useRef } from 'react' import styles from './CircleTimeline.module.scss' -import { - ANIMATION_DURATION, - ANIMATION_EASE, - CIRCLE_RADIUS, - FULL_CIRCLE_DEGREES, - HALF_CIRCLE_DEGREES, -} from '../../model' +import { calculateCoordinates } from '../../lib/utils/calculateCoordinates/calculateCoordinates' +import { ANIMATION_DURATION, ANIMATION_EASE } from '../../model' import type { TimePeriod } from '@/entities/TimePeriod' @@ -90,7 +86,7 @@ export const CircleTimeline = memo(function CircleTimeline({ if (point) { gsap.to(point, { rotation: -rotation, - duration: ANIMATION_DURATION, + duration: 0, ease: ANIMATION_EASE, }) } @@ -102,19 +98,9 @@ export const CircleTimeline = memo(function CircleTimeline({ * Пересчитывается только при изменении количества периодов */ const pointPositions = useMemo(() => { - return periods.map((_, index) => { - // Угол для текущей точки (в градусах) - const angle = (FULL_CIRCLE_DEGREES / periods.length) * index - - // Конвертация в радианы для тригонометрических функций - const radian = (angle * Math.PI) / HALF_CIRCLE_DEGREES - - // Вычисление координат на круге - const x = CIRCLE_RADIUS * Math.cos(radian) - const y = CIRCLE_RADIUS * Math.sin(radian) - - return { x, y } - }) + return periods.map((_, index, array) => + calculateCoordinates(array.length, index) + ) }, [periods]) /** @@ -139,7 +125,9 @@ export const CircleTimeline = memo(function CircleTimeline({ ref={(el) => { pointsRef.current[index] = el }} - className={`${styles.point} ${index === activeIndex ? styles.active : ''}`} + className={classNames(styles.point, { + [styles.active]: index === activeIndex, + })} style={{ left: `calc(50% + ${x}px)`, top: `calc(50% + ${y}px)`,