npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

nepali-bs-calendar-react

v0.2.0

Published

A lightweight React Nepali Bikram Sambat calendar/date picker component.

Readme

Nepali BS Calendar React

A lightweight, responsive React Nepali Bikram Sambat calendar/date picker component.

This package provides a Nepali BS date picker with support for:

  • Dynamic calendar data via React Context
  • Static calendar component (non-popup)
  • Nepali Bikram Sambat calendar dates
  • Controlled date value
  • Minimum and maximum date limits
  • Disabled dates
  • Custom date disabling logic
  • Error message support
  • Responsive popup positioning
  • Portal-based dropdown rendering
  • CSS variable based styling overrides

Example

View the example here


Installation

npm install nepali-bs-calendar-react

Setup (Required)

You must wrap your application (or the part using the calendar) with the NepaliCalendarProvider. This allows you to provide the calendar data dynamically.

import { NepaliCalendarProvider, defaultCalendarData } from 'nepali-bs-calendar-react'

function App() {
  return (
    <NepaliCalendarProvider data={defaultCalendarData}>
      {/* Your components */}
    </NepaliCalendarProvider>
  )
}

New In version 0.2.0

  • Performance optimizations for date conversion functions
  • Interactive documentation for the calendar added here

Basic Usage (Popup Picker)

import { useState } from 'react'
import { NepaliCalendar } from 'nepali-bs-calendar-react'
import 'nepali-bs-calendar-react/styles.css'

export default function MyComponent() {
  const [date, setDate] = useState<string | null>(null)

  return (
    <NepaliCalendar
      label="Select Transaction Date"
      value={date}
      onChange={(value) => setDate(value)}
      minDate="2080-01-01"
      maxDate="2081-12-30"
    />
  )
}

Static Calendar Usage

If you want to display the calendar directly on the page without a popup, use StaticNepaliCalendar.

import { useState } from 'react'
import { StaticNepaliCalendar } from 'nepali-bs-calendar-react'

export default function MyComponent() {
  const [date, setDate] = useState<string | null>(null)

  return (
    <StaticNepaliCalendar
      value={date}
      onChange={(value) => setDate(value)}
    />
  )
}

Dynamic Calendar Data

You can provide your own calendar data if you need to support more years or custom month lengths.

import { NepaliCalendarProvider, CalendarData } from 'nepali-bs-calendar-react'

const customData: CalendarData = {
  ref_ad: '2019-12-17',
  ref_bs: '2076-09-01',
  years: {
    2076: [31, 32, 31, 32, 31, 30, 30, 30, 29, 29, 30, 30],
    // ... add more years
  },
}

function App() {
  return (
    <NepaliCalendarProvider data={customData}>
      <NepaliCalendar />
    </NepaliCalendarProvider>
  )
}

If your bundler does not automatically include library CSS, import it manually:

import 'nepali-bs-calendar-react/styles.css'

Date Format

The component expects and returns BS dates in this format:

YYYY-MM-DD

Example:

2081-05-12

Props

| Prop | Type | Default | Description | | :--- | :--- | :--- | :--- | | value | string \| null | null | Current selected BS date in YYYY-MM-DD format. | | onChange | (value: string, date: NepaliDateValue) => void | - | Callback triggered when a date is selected. | | minDate | string | - | Minimum selectable BS date in YYYY-MM-DD format. | | maxDate | string | - | Maximum selectable BS date in YYYY-MM-DD format. | | disabledDates | string[] | [] | Specific disabled BS dates in YYYY-MM-DD format. | | isDateDisabled | (date: NepaliDateValue) => boolean | - | Custom function to disable a date. | | label | string | - | Label displayed above the picker. | | placeholder | string | Select date | Placeholder text when no date is selected. | | disabled | boolean | false | Disables the picker. | | error | string | - | Error message shown below the picker. | | touched | boolean | false | Shows error only when touched is true. | | className | string | "" | Extra class name added to the main wrapper. |


Type Reference

type NepaliDateValue = {
  year: number
  month: number
  day: number
}

onChange Example

<NepaliCalendar
  value={date}
  onChange={(value, dateObject) => {
    console.log(value)
    console.log(dateObject)
  }}
/>

Output:

"2081-05-12"

{
  year: 2081,
  month: 5,
  day: 12
}

Disable Specific Dates

<NepaliCalendar
  value={date}
  onChange={setDate}
  disabledDates={[
    '2081-01-01',
    '2081-01-15',
    '2081-02-10',
  ]}
/>

Minimum and Maximum Date

<NepaliCalendar
  value={date}
  onChange={setDate}
  minDate="2080-01-01"
  maxDate="2081-12-30"
/>

Custom Disabled Date Logic

You can disable dates using your own logic.

<NepaliCalendar
  value={date}
  onChange={setDate}
  isDateDisabled={(date) => {
    return date.day === 1
  }}
/>

Error Message

<NepaliCalendar
  label="Transaction Date"
  value={date}
  onChange={setDate}
  error="Transaction date is required"
  touched={true}
/>

The error only appears when both error and touched are provided.


Disabled Picker

<NepaliCalendar
  value={date}
  onChange={setDate}
  disabled
/>

Responsive Popup Behavior

The calendar popup is rendered using React Portal.

It automatically:

  • Opens below the trigger when there is enough space
  • Opens above the trigger when the trigger is near the bottom of the screen
  • Stays inside the viewport
  • Adjusts its width on small screens
  • Repositions on scroll and resize
  • Uses throttled positioning for better performance

This makes it suitable for desktop, tablet, and mobile layouts.


Styling

Import the default styles:

import 'nepali-bs-calendar-react/styles.css'

The component uses CSS variables, so you can customize the design without editing the package source code.

Because the popup uses createPortal, the safest way to override styles is by defining variables globally in your app CSS using :root.

Example:

:root {
  --ndp-trigger-border: #22c55e;
  --ndp-trigger-border-hover: #16a34a;
  --ndp-trigger-radius: 12px;
  --ndp-trigger-focus-shadow: 0 0 0 2px rgba(22, 163, 74, 0.16);

  --nc-bg: #f0fdf4;
  --nc-border-color: #bbf7d0;
  --nc-border-radius: 18px;
  --nc-title-color: #14532d;
  --nc-weekday-color: #15803d;
  --nc-cell-hover-bg: #dcfce7;
  --nc-cell-selected-bg: #16a34a;
  --nc-cell-selected-hover-bg: #15803d;
  --nc-cell-selected-color: #ffffff;
  --nc-shadow: 0 16px 40px rgba(20, 83, 45, 0.18);
}

Scoped Styling Note

You can pass a custom class name:

<NepaliCalendar
  className="my-nepali-calendar"
  value={date}
  onChange={setDate}
/>

However, because the popup is rendered through createPortal, wrapper-scoped CSS variables may only affect the trigger, not the popup.

For example, this may not fully style the popup:

.my-nepali-calendar {
  --nc-bg: #f0fdf4;
}

Recommended approach:

:root {
  --nc-bg: #f0fdf4;
}

or apply variables to body:

body {
  --nc-bg: #f0fdf4;
}

Available CSS Variables

Date Picker Variables

| Variable | Default | Description | | :--- | :--- | :--- | | --ndp-width | 100% | Main picker width. | | --ndp-gap | 6px | Gap between label, trigger, and error. | | --ndp-label-font-size | 14px | Label font size. | | --ndp-label-font-weight | 500 | Label font weight. | | --ndp-label-color | #222 | Label color. | | --ndp-trigger-min-height | 40px | Trigger button minimum height. | | --ndp-trigger-border | #d9d9d9 | Trigger border color. | | --ndp-trigger-border-hover | #4096ff | Trigger hover/open border color. | | --ndp-trigger-radius | 8px | Trigger border radius. | | --ndp-trigger-bg | #fff | Trigger background. | | --ndp-trigger-padding | 8px 12px | Trigger padding. | | --ndp-trigger-focus-shadow | 0 0 0 2px rgba(5, 145, 255, 0.12) | Focus shadow. | | --ndp-trigger-disabled-bg | #f5f5f5 | Disabled trigger background. | | --ndp-trigger-disabled-color | rgba(0, 0, 0, 0.25) | Disabled trigger text color. | | --ndp-value-color | rgba(0, 0, 0, 0.88) | Selected value text color. | | --ndp-placeholder-color | rgba(0, 0, 0, 0.4) | Placeholder color. | | --ndp-error-color | #ff4d4f | Error color. | | --ndp-error-font-size | 13px | Error font size. | | --ndp-popover-min-width | 280px | Minimum popup width. |


Calendar Variables

| Variable | Default | Description | | :--- | :--- | :--- | | --nc-border-color | #e5e7eb | Calendar border color. | | --nc-border-radius | 12px | Calendar border radius. | | --nc-bg | #fff | Calendar background. | | --nc-shadow | 0 12px 32px rgba(15, 23, 42, 0.18) | Calendar shadow. | | --nc-padding | 14px | Calendar padding. | | --nc-font-family | system-ui, -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif | Calendar font family. | | --nc-header-gap | 8px | Header gap. | | --nc-header-margin-bottom | 12px | Header bottom margin. | | --nc-title-font-size | 16px | Calendar title font size. | | --nc-title-font-weight | 600 | Calendar title font weight. | | --nc-title-color | #111827 | Calendar title color. | | --nc-nav-btn-size | 32px | Previous/next button size. | | --nc-nav-btn-border-color | #e5e7eb | Previous/next button border color. | | --nc-nav-btn-radius | 8px | Previous/next button radius. | | --nc-nav-btn-bg | #fff | Previous/next button background. | | --nc-nav-btn-color | #111827 | Previous/next button text color. | | --nc-nav-btn-hover-bg | #f9fafb | Previous/next hover background. | | --nc-nav-btn-font-size | 22px | Previous/next arrow font size. | | --nc-controls-gap | 8px | Gap between year, month, and day selects. | | --nc-controls-margin-bottom | 12px | Controls bottom margin. | | --nc-select-height | 34px | Select input height. | | --nc-select-border-color | #d1d5db | Select input border color. | | --nc-select-radius | 8px | Select input border radius. | | --nc-select-bg | #fff | Select input background. | | --nc-select-color | #111827 | Select input text color. | | --nc-select-padding | 0 8px | Select input padding. | | --nc-grid-gap | 4px | Gap between date cells. | | --nc-weekdays-margin-bottom | 6px | Weekday row bottom margin. | | --nc-weekday-font-size | 12px | Weekday font size. | | --nc-weekday-font-weight | 600 | Weekday font weight. | | --nc-weekday-color | #6b7280 | Weekday text color. | | --nc-cell-min-height | 36px | Date cell minimum height. | | --nc-cell-radius | 8px | Date cell border radius. | | --nc-cell-bg | transparent | Date cell background. | | --nc-cell-color | #111827 | Date cell text color. | | --nc-cell-hover-bg | #f3f4f6 | Date cell hover background. | | --nc-cell-selected-bg | #1677ff | Selected date background. | | --nc-cell-selected-color | #fff | Selected date text color. | | --nc-cell-selected-hover-bg | #1677ff | Selected date hover background. | | --nc-cell-disabled-color | #bdbdbd | Disabled date text color. | | --nc-cell-disabled-bg | transparent | Disabled date background. |


Mobile Styling Variables

You can also customize mobile-specific values.

:root {
  --nc-mobile-padding: 12px;
  --nc-mobile-title-font-size: 15px;
  --nc-mobile-nav-btn-size: 30px;
  --nc-mobile-cell-min-height: 34px;
  --nc-mobile-cell-font-size: 13px;

  --nc-small-padding: 10px;
  --nc-small-title-font-size: 14px;
  --nc-small-cell-min-height: 32px;
  --nc-small-cell-font-size: 12px;

  --nc-tiny-padding: 8px;
  --nc-tiny-cell-min-height: 30px;
  --nc-tiny-cell-font-size: 11px;
}

Utility Exports

import {
  adToBs,
  bsToAd,
  adStringToBs,
  bsStringToAd,
  formatBSDate,
  parseBSDate,
  isValidBSDate,
  getAvailableYears,
  getMonthDays,
  toNepaliNumber,
} from 'nepali-bs-calendar-react'

Supported Date Range

The calendar currently supports dates from 2076 BS to 2090 BS based on the bundled calendar data.


Development

Clone the project and install dependencies:

npm install

Build the package:

npm run build

Create a local npm package file:

npm pack

Local Testing With a Demo App

From your library folder:

npm install
npm run build

Create a separate Vite React app:

cd ..
npm create vite@latest nepali-calendar-demo -- --template react-ts
cd nepali-calendar-demo
npm install

Install your local package:

npm install ../nepali-calendar-package

Use it in src/App.tsx:

import { useState } from 'react'
import NepaliCalendar from 'nepali-bs-calendar-react'
import 'nepali-bs-calendar-react/styles.css'

export default function App() {
  const [date, setDate] = useState<string | null>(null)

  return (
    <div style={{ padding: 40 }}>
      <NepaliCalendar
        label="Select Date"
        value={date}
        onChange={setDate}
      />
    </div>
  )
}

Run the demo app:

npm run dev

Publishing

  1. Make sure the package name in package.json is available on npm.
{
  "name": "nepali-bs-calendar-react"
}
  1. Log in to npm:
npm login
  1. Build the package:
npm run build
  1. Publish:
npm publish --access public

License

MIT