feat: customizable colors
parent
07f9451b39
commit
50ea538717
@ -0,0 +1,312 @@
|
|||||||
|
import React, { useState } from 'react';
|
||||||
|
import { Year } from '../components/calendar/Year';
|
||||||
|
import { Controls } from '../components/calendar/Controls';
|
||||||
|
import { HeaderStyle, MonthCutoffType, DaySize, DateRange, ColorScheme } from '../types/calendar';
|
||||||
|
import styles from './Examples.module.scss';
|
||||||
|
import { format, isBefore, isEqual } from 'date-fns';
|
||||||
|
|
||||||
|
export const ComprehensiveColorScheme: React.FC = () => {
|
||||||
|
const [dateRange, setDateRange] = useState<DateRange>({
|
||||||
|
startDate: new Date(2025, 0, 15),
|
||||||
|
endDate: new Date(2025, 0, 20),
|
||||||
|
selecting: false,
|
||||||
|
hoverDate: null,
|
||||||
|
anchorDate: null
|
||||||
|
});
|
||||||
|
|
||||||
|
const [dayHeaderStyle, setDayHeaderStyle] = useState<HeaderStyle>('tiny');
|
||||||
|
const [monthCutoff, setMonthCutoff] = useState<MonthCutoffType>('truncate');
|
||||||
|
const [size, setSize] = useState<DaySize>('l');
|
||||||
|
const [fontProportion, setFontProportion] = useState<number>(100);
|
||||||
|
const [magnify, setMagnify] = useState<boolean>(false);
|
||||||
|
const [useCustomScheme, setUseCustomScheme] = useState<boolean>(true);
|
||||||
|
const [selectedScheme, setSelectedScheme] = useState<'professional' | 'vibrant' | 'minimal'>('professional');
|
||||||
|
|
||||||
|
// Define different color schemes
|
||||||
|
const colorSchemes: Record<string, ColorScheme> = {
|
||||||
|
professional: [
|
||||||
|
// Weekday states
|
||||||
|
{ type: 'weekday', state: 'default', colors: {
|
||||||
|
header: { backgroundColor: '#2c3e50', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#ffffff', color: '#2c3e50' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekday', state: 'selected', colors: {
|
||||||
|
header: { backgroundColor: '#3498db', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#e3f2fd', color: '#1976d2' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekday', state: 'selecting', colors: {
|
||||||
|
header: { backgroundColor: '#95a5a6', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#ecf0f1', color: '#7f8c8d' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekday', state: 'rangeStart', colors: {
|
||||||
|
header: { backgroundColor: '#2980b9', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#3498db', color: '#ffffff' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekday', state: 'rangeEnd', colors: {
|
||||||
|
header: { backgroundColor: '#2980b9', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#3498db', color: '#ffffff' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekday', state: 'rangeMid', colors: {
|
||||||
|
header: { backgroundColor: '#5dade2', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#aed6f1', color: '#1a5490' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekday', state: 'active', colors: {
|
||||||
|
header: { backgroundColor: '#e74c3c', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#c0392b', color: '#ffffff' }
|
||||||
|
}},
|
||||||
|
|
||||||
|
// Weekend states
|
||||||
|
{ type: 'weekend', state: 'default', colors: {
|
||||||
|
header: { backgroundColor: '#7f8c8d', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#ecf0f1', color: '#34495e' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekend', state: 'selected', colors: {
|
||||||
|
header: { backgroundColor: '#5dade2', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#d4e6f1', color: '#2874a6' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekend', state: 'rangeStart', colors: {
|
||||||
|
header: { backgroundColor: '#2980b9', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#3498db', color: '#ffffff' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekend', state: 'rangeEnd', colors: {
|
||||||
|
header: { backgroundColor: '#2980b9', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#3498db', color: '#ffffff' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekend', state: 'active', colors: {
|
||||||
|
header: { backgroundColor: '#c0392b', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#e74c3c', color: '#ffffff' }
|
||||||
|
}}
|
||||||
|
],
|
||||||
|
|
||||||
|
vibrant: [
|
||||||
|
// Weekday states
|
||||||
|
{ type: 'weekday', state: 'default', colors: {
|
||||||
|
header: { backgroundColor: '#9c27b0', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#ffffff', color: '#4a148c' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekday', state: 'selected', colors: {
|
||||||
|
header: { backgroundColor: '#ff9800', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#fff3e0', color: '#e65100' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekday', state: 'rangeStart', colors: {
|
||||||
|
header: { backgroundColor: '#f44336', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#ff5722', color: '#ffffff' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekday', state: 'rangeEnd', colors: {
|
||||||
|
header: { backgroundColor: '#f44336', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#ff5722', color: '#ffffff' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekday', state: 'rangeMid', colors: {
|
||||||
|
header: { backgroundColor: '#ff7043', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#ffccbc', color: '#bf360c' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekday', state: 'active', colors: {
|
||||||
|
header: { backgroundColor: '#00bcd4', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#0097a7', color: '#ffffff' }
|
||||||
|
}},
|
||||||
|
|
||||||
|
// Weekend states
|
||||||
|
{ type: 'weekend', state: 'default', colors: {
|
||||||
|
header: { backgroundColor: '#673ab7', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#ede7f6', color: '#311b92' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekend', state: 'selected', colors: {
|
||||||
|
header: { backgroundColor: '#ffc107', color: '#000000' },
|
||||||
|
content: { backgroundColor: '#fff8e1', color: '#f57f17' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekend', state: 'active', colors: {
|
||||||
|
header: { backgroundColor: '#006064', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#00acc1', color: '#ffffff' }
|
||||||
|
}}
|
||||||
|
],
|
||||||
|
|
||||||
|
minimal: [
|
||||||
|
// Weekday states
|
||||||
|
{ type: 'weekday', state: 'default', colors: {
|
||||||
|
header: { backgroundColor: '#f5f5f5', color: '#333333' },
|
||||||
|
content: { backgroundColor: '#ffffff', color: '#333333' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekday', state: 'selected', colors: {
|
||||||
|
header: { backgroundColor: '#e0e0e0', color: '#000000' },
|
||||||
|
content: { backgroundColor: '#f5f5f5', color: '#000000' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekday', state: 'rangeStart', colors: {
|
||||||
|
header: { backgroundColor: '#333333', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#666666', color: '#ffffff' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekday', state: 'rangeEnd', colors: {
|
||||||
|
header: { backgroundColor: '#333333', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#666666', color: '#ffffff' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekday', state: 'rangeMid', colors: {
|
||||||
|
header: { backgroundColor: '#999999', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#cccccc', color: '#333333' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekday', state: 'active', colors: {
|
||||||
|
header: { backgroundColor: '#000000', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#333333', color: '#ffffff' }
|
||||||
|
}},
|
||||||
|
|
||||||
|
// Weekend states
|
||||||
|
{ type: 'weekend', state: 'default', colors: {
|
||||||
|
header: { backgroundColor: '#fafafa', color: '#666666' },
|
||||||
|
content: { backgroundColor: '#f0f0f0', color: '#666666' }
|
||||||
|
}},
|
||||||
|
{ type: 'weekend', state: 'active', colors: {
|
||||||
|
header: { backgroundColor: '#212121', color: '#ffffff' },
|
||||||
|
content: { backgroundColor: '#424242', color: '#ffffff' }
|
||||||
|
}}
|
||||||
|
]
|
||||||
|
};
|
||||||
|
|
||||||
|
const handleDateSelect = (date: Date) => {
|
||||||
|
setDateRange(prev => {
|
||||||
|
if (!prev.selecting || !prev.anchorDate) {
|
||||||
|
return {
|
||||||
|
startDate: date,
|
||||||
|
endDate: date,
|
||||||
|
selecting: true,
|
||||||
|
hoverDate: date,
|
||||||
|
anchorDate: date
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
if (isEqual(date, prev.anchorDate)) {
|
||||||
|
return {
|
||||||
|
startDate: date,
|
||||||
|
endDate: date,
|
||||||
|
selecting: false,
|
||||||
|
hoverDate: null,
|
||||||
|
anchorDate: null
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
const [start, end] = isBefore(date, prev.anchorDate)
|
||||||
|
? [date, prev.anchorDate]
|
||||||
|
: [prev.anchorDate, date];
|
||||||
|
|
||||||
|
return {
|
||||||
|
startDate: start,
|
||||||
|
endDate: end,
|
||||||
|
selecting: false,
|
||||||
|
hoverDate: null,
|
||||||
|
anchorDate: null
|
||||||
|
};
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const handleDateHover = (date: Date) => {
|
||||||
|
setDateRange(prev => {
|
||||||
|
if (prev.selecting && prev.anchorDate) {
|
||||||
|
if (isEqual(date, prev.anchorDate)) {
|
||||||
|
return {
|
||||||
|
...prev,
|
||||||
|
startDate: date,
|
||||||
|
endDate: date,
|
||||||
|
hoverDate: date
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
const [start, end] = isBefore(date, prev.anchorDate)
|
||||||
|
? [date, prev.anchorDate]
|
||||||
|
: [prev.anchorDate, date];
|
||||||
|
|
||||||
|
return {
|
||||||
|
...prev,
|
||||||
|
startDate: start,
|
||||||
|
endDate: end,
|
||||||
|
hoverDate: date
|
||||||
|
};
|
||||||
|
}
|
||||||
|
return prev;
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const activeDates = [
|
||||||
|
new Date(2025, 0, 1), // New Year's Day
|
||||||
|
new Date(2025, 1, 14), // Valentine's Day
|
||||||
|
new Date(2025, 6, 4), // Independence Day
|
||||||
|
new Date(2025, 11, 25) // Christmas
|
||||||
|
];
|
||||||
|
|
||||||
|
return (
|
||||||
|
<section className={styles.section}>
|
||||||
|
<h2 className={styles.sectionTitle}>Comprehensive Color Scheme Customization</h2>
|
||||||
|
<p className={styles.sectionDescription}>
|
||||||
|
Customize colors for every state (default, selected, selecting, range start/end/mid, active)
|
||||||
|
and day type (weekday, weekend).
|
||||||
|
</p>
|
||||||
|
|
||||||
|
<Controls
|
||||||
|
headerStyle={dayHeaderStyle}
|
||||||
|
monthCutoff={monthCutoff}
|
||||||
|
size={size}
|
||||||
|
fontProportion={fontProportion}
|
||||||
|
magnify={magnify}
|
||||||
|
onHeaderStyleChange={setDayHeaderStyle}
|
||||||
|
onMonthCutoffChange={setMonthCutoff}
|
||||||
|
onSizeChange={setSize}
|
||||||
|
onFontProportionChange={setFontProportion}
|
||||||
|
onMagnifyChange={setMagnify}
|
||||||
|
/>
|
||||||
|
|
||||||
|
<div className={styles.controlRow}>
|
||||||
|
<label className={styles.control}>
|
||||||
|
<input
|
||||||
|
type="checkbox"
|
||||||
|
checked={useCustomScheme}
|
||||||
|
onChange={(e) => setUseCustomScheme(e.target.checked)}
|
||||||
|
/>
|
||||||
|
Use Custom Color Scheme
|
||||||
|
</label>
|
||||||
|
{useCustomScheme && (
|
||||||
|
<select
|
||||||
|
value={selectedScheme}
|
||||||
|
onChange={(e) => setSelectedScheme(e.target.value as any)}
|
||||||
|
style={{ marginLeft: '12px' }}
|
||||||
|
>
|
||||||
|
<option value="professional">Professional</option>
|
||||||
|
<option value="vibrant">Vibrant</option>
|
||||||
|
<option value="minimal">Minimal</option>
|
||||||
|
</select>
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div className={styles.demoContainer}>
|
||||||
|
<Year
|
||||||
|
year={2025}
|
||||||
|
dayHeaderStyle={dayHeaderStyle}
|
||||||
|
monthCutoff={monthCutoff}
|
||||||
|
weekendDays={[6, 0]}
|
||||||
|
dateRange={dateRange}
|
||||||
|
onDateSelect={handleDateSelect}
|
||||||
|
onDateHover={handleDateHover}
|
||||||
|
size={size}
|
||||||
|
fontProportion={fontProportion}
|
||||||
|
magnify={magnify}
|
||||||
|
activeDates={activeDates}
|
||||||
|
colorScheme={useCustomScheme ? colorSchemes[selectedScheme] : undefined}
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div className={styles.rangeInfo}>
|
||||||
|
<div>Selected Range: {dateRange.startDate && dateRange.endDate
|
||||||
|
? `${format(dateRange.startDate, 'PP')} - ${format(dateRange.endDate, 'PP')}`
|
||||||
|
: 'None'}</div>
|
||||||
|
<div style={{ marginTop: '10px', fontSize: '0.9em', color: '#666' }}>
|
||||||
|
Active dates (holidays): Jan 1, Feb 14, Jul 4, Dec 25
|
||||||
|
</div>
|
||||||
|
{useCustomScheme && (
|
||||||
|
<div style={{ marginTop: '10px', fontSize: '0.9em' }}>
|
||||||
|
<strong>Color Scheme Features:</strong>
|
||||||
|
<ul style={{ marginTop: '5px', paddingLeft: '20px' }}>
|
||||||
|
<li>Different colors for weekdays vs weekends</li>
|
||||||
|
<li>Distinct states: default, selected, selecting, range start/end/mid, active</li>
|
||||||
|
<li>Customizable header and content colors for each state</li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
);
|
||||||
|
};
|
||||||
@ -0,0 +1,108 @@
|
|||||||
|
import React, { useState } from 'react';
|
||||||
|
import { DateRange } from '../components/calendar/DateRange';
|
||||||
|
import { ActiveColors } from '../types/calendar';
|
||||||
|
import styles from './Examples.module.scss';
|
||||||
|
|
||||||
|
export const DateRangeWithActiveColors: React.FC = () => {
|
||||||
|
const [colorScheme, setColorScheme] = useState<'default' | 'green' | 'purple' | 'orange'>('default');
|
||||||
|
|
||||||
|
const fromDate = new Date(2025, 0, 15); // January 15, 2025
|
||||||
|
const toDate = new Date(2025, 0, 20); // January 20, 2025
|
||||||
|
|
||||||
|
const colorSchemes: Record<string, ActiveColors | undefined> = {
|
||||||
|
default: undefined,
|
||||||
|
green: {
|
||||||
|
headerBg: '#D4EDDA',
|
||||||
|
headerColor: '#155724',
|
||||||
|
contentBg: '#28A745',
|
||||||
|
contentColor: '#FFFFFF'
|
||||||
|
},
|
||||||
|
purple: {
|
||||||
|
headerBg: '#E7E5FF',
|
||||||
|
headerColor: '#4A3F8C',
|
||||||
|
contentBg: '#6F42C1',
|
||||||
|
contentColor: '#FFFFFF'
|
||||||
|
},
|
||||||
|
orange: {
|
||||||
|
headerBg: '#FFF3CD',
|
||||||
|
headerColor: '#856404',
|
||||||
|
contentBg: '#FD7E14',
|
||||||
|
contentColor: '#FFFFFF'
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
return (
|
||||||
|
<section className={styles.section}>
|
||||||
|
<h2 className={styles.sectionTitle}>Date Range with Active Colors</h2>
|
||||||
|
<p className={styles.sectionDescription}>
|
||||||
|
Customize the colors of selected date ranges using the activeColors prop.
|
||||||
|
</p>
|
||||||
|
|
||||||
|
<div className={styles.controlRow}>
|
||||||
|
<label className={styles.control}>
|
||||||
|
Color Scheme:
|
||||||
|
<select
|
||||||
|
value={colorScheme}
|
||||||
|
onChange={(e) => setColorScheme(e.target.value as any)}
|
||||||
|
style={{ marginLeft: '8px' }}
|
||||||
|
>
|
||||||
|
<option value="default">Default (Blue)</option>
|
||||||
|
<option value="green">Green</option>
|
||||||
|
<option value="purple">Purple</option>
|
||||||
|
<option value="orange">Orange</option>
|
||||||
|
</select>
|
||||||
|
</label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div className={styles.demoContainer}>
|
||||||
|
<h3>Before (Default Colors)</h3>
|
||||||
|
<DateRange
|
||||||
|
from={fromDate}
|
||||||
|
to={toDate}
|
||||||
|
selected={true}
|
||||||
|
headerStyle="tiny"
|
||||||
|
size="l"
|
||||||
|
magnify={true}
|
||||||
|
/>
|
||||||
|
|
||||||
|
<h3 style={{ marginTop: '2rem' }}>After (Custom Active Colors)</h3>
|
||||||
|
<DateRange
|
||||||
|
from={fromDate}
|
||||||
|
to={toDate}
|
||||||
|
selected={true}
|
||||||
|
headerStyle="tiny"
|
||||||
|
size="l"
|
||||||
|
magnify={true}
|
||||||
|
activeColors={colorSchemes[colorScheme]}
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div className={styles.codeExample}>
|
||||||
|
<pre>{`<DateRange
|
||||||
|
from={new Date(2025, 0, 15)}
|
||||||
|
to={new Date(2025, 0, 20)}
|
||||||
|
selected={true}
|
||||||
|
headerStyle="tiny"
|
||||||
|
size="l"
|
||||||
|
magnify={true}${colorScheme !== 'default' ? `
|
||||||
|
activeColors={{
|
||||||
|
headerBg: '${colorSchemes[colorScheme]?.headerBg}',
|
||||||
|
headerColor: '${colorSchemes[colorScheme]?.headerColor}',
|
||||||
|
contentBg: '${colorSchemes[colorScheme]?.contentBg}',
|
||||||
|
contentColor: '${colorSchemes[colorScheme]?.contentColor}'
|
||||||
|
}}` : ''}
|
||||||
|
/>`}</pre>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div className={styles.info}>
|
||||||
|
<h4>ActiveColors Properties:</h4>
|
||||||
|
<ul>
|
||||||
|
<li><code>headerBg</code>: Background color for the day header</li>
|
||||||
|
<li><code>headerColor</code>: Text color for the day header</li>
|
||||||
|
<li><code>contentBg</code>: Background color for the day content (number)</li>
|
||||||
|
<li><code>contentColor</code>: Text color for the day content (number)</li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
);
|
||||||
|
};
|
||||||
@ -0,0 +1,89 @@
|
|||||||
|
import { ColorScheme, DayState, DayType, StateColors, DayVariation } from '../types/calendar';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Determines the day type based on variations (greyed indicates weekend)
|
||||||
|
* or by checking the day of week
|
||||||
|
*/
|
||||||
|
export const getDayType = (date: Date, variations: DayVariation[], weekendDays: number[] = [6, 0]): DayType => {
|
||||||
|
// If variations include 'greyed', it's a weekend
|
||||||
|
if (variations.includes('greyed')) {
|
||||||
|
return 'weekend';
|
||||||
|
}
|
||||||
|
// Fallback to checking day of week
|
||||||
|
return weekendDays.includes(date.getDay()) ? 'weekend' : 'weekday';
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Maps variations to a DayState for color lookup
|
||||||
|
*/
|
||||||
|
export const getDayState = (variations: DayVariation[]): DayState => {
|
||||||
|
// Priority order for states
|
||||||
|
if (variations.includes('rangeStart') || variations.includes('rangeEnd')) {
|
||||||
|
if (variations.includes('rangeStart') && !variations.includes('rangeEnd')) {
|
||||||
|
return 'rangeStart';
|
||||||
|
}
|
||||||
|
if (variations.includes('rangeEnd') && !variations.includes('rangeStart')) {
|
||||||
|
return 'rangeEnd';
|
||||||
|
}
|
||||||
|
// If both rangeStart and rangeEnd (single day range)
|
||||||
|
return 'rangeStart';
|
||||||
|
}
|
||||||
|
if (variations.includes('active')) return 'active';
|
||||||
|
if (variations.includes('selected')) return 'rangeMid';
|
||||||
|
if (variations.includes('selecting')) return 'selecting';
|
||||||
|
return 'default';
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Finds the appropriate colors from the color scheme
|
||||||
|
*/
|
||||||
|
export const findColorInScheme = (
|
||||||
|
colorScheme: ColorScheme | undefined,
|
||||||
|
dayType: DayType,
|
||||||
|
dayState: DayState
|
||||||
|
): StateColors | undefined => {
|
||||||
|
if (!colorScheme) return undefined;
|
||||||
|
|
||||||
|
// First try to find exact match
|
||||||
|
const exactMatch = colorScheme.find(
|
||||||
|
entry => entry.type === dayType && entry.state === dayState
|
||||||
|
);
|
||||||
|
if (exactMatch) return exactMatch.colors;
|
||||||
|
|
||||||
|
// Fallback to weekday colors for weekend if not specified
|
||||||
|
if (dayType === 'weekend') {
|
||||||
|
const weekdayMatch = colorScheme.find(
|
||||||
|
entry => entry.type === 'weekday' && entry.state === dayState
|
||||||
|
);
|
||||||
|
if (weekdayMatch) return weekdayMatch.colors;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Fallback to default state for the day type
|
||||||
|
const defaultMatch = colorScheme.find(
|
||||||
|
entry => entry.type === dayType && entry.state === 'default'
|
||||||
|
);
|
||||||
|
if (defaultMatch) return defaultMatch.colors;
|
||||||
|
|
||||||
|
// Final fallback to weekday default
|
||||||
|
const weekdayDefault = colorScheme.find(
|
||||||
|
entry => entry.type === 'weekday' && entry.state === 'default'
|
||||||
|
);
|
||||||
|
return weekdayDefault?.colors;
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the custom colors for a day based on its state and type
|
||||||
|
*/
|
||||||
|
export const getCustomColors = (
|
||||||
|
date: Date,
|
||||||
|
variations: DayVariation[],
|
||||||
|
colorScheme: ColorScheme | undefined,
|
||||||
|
weekendDays: number[] = [6, 0]
|
||||||
|
): StateColors | undefined => {
|
||||||
|
if (!colorScheme) return undefined;
|
||||||
|
|
||||||
|
const dayType = getDayType(date, variations, weekendDays);
|
||||||
|
const dayState = getDayState(variations);
|
||||||
|
|
||||||
|
return findColorInScheme(colorScheme, dayType, dayState);
|
||||||
|
};
|
||||||
Loading…
Reference in New Issue