feat: ready to publish

master
Guillermo Pages 5 months ago
parent 22a02950c3
commit 272678529f

@ -1,58 +1,155 @@
# React Calendar Component
# react-calendario
A modern, flexible calendar component built with React, TypeScript, and SCSS modules.
## Demo
Check out the live demo at [calendar.code.meow.ch](https://calendar.code.meow.ch)
A modern, flexible, and highly customizable calendar component library for React with TypeScript support.
## Features
- 📅 Multiple calendar views:
- Full year view with configurable month grid
- Single month view with customizable layout
- Week view with interactive options
- Date range picker with hover preview
- 🎨 Visual customization:
- Four header styles: expanded, compacted, tiny, and numeric
- Configurable day sizes (XS to XL)
- Adjustable font proportions
- Optional magnify effect for selected dates
- Weekend highlighting
- 🔧 Functional options:
- Month cutoff handling (dimmed, truncated, or show all)
- Interactive date range selection
- Hover states and preview
- Responsive design for all screen sizes
- 🛠 Technical features:
- Built with React + TypeScript
- SCSS modules for styling
- date-fns for date manipulation
- Zero external dependencies beyond core requirements
- 📅 **Multiple Views**: Year, Month, Week, and custom date ranges
- 🎨 **Highly Customizable**: Multiple header styles, sizes, and visual options
- 🔍 **Interactive**: Date selection, range picking, and click handlers
- 📱 **Responsive**: Works on all screen sizes
- 🎯 **TypeScript**: Full type safety and IntelliSense support
- 🎨 **Themeable**: Customizable colors and styles
- 📦 **Lightweight**: Minimal dependencies
## Installation
```bash
npm install
npm install react-calendario date-fns classnames
```
## Development
or
```bash
npm run dev
yarn add react-calendario date-fns classnames
```
## Quick Start
```tsx
import { Month } from 'react-calendario';
function App() {
return (
<Month
date={new Date()}
dayHeaderStyle="expanded"
size="l"
/>
);
}
```
## Usage Examples
## Components
### Date Range Picker
### Year
Display a full year calendar with customizable month grid.
```tsx
import React, { useState } from 'react';
import { Year } from './components/calendar/Year';
import { DateRange } from './types/calendar';
import { Year } from 'react-calendario';
<Year
year={2024}
dayHeaderStyle="tiny"
monthCutoff="truncate"
size="m"
fontProportion={100}
magnify={true}
/>
```
### Month
Display a single month with various layout options.
```tsx
import { Month } from 'react-calendario';
<Month
date={new Date()}
dayHeaderStyle="expanded"
direction="column"
monthCutoff="dimmed"
size="xl"
/>
```
### Week
Display a single week view.
```tsx
import { Week } from 'react-calendario';
<Week
startDate={new Date()}
headerStyle="compacted"
referenceMonth={0}
size="l"
/>
```
### DateRange
Display a custom date range with optional selection and interactivity.
```tsx
import { DateRange } from 'react-calendario';
<DateRange
from={new Date(2024, 0, 15)}
to={new Date(2024, 0, 22)}
included={true}
selected={true}
headerStyle="tiny"
size="l"
onDateClick={(date) => console.log('Clicked:', date)}
activeDates={[new Date(2024, 0, 17)]}
/>
```
## Props
### Common Props
All components share these common props:
| Prop | Type | Default | Description |
|------|------|---------|-------------|
| `size` | `'xl' \| 'l' \| 'm' \| 's' \| 'xs' \| 'xxs'` | `'l'` | Day cell size |
| `fontProportion` | `number` | `100` | Font size percentage (10-100) |
| `magnify` | `boolean` | `false` | Enable magnify effect on selection |
| `weekendDays` | `number[]` | `[6, 0]` | Weekend day indices (0=Sunday) |
### Header Styles
| Style | Description |
|-------|-------------|
| `'expanded'` | Full day names (e.g., "Monday") |
| `'compacted'` | Three-letter abbreviations (e.g., "Mon") |
| `'tiny'` | Two-letter abbreviations (e.g., "Mo") |
| `'none'` | Numbers only |
### Size Options
- `'xxs'`: Extra extra small (20px height, 1:1.5 header:content ratio)
- `'xs'`: Extra small (24px height)
- `'s'`: Small (28px height)
- `'m'`: Medium (32px height)
- `'l'`: Large (36px height)
- `'xl'`: Extra large (48px height)
## Advanced Usage
### Date Range Selection
```tsx
import { useState } from 'react';
import { Year } from 'react-calendario';
function DateRangePicker() {
const [dateRange, setDateRange] = useState<DateRange>({
const [dateRange, setDateRange] = useState({
startDate: null,
endDate: null,
selecting: false,
@ -60,158 +157,85 @@ function DateRangePicker() {
anchorDate: null
});
const handleDateSelect = (date: Date) => {
setDateRange(prev => {
if (!prev.selecting) {
return {
startDate: date,
endDate: date,
selecting: true,
hoverDate: date,
anchorDate: date
};
}
// Complete the selection
return {
startDate: prev.anchorDate,
endDate: date,
selecting: false,
hoverDate: null,
anchorDate: null
};
});
const handleDateSelect = (date) => {
// Your range selection logic
};
return (
<Year
year={2024}
dayHeaderStyle="tiny"
monthCutoff="truncate"
weekendDays={[6, 0]}
dateRange={dateRange}
onDateSelect={handleDateSelect}
onDateHover={(date) => setDateRange(prev => ({ ...prev, hoverDate: date }))}
size="l"
fontProportion={100}
magnify={true}
/>
);
}
```
### Single Month View
### Interactive Date Range with Active States
```tsx
import React from 'react';
import { Month } from './components/calendar/Month';
import { DateRange } from 'react-calendario';
function SingleMonth() {
return (
<Month
date={new Date()}
dayHeaderStyle="expanded"
direction="column"
monthCutoff="dimmed"
weekendDays={[6, 0]}
size="xl"
fontProportion={100}
/>
);
}
```
function InteractiveCalendar() {
const [activeDates, setActiveDates] = useState([]);
### Week View
```tsx
import React from 'react';
import { Week } from './components/calendar/Week';
const handleDateClick = (date) => {
setActiveDates(prev => {
const exists = prev.some(d => d.getTime() === date.getTime());
return exists
? prev.filter(d => d.getTime() !== date.getTime())
: [...prev, date];
});
};
function WeekView() {
return (
<Week
startDate={new Date()}
headerStyle="compacted"
referenceMonth={new Date().getMonth()}
weekendDays={[6, 0]}
size="l"
fontProportion={100}
<DateRange
from={new Date(2024, 0, 1)}
to={new Date(2024, 0, 31)}
onDateClick={handleDateClick}
activeDates={activeDates}
/>
);
}
```
### Compact Year View
## Styling
```tsx
import React from 'react';
import { Year } from './components/calendar/Year';
The components use CSS modules and CSS variables for theming. You can override the default styles by:
function CompactYear() {
return (
<Year
year={2024}
dayHeaderStyle="tiny"
monthCutoff="truncate"
weekendDays={[6, 0]}
size="xs"
fontProportion={80}
magnify={true}
/>
);
}
```
1. Using the built-in props for common customizations
2. Overriding CSS variables in your global styles
3. Applying custom CSS classes
## Component Props
### Year Component
```typescript
interface YearProps {
year: number;
dayHeaderStyle: 'expanded' | 'compacted' | 'tiny' | 'none';
monthDayOfWeekHeaderStyle?: HeaderStyle;
monthCutoff?: 'dimmed' | 'truncate' | undefined;
weekendDays?: number[];
dateRange?: DateRange;
onDateSelect?: (date: Date) => void;
onDateHover?: (date: Date) => void;
size?: 'xl' | 'l' | 'm' | 's' | 'xs';
fontProportion?: number;
magnify?: boolean;
}
```
### CSS Variables
### Month Component
```typescript
interface MonthProps {
date: Date;
dayHeaderStyle: HeaderStyle;
direction: 'row' | 'column';
monthCutoff?: MonthCutoffType;
weekendDays?: number[];
dateRange?: DateRange;
onDateSelect?: (date: Date) => void;
onDateHover?: (date: Date) => void;
size?: DaySize;
fontProportion?: number;
magnify?: boolean;
```css
:root {
--color-primary: #2196f3;
--color-primary-dark: #1976d2;
--color-selected: #e3f2fd;
/* ... and more */
}
```
## Styling
The component uses SCSS modules for styling. Key style files:
- `src/components/calendar/shared/_colors.scss`: Color variables
- `src/components/calendar/shared/_variables.scss`: Layout variables
- Individual component SCSS modules for specific styling
## TypeScript
## Browser Support
Full TypeScript support with exported types:
- Chrome (latest)
- Firefox (latest)
- Safari (latest)
- Edge (latest)
```tsx
import type {
DateRange,
HeaderStyle,
DaySize,
MonthCutoffType
} from 'react-calendario';
```
## License
MIT
## Contributing
Contributions are welcome! Please feel free to submit a Pull Request.

40
package-lock.json generated

@ -1,25 +1,31 @@
{
"name": "react-calendar",
"version": "0.0.0",
"name": "react-calendario",
"version": "1.0.0",
"lockfileVersion": 3,
"requires": true,
"packages": {
"": {
"name": "react-calendar",
"version": "0.0.0",
"name": "react-calendario",
"version": "1.0.0",
"license": "MIT",
"dependencies": {
"classnames": "^2.5.1",
"date-fns": "^4.1.0",
"react": "^19.1.0",
"react-dom": "^19.1.0"
"date-fns": "^4.1.0"
},
"devDependencies": {
"@types/node": "^24.0.14",
"@types/react": "^19.1.8",
"@types/react-dom": "^19.1.6",
"@vitejs/plugin-react": "^4.6.0",
"react": "^19.1.0",
"react-dom": "^19.1.0",
"sass": "^1.89.2",
"typescript": "^5.8.3",
"vite": "^7.0.4"
},
"peerDependencies": {
"react": ">=16.8.0",
"react-dom": ">=16.8.0"
}
},
"node_modules/@ampproject/remapping": {
@ -1430,6 +1436,16 @@
"dev": true,
"license": "MIT"
},
"node_modules/@types/node": {
"version": "24.0.14",
"resolved": "https://registry.npmjs.org/@types/node/-/node-24.0.14.tgz",
"integrity": "sha512-4zXMWD91vBLGRtHK3YbIoFMia+1nqEz72coM42C5ETjnNCa/heoj7NT1G67iAfOqMmcfhuCZ4uNpyz8EjlAejw==",
"dev": true,
"license": "MIT",
"dependencies": {
"undici-types": "~7.8.0"
}
},
"node_modules/@types/react": {
"version": "19.1.8",
"resolved": "https://registry.npmjs.org/@types/react/-/react-19.1.8.tgz",
@ -1898,6 +1914,7 @@
"version": "19.1.0",
"resolved": "https://registry.npmjs.org/react/-/react-19.1.0.tgz",
"integrity": "sha512-FS+XFBNvn3GTAWq26joslQgWNoFu08F4kl0J4CgdNKADkdSGXQyTCnKteIAJy96Br6YbpEU1LSzV5dYtjMkMDg==",
"dev": true,
"license": "MIT",
"engines": {
"node": ">=0.10.0"
@ -1907,6 +1924,7 @@
"version": "19.1.0",
"resolved": "https://registry.npmjs.org/react-dom/-/react-dom-19.1.0.tgz",
"integrity": "sha512-Xs1hdnE+DyKgeHJeJznQmYMIBG3TKIHJJT95Q58nHLSrElKlGQqDTR2HQ9fx5CN/Gk6Vh/kupBTDLU11/nDk/g==",
"dev": true,
"license": "MIT",
"dependencies": {
"scheduler": "^0.26.0"
@ -2003,6 +2021,7 @@
"version": "0.26.0",
"resolved": "https://registry.npmjs.org/scheduler/-/scheduler-0.26.0.tgz",
"integrity": "sha512-NlHwttCI/l5gCPR3D1nNXtWABUmBwvZpEQiD4IXSbIDq8BzLIK/7Ir5gTFSGZDUu37K5cMNp0hFtzO38sC7gWA==",
"dev": true,
"license": "MIT"
},
"node_modules/semver": {
@ -2096,6 +2115,13 @@
"node": ">=14.17"
}
},
"node_modules/undici-types": {
"version": "7.8.0",
"resolved": "https://registry.npmjs.org/undici-types/-/undici-types-7.8.0.tgz",
"integrity": "sha512-9UJ2xGDvQ43tYyVMpuHlsgApydB8ZKfVYTsLDhXkFL/6gfkp+U8xTGdh8pMJv1SpZna0zxG1DwsKZsreLbXBxw==",
"dev": true,
"license": "MIT"
},
"node_modules/update-browserslist-db": {
"version": "1.1.3",
"resolved": "https://registry.npmjs.org/update-browserslist-db/-/update-browserslist-db-1.1.3.tgz",

@ -1,25 +1,53 @@
{
"name": "react-calendar",
"private": true,
"version": "0.0.0",
"name": "react-calendario",
"version": "1.0.0",
"description": "A modern, flexible calendar component for React with TypeScript support",
"type": "module",
"main": "dist/index.js",
"module": "dist/index.es.js",
"types": "dist/index.d.ts",
"files": [
"dist"
],
"scripts": {
"dev": "vite",
"build": "tsc && vite build",
"preview": "vite preview"
"build:lib": "tsc --declaration --emitDeclarationOnly --outDir dist && vite build --config vite.config.lib.ts",
"preview": "vite preview",
"prepublishOnly": "npm run build:lib"
},
"keywords": [
"react",
"calendar",
"date",
"datepicker",
"date-range",
"typescript",
"component"
],
"author": "",
"license": "MIT",
"repository": {
"type": "git",
"url": "https://github.com/yourusername/react-calendario"
},
"peerDependencies": {
"react": ">=16.8.0",
"react-dom": ">=16.8.0"
},
"dependencies": {
"react": "^19.1.0",
"react-dom": "^19.1.0",
"date-fns": "^4.1.0",
"classnames": "^2.5.1"
"classnames": "^2.5.1",
"date-fns": "^4.1.0"
},
"devDependencies": {
"@types/node": "^24.0.14",
"@types/react": "^19.1.8",
"@types/react-dom": "^19.1.6",
"@vitejs/plugin-react": "^4.6.0",
"react": "^19.1.0",
"react-dom": "^19.1.0",
"sass": "^1.89.2",
"typescript": "^5.8.3",
"vite": "^7.0.4",
"sass": "^1.89.2"
"vite": "^7.0.4"
}
}

Loading…
Cancel
Save