mirror of
https://github.com/chillpadclub/bedolaga-cabinet.git
synced 2026-07-29 18:13:47 +00:00
fix: replace hardcoded green with theme-aware accent color
Normal traffic zone now uses configurable accent palette instead of hardcoded success/green. Added useTrafficZone hook that resolves mainHex dynamically from theme colors. Replaced emerald/teal classes with success palette in SuccessNotificationModal. Fixed hardcoded green hex values in Subscription and SubscriptionPurchase pages.
This commit is contained in:
@@ -159,13 +159,13 @@ export default function SuccessNotificationModal() {
|
||||
let title = data.title;
|
||||
const message = data.message;
|
||||
let icon = <CheckCircleIcon />;
|
||||
let gradientClass = 'from-success-500 to-emerald-600';
|
||||
let gradientClass = 'from-success-500 to-success-600';
|
||||
|
||||
if (!title) {
|
||||
if (isBalanceTopup) {
|
||||
title = t('successNotification.balanceTopup.title', 'Balance topped up!');
|
||||
icon = <WalletIcon />;
|
||||
gradientClass = 'from-success-500 to-emerald-600';
|
||||
gradientClass = 'from-success-500 to-success-600';
|
||||
} else if (data.type === 'subscription_activated') {
|
||||
title = t('successNotification.subscriptionActivated.title', 'Subscription activated!');
|
||||
icon = <RocketIcon />;
|
||||
@@ -185,7 +185,7 @@ export default function SuccessNotificationModal() {
|
||||
} else if (data.type === 'traffic_purchased') {
|
||||
title = t('successNotification.trafficPurchased.title', 'Traffic added!');
|
||||
icon = <TrafficIcon />;
|
||||
gradientClass = 'from-emerald-500 to-teal-600';
|
||||
gradientClass = 'from-success-500 to-success-600';
|
||||
}
|
||||
}
|
||||
|
||||
@@ -273,7 +273,7 @@ export default function SuccessNotificationModal() {
|
||||
<span className="text-dark-400">
|
||||
{t('successNotification.trafficAdded', 'Traffic added')}
|
||||
</span>
|
||||
<span className="text-lg font-bold text-emerald-400">+{data.trafficGbAdded} GB</span>
|
||||
<span className="text-lg font-bold text-success-400">+{data.trafficGbAdded} GB</span>
|
||||
</div>
|
||||
)}
|
||||
|
||||
@@ -329,7 +329,7 @@ export default function SuccessNotificationModal() {
|
||||
{isBalanceTopup && (
|
||||
<button
|
||||
onClick={handleGoToBalance}
|
||||
className="flex w-full items-center justify-center gap-2 rounded-xl bg-gradient-to-r from-success-500 to-emerald-600 py-3.5 font-bold text-white shadow-lg shadow-success-500/25 transition-all hover:from-success-400 hover:to-emerald-500 active:from-success-600 active:to-emerald-700"
|
||||
className="flex w-full items-center justify-center gap-2 rounded-xl bg-gradient-to-r from-success-500 to-success-600 py-3.5 font-bold text-white shadow-lg shadow-success-500/25 transition-all hover:from-success-400 hover:to-success-500 active:from-success-600 active:to-success-700"
|
||||
>
|
||||
<WalletIcon />
|
||||
<span>{t('successNotification.goToBalance', 'Go to Balance')}</span>
|
||||
@@ -349,7 +349,7 @@ export default function SuccessNotificationModal() {
|
||||
{isTrafficPurchased && (
|
||||
<button
|
||||
onClick={handleGoToSubscription}
|
||||
className="flex w-full items-center justify-center gap-2 rounded-xl bg-gradient-to-r from-emerald-500 to-teal-600 py-3.5 font-bold text-white shadow-lg shadow-emerald-500/25 transition-all hover:from-emerald-400 hover:to-teal-500 active:from-emerald-600 active:to-teal-700"
|
||||
className="flex w-full items-center justify-center gap-2 rounded-xl bg-gradient-to-r from-success-500 to-success-600 py-3.5 font-bold text-white shadow-lg shadow-success-500/25 transition-all hover:from-success-400 hover:to-success-500 active:from-success-600 active:to-success-700"
|
||||
>
|
||||
<TrafficIcon />
|
||||
<span>{t('successNotification.goToSubscription', 'Go to Subscription')}</span>
|
||||
|
||||
@@ -1,10 +1,9 @@
|
||||
import { useMemo } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import { Link } from 'react-router';
|
||||
import type { Subscription } from '../../types';
|
||||
import { useCurrency } from '../../hooks/useCurrency';
|
||||
import { useTheme } from '../../hooks/useTheme';
|
||||
import { getTrafficZone } from '../../utils/trafficZone';
|
||||
import { useTrafficZone } from '../../hooks/useTrafficZone';
|
||||
import { getGlassColors } from '../../utils/glassTheme';
|
||||
|
||||
interface StatsGridProps {
|
||||
@@ -46,10 +45,7 @@ export default function StatsGrid({
|
||||
const { isDark } = useTheme();
|
||||
const g = getGlassColors(isDark);
|
||||
|
||||
const zone = useMemo(
|
||||
() => getTrafficZone(subscription?.traffic_used_percent ?? 0),
|
||||
[subscription?.traffic_used_percent],
|
||||
);
|
||||
const zone = useTrafficZone(subscription?.traffic_used_percent ?? 0);
|
||||
|
||||
const cards = [
|
||||
{
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
import { useMemo } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import { useNavigate } from 'react-router';
|
||||
import { Link } from 'react-router';
|
||||
@@ -7,7 +6,7 @@ import TrafficProgressBar from './TrafficProgressBar';
|
||||
import Sparkline from './Sparkline';
|
||||
import { useAnimatedNumber } from '../../hooks/useAnimatedNumber';
|
||||
import { useTheme } from '../../hooks/useTheme';
|
||||
import { getTrafficZone } from '../../utils/trafficZone';
|
||||
import { useTrafficZone } from '../../hooks/useTrafficZone';
|
||||
import { formatTraffic } from '../../utils/formatTraffic';
|
||||
import { getGlassColors } from '../../utils/glassTheme';
|
||||
import { HoverBorderGradient } from '../ui/hover-border-gradient';
|
||||
@@ -57,7 +56,7 @@ export default function SubscriptionCardActive({
|
||||
const usedPercent = trafficData?.traffic_used_percent ?? subscription.traffic_used_percent;
|
||||
const usedGb = trafficData?.traffic_used_gb ?? subscription.traffic_used_gb;
|
||||
const isUnlimited = trafficData?.is_unlimited ?? subscription.traffic_limit_gb === 0;
|
||||
const zone = useMemo(() => getTrafficZone(usedPercent), [usedPercent]);
|
||||
const zone = useTrafficZone(usedPercent);
|
||||
const animatedPercent = useAnimatedNumber(usedPercent);
|
||||
|
||||
const formattedDate = new Date(subscription.end_date).toLocaleDateString();
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
import { useMemo } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import { getTrafficZone } from '../../utils/trafficZone';
|
||||
import { useTrafficZone } from '../../hooks/useTrafficZone';
|
||||
import { formatTraffic } from '../../utils/formatTraffic';
|
||||
import { useTheme } from '../../hooks/useTheme';
|
||||
import { getGlassColors } from '../../utils/glassTheme';
|
||||
@@ -25,17 +25,20 @@ export default function TrafficProgressBar({
|
||||
const { t } = useTranslation();
|
||||
const { isDark } = useTheme();
|
||||
const g = getGlassColors(isDark);
|
||||
const zone = useMemo(() => getTrafficZone(percent), [percent]);
|
||||
const zone = useTrafficZone(percent);
|
||||
// Gradient always starts from the accent color (normal zone)
|
||||
const startHex = zone.colors.accent || '#3b82f6';
|
||||
const clampedPercent = Math.min(percent, 100);
|
||||
const barHeight = compact ? 8 : 14;
|
||||
|
||||
// Multi-segment gradient matching prototype
|
||||
const fillGradient = useMemo(() => {
|
||||
if (percent < 50) return `linear-gradient(90deg, #00C987, ${zone.mainHex})`;
|
||||
if (percent < 75) return `linear-gradient(90deg, #00C987, #FFB800, ${zone.mainHex})`;
|
||||
if (percent < 90) return `linear-gradient(90deg, #00C987, #FFB800, #FF6B35, ${zone.mainHex})`;
|
||||
return 'linear-gradient(90deg, #00C987, #FFB800, #FF6B35, #FF3B5C)';
|
||||
}, [percent, zone.mainHex]);
|
||||
if (percent < 50) return `linear-gradient(90deg, ${startHex}, ${zone.mainHex})`;
|
||||
if (percent < 75) return `linear-gradient(90deg, ${startHex}, #FFB800, ${zone.mainHex})`;
|
||||
if (percent < 90)
|
||||
return `linear-gradient(90deg, ${startHex}, #FFB800, #FF6B35, ${zone.mainHex})`;
|
||||
return `linear-gradient(90deg, ${startHex}, #FFB800, #FF6B35, #FF3B5C)`;
|
||||
}, [percent, zone.mainHex, startHex]);
|
||||
|
||||
if (isUnlimited) {
|
||||
return (
|
||||
|
||||
Reference in New Issue
Block a user