Panchang Core — Advanced Vedic Astrology Engine for PHP

Introduction

Authentic Vedic Panchanga calculation engine with Swiss Ephemeris precision.

Overview

Panchang Core is a comprehensive PHP package for calculating Vedic Panchanga elements, Muhūrtas, and Hindu festivals with maximum astronomical precision. Built on Swiss Ephemeris FFI, it provides zero-tolerance calculations for authentic Vedic astrology applications.

Complete Panchanga

Tithi, Vara, Nakṣatra, Yoga, Karaṇa with precise fractions

🕉

162 Hindu Festivals

Comprehensive library covering major and minor festivals for all regions and traditions.

Muhūrta

Abhijit, Brahma Muhūrta, Rahu Kāla, Gulika, Yamaganda

Regional Support

Smarta, Vaishnava, North, South, Bengal, Maharashtra, Tamil traditions

Classical Sources

Classical Sanskrit texts used for calculations
Text Implementation
Sūrya Siddhānta (Sage-Attributed)
Sūrya Siddhānta 1.29 Tithi calculation
Sūrya Siddhānta 8.1 Nakṣatra calculation
Sūrya Siddhānta Yoga, Karana
Sūrya Siddhānta 1.10 Muhūrta
Sūrya Siddhānta 1.11 Ghaṭikā, Pala
Bṛhat Parāśara Horā Śāstra (BPHS)
BPHS Vimśottarī Daśā System, Nakṣatra lords, Daśā years
BPHS Horā
Bṛhat Saṃhitā (Varāhamihira)
Bṛhat Saṃhitā 8 Samvatsara
Bṛhat Saṃhitā Ritu
Muhūrta & Kāla Nirṇaya
Muhūrta Chintāmaṇi Aruṇodaya, Pradoṣa, Bhadra
Ashtānga Hṛdaya Brahma Muhūrta
Charaka Saṃhitā Muhūrta
Kāla Nirṇaya Choghadiya
Festival Resolution
Nirṇaya Sindhu Bhadra rules, Festival timing
Dharma Sindhu Holikā Dahan, Vṛddhi/Kṣaya
Hari Bhakti Vilāsa Ekādaśī
Modern Astronomy
Swiss Ephemeris Vara (weekday), Ayanāṃśa, Graha Sphuṭa

Installation

Composer Install
composer require jayeshmepani/panchang-core

Requirements

  • PHP 8.3+— uses typed constants, readonly classes, enums
  • Swiss Ephemeris FFI— jayeshmepani/swiss-ephemeris-ffi
  • Carbon— nesbot/carbon
  • FFI Extension— required for Swiss Ephemeris

Quick Start

Standalone Usage
<?php

require 'vendor/autoload.php';

use JayeshMepani\PanchangCore\Panchanga\PanchangService;
use JayeshMepani\PanchangCore\Astronomy\AstronomyService;
use JayeshMepani\PanchangCore\Astronomy\SunService;
use JayeshMepani\PanchangCore\Panchanga\PanchangaEngine;
use JayeshMepani\PanchangCore\Panchanga\MuhurtaService;
use JayeshMepani\PanchangCore\Festivals\FestivalService;
use JayeshMepani\PanchangCore\Festivals\FestivalRuleEngine;
use JayeshMepani\PanchangCore\Festivals\FestivalFamilyOrchestrator;
use JayeshMepani\PanchangCore\Festivals\Utils\BhadraEngine;
use SwissEph\FFI\SwissEphFFI;
use Carbon\CarbonImmutable;

// Initialize services
$sweph = new SwissEphFFI();
$ruleEngine = new FestivalRuleEngine();
$orchestrator = new FestivalFamilyOrchestrator();

$panchang = new PanchangService(
    $sweph,
    new SunService($sweph),
    new AstronomyService($sweph),
    new PanchangaEngine(),
    new MuhurtaService(),
    new FestivalService($ruleEngine, $orchestrator),
    new BhadraEngine()
);

// Calculate panchanga
$date = CarbonImmutable::parse('2026-03-24');
$details = $panchang->getDayDetails(
    date: $date,
    lat: 23.2472446,
    lon: 69.668339,
    tz: 'Asia/Kolkata'
);

echo "Tithi: " . $details['Tithi']['name'] . "\n";
echo "Nakshatra: " . $details['Nakshatra']['name'] . "\n";

Configuration

Global settings and formatting preferences available in config/panchang.php.

Overview

When running inside Laravel, you can publish the configuration file to config/panchang.php. These settings control the default formatting across the entire package output, allowing you to globally enforce timezone notations, unit systems, and double precision decimals.

Default Calculation Options

The defaultsarray configures formatting representations.

Default calculation configuration options
Setting Description Acceptable Values
measurement_system Unit system for generic dimensions and lengths. indian_metric: Metric (meters, km)
western: Imperial (feet, miles)
date_time_format String formatting of generic date-time outputs. indian_12h: "24/03/2026 06:14:00 AM"
indian_24h: "24/03/2026 06:14:00"
iso8601: "2026-03-24T06:14:00+05:30"
time_notation Global time output behavior (sunrise, sunset, muhurtas). 12h: "06:14:00 AM"
24h: "06:14:00"
coordinate_format Format for geographical coordinates. decimal: 23.2472446, 69.668339
dms: "23°14'50.1\"N, 69°40'06.0\"E"
angle_unit Format for astronomical degrees (planet longitudes, Ascendant, Ayanamsa). degree: 350.5234°
dms: "350°31'24\""
duration_format How lengths of time are formatted. mixed: "1h 30m 0s"
minutes: 90.0
seconds: 5400.0
hours: 1.5
number_precision Decimal points for all floating-point and angular outputs. Maximum accuracy guaranteed via IEEE 754. Integer (Default: 16)

Festival Calculation Settings

The festivalsarray provides defaults for region and tradition if not explicitly supplied.

Festival calculation configuration
Setting Description Acceptable Values
default_tradition Default sect or tradition used to resolve conflicting festival rules. Smarta, Vaishnava
default_region Default geographical region for festival rule variations. North, South, Bengal, Maharashtra, Tamil

Timing Semantics

  • Time-only fields include date-qualified companion keys as *_iso where applicable.
  • Panchang day is evaluated from sunrise to next sunrise; times earlier than sunrise belong to next civil date.
  • Varjyam supports multiple windows via window_count and windows[].
  • Pradosha_Kaal in day output includes base night window and Trayodashi-overlap effective window.

Nakshatra

Enum: JayeshMepani\PanchangCore\Core\Enums\Nakshatra

Represents the 27 lunar mansions in Vedic astrology. Each nakṣatra spans 13°20' of the zodiac.

Quick Usage

use JayeshMepani\PanchangCore\Core\Enums\Nakshatra;

// Get nakshatra from moon longitude
$nakshatra = Nakshatra::fromLongitude(125.3); // Magha

echo $nakshatra->getName();          // "Magha"
echo $nakshatra->getDeity();         // "Pitṛs"
echo $nakshatra->getRulingPlanet(); // "Sun"
echo $nakshatra->getSymbol();       // "Royal Throne"

// Get pada (quarter)
$pada = Nakshatra::getPada(125.3);    // 2
echo "Pada: $pada\n";                // Pada: 2

// Get longitude range
$range = Nakshatra::Ashwini->getLongitudeRange();
echo $range['start'] . "° - " . $range['end'] . "°\n"; // 0° - 13.333°

Cases

Ashwini
Bharani
Krittika
Rohini
Mrigashira
Ardra
Punarvasu
Pushya
Ashlesha
Magha
PurvaPhalguni
UttaraPhalguni
Hasta
Chitra
Swati
Vishakha
Anuradha
Jyeshtha
Mula
PurvaAshadha
UttaraAshadha
Shravana
Dhanishta
Shatabhisha
PurvaBhadrapada
UttaraBhadrapada
Revati

Methods

getName()

Get Sanskrit name

public function getName(): string
Returns:string— Sanskrit name

getDeity()

Get deity of the nakṣatra

public function getDeity(): string
Returns:string— Deity name

getRulingPlanet()

Get ruling planet

public function getRulingPlanet(): string
Returns:string— Planet name

getSymbol()

Get Vedic symbol

public function getSymbol(): string
Returns:string— Symbol description

getLongitudeRange()

Get Vedic longitude range

public function getLongitudeRange(): array{start: float, end: float}
Returns:array— Longitude range in degrees

fromLongitude()

Get nakṣatra from longitude

public static function fromLongitude(float $longitude): self
Parameters:
  • $longitude(float) — Longitude in degrees (0–360)
Returns:self— Nakṣatra instance

getPada()

Get pada (quarter) from longitude

public static function getPada(float $longitude): int
Parameters:
  • $longitude(float) — Longitude in degrees
Returns:int— Pada number (1–4)

Tithi

Enum: JayeshMepani\PanchangCore\Core\Enums\Tithi

Represents the 30 lunar days in a Hindu lunar month. Each tithi is completed when the Moon gains 12° on the Sun.

Quick Usage

use JayeshMepani\PanchangCore\Core\Enums\Tithi;

// Get tithi by index (1-30)
$tithi = Tithi::from(12); // Shukla Dwadashi

echo $tithi->getName();            // "Dwadashi"
echo $tithi->getPaksha()->name;    // "Shukla"

// Check paksha
if ($tithi->getPaksha() === Paksha::Shukla) {
    echo "Waxing moon phase\n";
}

// Get normalized index (1-15 for both pakshas)
echo $tithi->getNormalizedIndex(); // 12

Cases

ShuklaPratipada
ShuklaDwitiya
ShuklaTritiya
ShuklaChaturthi
ShuklaPanchami
ShuklaShashthi
ShuklaSaptami
ShuklaAshtami
ShuklaNavami
ShuklaDashami
ShuklaEkadashi
ShuklaDwadashi
ShuklaTrayodashi
ShuklaChaturdashi
Purnima
KrishnaPratipada
KrishnaDwitiya
KrishnaTritiya
KrishnaChaturthi
KrishnaPanchami
KrishnaShashthi
KrishnaSaptami
KrishnaAshtami
KrishnaNavami
KrishnaDashami
KrishnaEkadashi
KrishnaDwadashi
KrishnaTrayodashi
KrishnaChaturdashi
Amavasya

Methods

getName()

Get Sanskrit name

public function getName(): string
Returns:string— Name (e.g., 'Pratipada', 'Purnima')

getPaksha()

Get pakṣa (fortnight)

public function getPaksha(): Paksha
Returns:Paksha— Shukla or Krishna

getNormalizedIndex()

Get normalized index (1–15)

public function getNormalizedIndex(): int
Returns:int— Index within pakṣa

isEkadashi()

Check if this is Ekadashi

public function isEkadashi(): bool
Returns:bool

isPurnimaOrAmavasya()

Check if Purnima or Amavasya

public function isPurnimaOrAmavasya(): bool
Returns:bool

fromLongitudes()

Get tithi from Sun-Moon longitudes

public static function fromLongitudes(float $sunLon, float $moonLon): self
Parameters:
  • $sunLon(float) — Sun longitude in degrees
  • $moonLon(float) — Moon longitude in degrees
Returns:self

getFractionRemaining()

Get fraction remaining in tithi

public static function getFractionRemaining(float $sunLon, float $moonLon): float
Returns:float— Fraction (0.0–1.0)

Paksha

Enum: JayeshMepani\PanchangCore\Core\Enums\Paksha

Represents the two fortnights in a lunar month.

Cases

Shukla
Krishna

Methods

getName()

Get Sanskrit name

public function getName(): string

getDescription()

Get description

public function getDescription(): string

getTithiRange()

Get tithi range

public function getTithiRange(): array{start: int, end: int}

containsTithi()

Check if tithi belongs to this pakṣa

public function containsTithi(int $tithiIndex): bool

normalizeTithi()

Normalize tithi to 1–15 range

public function normalizeTithi(int $tithiIndex): int

Yoga

Enum: JayeshMepani\PanchangCore\Core\Enums\Yoga

Represents the 27 yogas. Each yoga is completed when the Sun-Moon longitude sum advances by 13°20'.

Cases

Vishkambha
Priti
Ayushman
Saubhagya
Shobhana
Atiganda
Sukarma
Dhriti
Shula
Ganda
Vriddhi
Dhruva
Vyaghata
Harshana
Vajra
Siddhi
Vyatipata
Variyana
Parigha
Shiva
Siddha
Sadhya
Shubha
Shukla
Brahma
Aindra
Vaidhriti

Methods

getName()

Get Sanskrit name

public function getName(): string

fromLongitudes()

Get yoga from Sun-Moon longitudes

public static function fromLongitudes(float $sunLon, float $moonLon): self

Karana

Enum: JayeshMepani\PanchangCore\Core\Enums\Karana

Represents the 11 karanas (half lunar days). Each tithi is divided into two karanas.

Cases

Bava
Balava
Kaulava
Taitila
Gara
Vanija
Vishti
Shakuni
Chatushpada
Naga
Kimstughna

Methods

getName()

Get Sanskrit name

public function getName(): string

getType()

Get type (Chara/Sthira)

public function getType(): string

isVishti()

Check if this is Vishti (Bhadra)

public function isVishti(): bool

fromTithi()

Get karana from tithi

public static function fromTithi(int $tithiIndex, float $fraction): self

Vara

Enum: JayeshMepani\PanchangCore\Core\Enums\Vara

Represents the 7 weekdays, each ruled by a planet.

Cases

Sunday
Monday
Tuesday
Wednesday
Thursday
Friday
Saturday

Methods

getName()

Get Sanskrit name

public function getName(): string

getEnglishName()

Get English name

public function getEnglishName(): string

getRulingPlanet()

Get ruling planet

public function getRulingPlanet(): string

fromJulianDay()

Get weekday from Julian Day

public static function fromJulianDay(float $jd): self

Core Enums

Basic enumeration types used throughout the package.

Ritu (Seasons)

Represents the 6 Hindu seasons. Each ṛtu spans 2 lunar months.

Vasanta(Spring)
Grishma(Summer)
Varsha(Monsoon)
Sharad(Autumn)
Hemanta(Pre-Winter)
Shishira(Winter)
Usage:PanchangaEngine::getRitu($sunLon)returns season from Sun longitude

Masa (Lunar Months)

Represents the 12 lunar months in the Hindu calendar.

Chaitra
Vaishakha
Jyeshtha
Ashadha
Shravana
Bhadrapada
Ashvina
Kartika
Margashirsha
Pausha
Magha
Phalguna
Usage:PanchangaEngine::getHinduMonth($sunLon, $moonLon)

Samvatsara (60-Year Cycle)

Represents the 60 years in the Jupiter cycle.

Prabhava
Vibhava
Shukla
Pramoda
Prajapati
… (60 total)
Usage:PanchangaEngine::getSamvatsara($vikramSamvat)

Rasi (Zodiac Signs)

Represents the 12 zodiac signs in Vedic astrology.

Mesha(Aries)
Vrishabha(Taurus)
Mithuna(Gemini)
Karka(Cancer)
Simha(Leo)
Kanya(Virgo)
Tula(Libra)
Vrischika(Scorpio)
Dhanu(Sagittarius)
Makara(Capricorn)
Kumbha(Aquarius)
Meena(Pisces)
Usage:Used internally for sign calculations. Each rasi spans 30°.

Vimshottari Dasha

Planetary periods in Vedic astrology, summing to 120 years.

Ketu(7 yr)
Venus(20 yr)
Sun(6 yr)
Moon(10 yr)
Mars(7 yr)
Rahu(18 yr)
Jupiter(16 yr)
Saturn(19 yr)
Mercury(17 yr)

Muhurta

Represents the 30 divisions of a day (approx 48 minutes each).

Rudra
Ahi
Mitra
Pitri
Vasu
Varaha
Vishvedeva
Vidhi
… (30 total)
Usage:MuhurtaService::calculateMuhurtaTable($sunrise, $sunset, $nextSunrise)

Choghadiya

8 day and night time divisions primarily used in North & West India.

Udveg(Inauspicious)
Chal(Neutral)
Labh(Auspicious)
Amrita(Very Auspicious)
Kala(Inauspicious)
Shubh(Auspicious)
Rog(Inauspicious)
Usage:MuhurtaService::calculateChoghadiyaTable()

Hora

24 hourly planetary divisions of a day.

Sun
Venus
Mercury
Moon
Saturn
Jupiter
Mars
Usage:MuhurtaService::calculateHoraTable()— Each hora spans ~1 hour

PanchangService

Service: JayeshMepani\PanchangCore\Panchanga\PanchangService

Facade-like service that orchestrates all underlying components to provide complete daily details.

Methods

getDayDetails()

Returns complete Panchanga details for a given date and location. Includes Tithi, Nakshatra, Yoga, Karana, Muhurta, Choghadiya, Hora, and festival data.

public function getDayDetails(CarbonImmutable $date, float $lat, float $lon, string $tz, float $elevation=0.0, ?CarbonImmutable $ayanamsaAt=null, array $options=[]): array
Parameters:
$date(CarbonImmutable) — Date to calculate
$lat(float) — Latitude in degrees
$lon(float) — Longitude in degrees
$tz(string) — Timezone (e.g., 'Asia/Kolkata')
$elevation(float, optional) — Elevation in meters (default: 0.0)
$ayanamsaAt(CarbonImmutable, optional) — Custom ayanamsa calculation time
$options(array, optional) — Additional options
Returns:array — Complete panchanga data with keys: Tithi, Nakshatra, Yoga, Karana, Vara, Muhurta, Choghadiya, Hora, Festivals, etc.

getFestivalSnapshot()

Lightweight daily snapshot for festival resolution. Faster than getDayDetails when you only need festival data.

public function getFestivalSnapshot(CarbonImmutable $date, float $lat, float $lon, string $tz, float $elevation=0.0): array
Parameters:
$date(CarbonImmutable) — Date to calculate
$lat(float) — Latitude
$lon(float) — Longitude
$tz(string) — Timezone
$elevation(float, optional) — Elevation in meters
Returns:array — Festival data and minimal panchanga elements.

configure()

Global configuration for the service (typically used in standalone mode).

public static function configure(string $ephePath, string $ayanamsa='LAHIRI'): void
Parameters:
  • $ephePath(string) — Absolute path to ephemeris files
  • $ayanamsa(string) — 'LAHIRI', 'RAMAN', or 'KRISHNAMURTI'

AstronomyService

Service: JayeshMepani\PanchangCore\Astronomy\AstronomyService

Calculates planetary longitudes and Julian Days using Swiss Ephemeris.

Methods

toJulianDayUtc()

Convert birth data array to high-precision Julian Day (UTC).

public function toJulianDayUtc(array $birth): float
Parameters:
$birth(array) — Associative array: [year, month, day, hour, minute, second, timezone]
Returns:float — Julian Day number (UT1)

getPlanets()

Returns all planetary longitudes for a given birth details.

public function getPlanets(array $birth): array
Parameters:
$birth(array) — Birth details with location and time.
Returns:array — Map of planet names to longitudinal degrees.

getAscendant()

Calculate the Ascendant (Lagna) longitude for a specific time and location.

public function getAscendant(array $birth): float
Parameters:
$birth(array) — Birth details.
Returns:float — Ascendant longitude in degrees.

getAyanamsa()

Get the ayanamsa (sidereal difference) value for a given Julian Day.

public function getAyanamsa(float $jd): float
Parameters:
$jd(float) — Julian Day (UTC).
Returns:float — Ayanamsa in decimal degrees.

SunService

Service: JayeshMepani\PanchangCore\Astronomy\SunService

Calculates sunrise, sunset, and solar events using precision algorithms.

Methods

getSunriseSunset()

Calculate exact sunrise and sunset times for a location.

public function getSunriseSunset(array $birth): array
Parameters:
$birth(array) — Birth details with lat/lon and date.
Returns:array[CarbonImmutable sunrise, CarbonImmutable sunset]

getMoonriseMoonset()

Calculate moonrise and moonset times (geocentric).

public function getMoonriseMoonset(array $birth): array
Parameters:
$birth(array) — Birth details.
Returns:array[CarbonImmutable moonrise, CarbonImmutable moonset]

getTwilightTimes()

Calculate civil, nautical, and astronomical twilight boundaries.

public function getTwilightTimes(array $birth): array
Parameters:
$birth(array) — Birth details.
Returns:array — Map of twilight phases.

isDayBirth()

Check if a specific time occurs between sunrise and sunset.

public function isDayBirth(array $birth): bool
Parameters:
$birth(array) — Birth details.
Returns:bool — True if daylight birth.

PanchangaEngine

Service: JayeshMepani\PanchangCore\Panchanga\PanchangaEngine

Core panchanga calculation engine for tithi, yoga, karana, and seasonal logic (no ephemeris dependencies).

Methods

calculateTithi()

Calculate Tithi from Sun and Moon longitudes.

public function calculateTithi(float $sunLon, float $moonLon): array
Parameters:
$sunLon(float) — Sun longitude in degrees.
$moonLon(float) — Moon longitude in degrees.
Returns:array{index, name, paksha, fraction_left}
Example:

$tithi = $engine->calculateTithi(350.5, 125.3);
echo $tithi['name']; // "Dwadashi"
                

getNakshatraInfo()

Determine Nakshatra and Pada from a specific longitude.

public function getNakshatraInfo(float $longitude): array
Parameters:
$longitude(float) — Celestial longitude in degrees.
Returns:array[name, pada, lord]

calculateYoga()

Calculate Yoga from the sum of Sun and Moon longitudes.

public function calculateYoga(float $sunLon, float $moonLon): array
Parameters:
  • $sunLon(float) — Sun longitude.
  • $moonLon(float) — Moon longitude.
Returns:array{index, name}

getKarana()

Get the Karana (half-tithi) from celestial longitudes.

public function getKarana(float $sunLon, float $moonLon): array
Parameters:
  • $sunLon(float) — Sun longitude.
  • $moonLon(float) — Moon longitude.
Returns:array[name, number]

calculateVara()

Calculate weekday (Vara) relative to local sunrise.

public function calculateVara(array $birth, SunService $sunService): array
Parameters:
  • $birth(array) — Birth details.
  • $sunService(SunService) — Helper for sunrise timing.
Returns:array{index, name, lord}

getRitu()

Identify the Vedic season (Ritu) based on solar longitude.

public function getRitu(float $sunLon): string
Parameters:
  • $sunLon(float) — Sun longitude.
Returns:string — Sanskrit name of the season (e.g., "Sharad").

getAyana()

Identify the solar hemisphere (Uttarayana or Dakshinayana).

public function getAyana(float $sunLon): string
Parameters:
  • $sunLon(float) — Sun longitude.
Returns:string — "Uttarayana" or "Dakshinayana".

getSamvat()

Calculate Vikram Samvat and Saka Samvat years.

public function getSamvat(int $year, int $month): array
Parameters:
  • $year(int) — Gregorian year.
  • $month(int) — Gregorian month (1-12).
Returns:array{Vikram_Samvat, Saka_Samvat}

getSamvatsara()

Identify the Samvatsara name in the 60-year Jupiter cycle.

public function getSamvatsara(int $vikramSamvat): string
Parameters:
  • $vikramSamvat(int) — Vikram Samvat year.
Returns:string — Samvatsara name.

getHinduMonth()

Identify the Hindu lunar month for a given moment.

public function getHinduMonth(float $sunLon, float $moonLon, string $paksha='Shukla'): array
Parameters:
  • $sunLon(float) — Sun longitude.
  • $moonLon(float) — Moon longitude.
  • $paksha(string) — Current lunar phase.
Returns:array{Amanta, Purnimanta, Amanta_Index, Purnimanta_Index}

getSamvatsaraNorth()

Calculate North Indian Samvatsara name (variant cycle).

public function getSamvatsaraNorth(int $vikramSamvat): string
Parameters:
  • $vikramSamvat(int) — Vikram Samvat year.
Returns:string — North Samvatsara name.

getKaliSamvat()

Calculate the year in the Kali Yuga era.

public function getKaliSamvat(int $vikramSamvat): int
Parameters:
  • $vikramSamvat(int) — Vikram Samvat year.
Returns:int — Kali Samvat year.

getGujaratiSamvat()

Calculate the year in the Gujarati (Kartikadi) Samvat era.

public function getGujaratiSamvat(int $vikramSamvat, int $monthIdx): int
Parameters:
  • $vikramSamvat(int) — Vikram Samvat year.
  • $monthIdx(int) — Month index (0-11).
Returns:int — Gujarati Samvat year.

calculatePanchakaRahita()

Calculate Panchaka Rahita status for Muhurta selection (classical residual logic).

public function calculatePanchakaRahita(int $tithi, int $vara, int $nak, int $lagna): array
Parameters:
  • $tithi(int) — Tithi index.
  • $vara(int) — Weekday index.
  • $nak(int) — Nakshatra index.
  • $lagna(int) — Lagna index.
Returns:array{status, classification}

calculateKundaLagna()

Calculate Kunda Lagna (Ascendant * 81) used for birth time rectification.

public function calculateKundaLagna(float $ascendantLongitude): array
Parameters:
  • $ascendantLongitude(float) — Longitude of the Ascendant.
Returns:array{degrees, rasi}

isVishtiKarana()

Determine if the current moment falls under the inauspicious Vishti Karana (Bhadra).

public function isVishtiKarana(float $sunLon, float $moonLon): bool
Parameters:
  • $sunLon(float) — Sun longitude.
  • $moonLon(float) — Moon longitude.
Returns:bool — True if Bhadra is active.

MuhurtaService

Service: JayeshMepani\PanchangCore\Panchanga\MuhurtaService

Advanced engine for time-based divisions, auspicious periods, and negative time clusters.

Methods

calculateMuhurtaTable()

Calculate all 30 named Muhurtas for a full 24-hour cycle.

public function calculateMuhurtaTable(CarbonImmutable $sunrise, CarbonImmutable $sunset, CarbonImmutable $nextSunrise): array
Parameters:
  • $sunrise(CarbonImmutable) — Current day sunrise.
  • $sunset(CarbonImmutable) — Current day sunset.
  • $nextSunrise(CarbonImmutable) — Next day sunrise.
Returns:array — 30 muhurta objects with {name, start, end}.

calculateChoghadiyaTable()

Calculate 8 day and 8 night Choghadiya periods.

public function calculateChoghadiyaTable(CarbonImmutable $sunrise, CarbonImmutable $sunset, CarbonImmutable $nextSunrise, int $varaIdx): array
Parameters:
  • $sunrise(CarbonImmutable) — Sunrise time.
  • $sunset(CarbonImmutable) — Sunset time.
  • $nextSunrise(CarbonImmutable) — Next sunrise time.
  • $varaIdx(int) — Weekday index (0-6).
Returns:array — Detailed list of 16 Choghadiya divisions.

calculateHoraTable()

Identify the 24 planetary Hora rulers for the day.

public function calculateHoraTable(CarbonImmutable $sunrise, CarbonImmutable $sunset, CarbonImmutable $nextSunrise, int $varaIdx): array
Parameters:
  • $sunrise(CarbonImmutable) — Sunrise time.
  • $sunset(CarbonImmutable) — Sunset time.
  • $nextSunrise(CarbonImmutable) — Next sunrise time.
  • $varaIdx(int) — Weekday index (0-6).
Returns:array — 24 Hora objects with {planet, start, end}.

calculateAbhijitMuhurta()

Determine the most auspicious midday period (Abhijit).

public function calculateAbhijitMuhurta(CarbonImmutable $sunrise, CarbonImmutable $sunset): array
Parameters:
  • $sunrise(CarbonImmutable) — Sunrise time.
  • $sunset(CarbonImmutable) — Sunset time.
Returns:array{start, end, duration}.

calculateBrahmaMuhurta()

Identify the pre-dawn auspicious period (Brahma Muhurta).

public function calculateBrahmaMuhurta(CarbonImmutable $sunrise): array
Parameters:
$sunrise(CarbonImmutable) — Sunrise time.
Returns:array{start, end, name}

calculateLagnaTable()

Calculate full 12/13 Lagna (Ascendant) intervals for the day with exact sign entry times.

public function calculateLagnaTable(CarbonImmutable $sunrise, CarbonImmutable $sunset, CarbonImmutable $nextSunrise, float $sunriseSunLon, float $ayanamsa, float $lat, float $lon, SwissEphFFI $sweph): array
Parameters:
  • $sunrise, $sunset, $nextSunrise(CarbonImmutable) — Boundary timestamps.
  • $sunriseSunLon(float) — Sun longitude at sunrise.
  • $ayanamsa(float) — Calculation offset.
  • $lat, $lon(float) — Coordinates.
Returns:array — List of sign durations with start/end times.

calculatePrahara()

Calculate 8 Prahara (4 day + 4 night) as per Srimad Bhagavata Purana.

public function calculatePrahara(CarbonImmutable $sunrise, CarbonImmutable $sunset, CarbonImmutable $nextSunrise): array
Parameters:
  • $sunrise, $sunset, $nextSunrise(CarbonImmutable) — Boundary timestamps.
Returns:array — 8 canonical Prahara periods.

calculateDurMuhurta()

Identify specific inauspicious Muhurtas from the daily 30-period table.

public function calculateDurMuhurta(CarbonImmutable $sunrise, CarbonImmutable $sunset, CarbonImmutable $nextSunrise): array
Parameters:
  • $sunrise, $sunset, $nextSunrise(CarbonImmutable) — Boundary timestamps.
Returns:array — List of Dur-Muhurta periods.

calculateVarjyam()

Calculate one Varjyam (Tyajyam) window for a specific Nakshatra span.

public function calculateVarjyam(CarbonImmutable $sunrise, CarbonImmutable $sunset, CarbonImmutable $nextSunrise, int $nakIdx, float $nakStartJd, float $nakEndJd): array
Parameters:
  • $sunrise, $sunset, $nextSunrise(CarbonImmutable) — Boundary timestamps.
  • $nakIdx(int) — Nakshatra index.
  • $nakStartJd, $nakEndJd(float) — Nakshatra span boundaries.
Returns:array — Varjyam window payload for that Nakshatra. Day-level aggregation is done in PanchangService.

calculateAmritaKaal()

Calculate Amrita Kaal (auspicious period — opposite of Varjyam).

public function calculateAmritaKaal(CarbonImmutable $sunrise, array $varjyam): array
Parameters:
  • $sunrise(CarbonImmutable) — Sunrise time.
  • $varjyam(array) — Calculated Varjyam results.
Returns:array{amrita_kaal_start, amrita_kaal_end, duration_minutes}

calculatePradoshaKaal()

Legacy helper around sunset. Full Trayodashi-overlap Pradosha logic in day output is computed by PanchangService.

public function calculatePradoshaKaal(CarbonImmutable $sunset, int $tithiNum): array
Parameters:
  • $sunset(CarbonImmutable) — Sunset time.
  • $tithiNum(int) — Absolute Tithi index.
Returns:array — Pradosha timings.

calculateBadTimes()

Calculate Rahu Kala, Gulika, and Yamaganda for a given day.

public function calculateBadTimes(CarbonImmutable $sunrise, CarbonImmutable $sunset, int $varaIdx): array
Parameters:
  • $sunrise, $sunset(CarbonImmutable) — Sunrise/Sunset.
  • $varaIdx(int) — Weekday index.
Returns:array — Set of bad time intervals.

EclipseService

Service: JayeshMepani\PanchangCore\Astronomy\EclipseService

Predict solar and lunar eclipses with sub-second precision, including contact times, magnitudes, and visibility assessment.

Methods

getEclipsesForYear()

Find all eclipses occurring in a specific calendar year globally or for a location.

public function getEclipsesForYear(int $year, float $lat, float $lon, string $tz): array
Parameters:
  • $year(int) — Gregorian year.
  • $lat, $lon(float) — Coordinates.
  • $tz(string) — Timezone.
Returns:array — List of eclipse events with times, type, and visibility.

BhadraEngine

Service: JayeshMepani\PanchangCore\Festivals\Utils\BhadraEngine

Advanced Bhadra (Vishti Karana) analysis according to Muhūrta Chintāmaṇi and Nirṇaya Sindhu.

Methods

calculateBhadra()

Calculate Bhadra subdivisions (Mukha, Madhya, Puchha) and location (Bhadravāsa/Lok).

public function calculateBhadra(float $sunriseJd, float $vishtiStartJd, float $vishtiEndJd, int $moonRasi, int $tithi, string $paksha): array
Parameters:
  • $sunriseJd(float) — Julian Day of sunrise.
  • $vishtiStartJd(float) — Julian Day of Vishti Karana start.
  • $vishtiEndJd(float) — Julian Day of Vishti Karana end.
  • $moonRasi(int) — Moon's Rasi (sign) index.
  • $tithi(int) — Tithi index.
  • $paksha(string) — 'Shukla' or 'Krishna'.
Returns:array— {mukha, madhya, puchha, lok, status}

AstroCore

Utility: JayeshMepani\PanchangCore\Core\AstroCore

Core astronomical utility class for normalization, coordinate conversion, and high-precision formatting.

Static Methods

normalize()

Normalize any angle to [0, 360) range.

public static function normalize(float $angle): float
Parameters:
  • $angle(float) — Angle in decimal degrees.
Returns:float — Normalized angle.

formatAngle()

Format decimal degrees to DMS (Deg° Min' Sec") string.

formatTime()

Format time based on library configuration (12h/24h).

public static function formatTime(CarbonImmutable $dt): string
Parameters:
  • $dt(CarbonImmutable) — Date/Time object.
Returns:string — Formatted time string.

formatDuration()

Format minutes to Hh Mm string.

public static function formatDuration(float $minutes): string
Parameters:
  • $minutes(float) — Duration in minutes.
Returns:string — Formatted duration.

r9()

Round value to high precision (9 decimal places) for consistency.

public static function r9(float $value): float
Parameters:
  • $value(float) — Decimal value.
Returns:float — Rounded value.

Configuration

Complete reference for config/panchang.php.

Key Type Default Description
ephe_path string __DIR__ . '/../ephe' Path to Swiss Ephemeris .se1 files.
ayanamsa string 'LAHIRI' Default calculation system (LAHIRI, RAMAN, etc.).
defaults.measurement_system string 'indian_metric' Unit system for generic measurements.
defaults.date_time_format string 'indian_12h' Date-time output format.
defaults.time_notation string '12h' Time output notation.
festivals.default_tradition string 'Smarta' Default tradition used for festival resolution.
festivals.default_region string 'North' Default region used for festival resolution.

Constants & Enums

Available options for calculation parameters.

Ayanamsa Systems

  • LAHIRI— Chitra Paksha (Standard)
  • RAMAN— BV Raman
  • KRISHNAMURTI— KP System
  • SAYANA— Tropical (Zero offset)
  • JNRBHASIN— JN Bhasin

Traditions

  • Smarta— Standard Dharmasindhu rules
  • Vaishnava— ISKCON/Gaudiya rules

Regions

  • North— Purnimanta calendar (UP, Delhi, Rajasthan)
  • South— Amanta calendar (Karnataka, Andhra, TN)
  • Maharashtra, Gujarat— Regional variations
  • Bengal— Solar calendar variations

FestivalService

Service: JayeshMepani\PanchangCore\Festivals\FestivalService

Calculate Hindu festivals based on Tithi, Nakshatra, and complex regional traditions/priorities.

Methods

resolveFestivalsForDate()

Resolve all festivals for a date using today's and tomorrow's snapshot context.

public function resolveFestivalsForDate(CarbonImmutable $date, array $todayDetails, array $tomorrowDetails): array
Parameters:
  • $date(CarbonImmutable) — Target date.
  • $todayDetails(array) — Festival snapshot for date.
  • $tomorrowDetails(array) — Festival snapshot for next date.
Returns:array — List of festival objects with names, types, and metadata.
Example:
$today = $panchang->getFestivalSnapshot(
    CarbonImmutable::parse('2026-03-24'),
    23.247,
    69.668,
    'Asia/Kolkata'
);
$tomorrow = $panchang->getFestivalSnapshot(
    CarbonImmutable::parse('2026-03-25'),
    23.247,
    69.668,
    'Asia/Kolkata'
);

$festivals = $festivalService->resolveFestivalsForDate(
    CarbonImmutable::parse('2026-03-24'),
    $today,
    $tomorrow
);

foreach ($festivals as $festival) {
    echo $festival['name'] . "\n";
}

Laravel Integration

Complete guide for using Panchang Core in Laravel applications.

Installation

composer require jayeshmepani/panchang-core

Configuration

Publish the configuration file:

php artisan vendor:publish --provider="JayeshMepani\PanchangCore\PanchangServiceProvider" --tag="panchang-config"

This creates config/panchang.php:

return [
    'ephe_path' => env('PANCHANG_EPHE_PATH', ''),
    'ayanamsa' => env('PANCHANG_AYANAMSA', 'LAHIRI'),
    'defaults' => [
        'tradition' => 'Smarta',
        'region' => 'North',
    ],
];

Using the Facade

use JayeshMepani\PanchangCore\Facades\Panchang;
use Carbon\CarbonImmutable;

// Get complete panchanga
$details = Panchang::getDayDetails(
    date: CarbonImmutable::parse('2026-03-24'),
    lat: 23.2472,
    lon: 69.6683,
    tz: 'Asia/Kolkata'
);

echo $details['Tithi']['name'];    // "Dwadashi"
echo $details['Nakshatra']['name']; // "Magha"

Service Container

Or inject via constructor:

use JayeshMepani\PanchangCore\Panchanga\PanchangService;

class PanchangController extends Controller
{
    public function __construct(
        private PanchangService $panchang
    ) {}

    public function show()
    {
        $details = $this->panchang->getDayDetails(
            date: CarbonImmutable::now(),
            lat: 28.6139,
            lon: 77.2090,
            tz: 'Asia/Kolkata'
        );

        return view('panchang', compact('details'));
    }
}

Return Value Structures

Complete data structures returned by main methods.

getDayDetails() Return Structure

[
  'Tithi'=>[ 'index'=>12, 'name'=>'Dwadashi', 'paksha'=>'Shukla', 'fraction_left'=>0.7666, ],
  'Nakshatra'=>[ 'index'=>10, 'name'=>'Magha', 'pada'=>2, 'lord'=>'Sun', ],
  'Yoga'=>['index'=>9, 'name'=>'Shula'],
  'Karana'=>['index'=>23, 'name'=>'Bava'],
  'Vara'=>['index'=>2, 'name'=>'Tuesday', 'lord'=>'Mars'],
  'Muhurta_Full_Day'=>[ 
    ['name'=>'Rudra', 'start'=>'06:14', 'end'=>'07:02'], // ... 30 periods
  ],
  'Chogadiya_Full_Day'=>[
    ['name'=>'Amrit', 'mode'=>'Day', 'start'=>'06:14', 'end'=>'07:46'], // ... 16 divisions
  ],
  'Hora_Full_Day'=>[
    ['planet'=>'Sun', 'start'=>'06:14', 'end'=>'07:14'], // ... 24 horas
  ],
  'Prahara_Full_Day'=>[
    ['name'=>'Pratah Prahara', 'start'=>'06:14', 'end'=>'09:18'], // ... 8 objects
  ],
  'Lagna_Full_Day'=>[
    ['sign_name'=>'Mesha', 'start'=>'06:14', 'end'=>'08:22'], // ... 12/13 signs
  ],
  'Dur_Muhurta_Full_Day'=>[
    ['name'=>'Rudra', 'start'=>'06:14', 'end'=>'07:02'], // Inauspicious Muhurtas only
  ],
  'Festivals'=>[['name'=>'Pradosh Vrat', 'type'=>'vrat']],
  'Sunrise'=>'06:14:00',
  'Sunset'=>'18:32:00',
  'Moonrise'=>'15:45:00',
  'Moonset'=>'04:20:00',
]

getFestivalSnapshot() Return Structure

[
  'Festivals' => [
    ['name' => 'Holika Dahan', 'type' => 'festival', 'priority' => 1],
  ],
  'Tithi' => [...],
  'Nakshatra' => [...],
]

Real-World Examples

Complete working examples for common use cases.

1. Daily Panchang Display

// Show today's panchang
$today = Panchang::getDayDetails(
    date: CarbonImmutable::now(),
    lat: $userLat,
    lon: $userLon,
    tz: $userTz
);

echo "Tithi: " . $today['Tithi']['name'];
echo "Nakshatra: " . $today['Nakshatra']['name'];

2. Festival Calendar

// Get festivals for entire month
$monthFestivals = [];
for ($day = 1; $day <= 31; $day++) {
    $date = CarbonImmutable::create(2026, 10, $day);
    $fest = Panchang::getFestivalSnapshot($date, $lat, $lon, $tz);
    
    if (!empty($fest['Festivals'])) {
        $monthFestivals[$day] = $fest['Festivals'];
    }
}

3. Tradition-Specific Resolution

// Smarta-style date resolution (date-scoped festivals)
$smarta = Panchang::getDayDetails(
    CarbonImmutable::parse('2026-09-06'),
    28.61, 77.20, 'Asia/Kolkata'
)['Festivals'];

// Next-day festival context (for comparison)
$vaishnava = Panchang::getDayDetails(
    CarbonImmutable::parse('2026-09-07'),
    28.61, 77.20, 'Asia/Kolkata'
)['Festivals'];

4. Birth Chart Basics

// Get planetary positions for a birth date
$birthData = [
    'year' => 1990, 'month' => 5, 'day' => 15,
    'hour' => 14, 'minute' => 30, 'second' => 0,
    'tz' => 'Asia/Kolkata', 'lat' => 28.61, 'lon' => 77.20
];

$planets = $astronomy->getPlanets($birthData);
$ascendant = $astronomy->getAscendant($birthData);

echo "Sun: " . $planets['Sun'] . "°\n";
echo "Ascendant: " . $ascendant . "°";

5. Comprehensive Full-Day Data

// Get all advanced time divisions for a date
$details = Panchang::getDayDetails($date, $lat, $lon, $tz);

$lagnas   = $details['Lagna_Full_Day'];     // Exact Sign entry times
$horas    = $details['Hora_Full_Day'];       // 24 planetary rulers
$praharas = $details['Prahara_Full_Day'];    // 8 canonical periods
$muhurtas = $details['Muhurta_Full_Day'];    // 30 named Muhurtas
$durs     = $details['Dur_Muhurta_Full_Day']; // Inauspicious Muhurtas

Accuracy & Date Range

Technical specifications of the Swiss Ephemeris astronomical engine.

Precision Modes

Mode Date Range Precision
High Precision 13,201 BCE to 17,191 CE 0.001 arcsec
Standard 3,000 BCE to 3,000 CE 0.1 arcsec

*High Precision requires .se1 data files from Astro.com.

Ephemeris File Structure

Files are split into 600-year periods:

  • sepl_*.se1/semo_*.se1 — Common Era (AD) Dates
  • seplm*.se1/semom*.se1 — Before Common Era (BC)
  • se00*.se1 — Asteroids (Range: 5401 BCE to 5399 CE)

Calculation Precision

  • IEEE 754 — Double precision (53-bit significand)
  • Lossless — No intermediate rounding in formulas
  • High Convergence — 80 iterations for 1e-24 JD precision

Error Handling

Understanding and handling errors.

Common Exceptions

Common exceptions and how to handle them
Exception When It Occurs How to Handle
RuntimeException Swiss Ephemeris file not found Set correct ephe_path in config
InvalidArgumentException Invalid latitude/longitude Validate coordinates before calling
RuntimeException Timezone not found Use valid PHP timezone identifiers

Best Practices

try {
    $details = Panchang::getDayDetails(
        date: $date,
        lat: $lat, // Validate: -90 to 90
        lon: $lon, // Validate: -180 to 180
        tz: $tz    // Validate: timezone_exists($tz)
    );
} catch (RuntimeException $e) {
    Log::error('Panchang calculation failed', [
        'error' => $e->getMessage(),
        'location' => compact('lat', 'lon', 'tz')
    ]);

    return response()->json([
        'error' => 'Unable to calculate panchang for this location'
    ], 500);
}

FAQ & Troubleshooting

Common questions and solutions.

Why are my calculations different from other panchang apps?
Answer
  • Ayanamsa: We use Lahiri by default. Change via config if needed.
  • Location: Ensure exact latitude/longitude.
  • Tradition: Smarta vs Vaishnava have different rules.
  • Precision Mode: Ensure you have .se1 ephemeris files installed for 0.001" accuracy. Without them, the engine falls back to the Moshier model (0.1" precision).
How do I change the ayanamsa?
Answer

Set in config or pass to getDayDetails():

// In config/panchang.php
'ayanamsa' => 'RAMAN', // Options: LAHIRI, RAMAN, KRISHNAMURTI

// Or per-call
$details = Panchang::getDayDetails(
    date: $date, lat: $lat, lon: $lon, tz: $tz,
    ayanamsaAt: CarbonImmutable::now()
);
Why is Janmashtami on different dates?
Answer

This is normal. Smarta tradition celebrates on one day (ashtami at sunrise), Vaishnava on another (ashtami + Rohini nakshatra at midnight). Use the tradition parameter for the correct date.

How accurate are the calculations?
Answer

We use Swiss Ephemeris which provides accuracy to within 1 arcsecond for planetary positions. All calculations use IEEE 754 double precision with no intermediate rounding.

Can I use this for historical dates?
Answer

Yes! Swiss Ephemeris supports dates from 3000 BCE to 3000 CE. Just pass any valid CarbonImmutable date.

License

AGPL-3.0 License

This project is licensed under the GNU Affero General Public License v3.0 (AGPL-3.0).

The core engine utilize the Swiss Ephemeris for precision calculations, which follows a dual-licensing model:

  • Open Source: Licensed under GNU AGPLv3. If you use this package in a free/open-source project, your project must also be licensed under AGPLv3.
  • Commercial: If you wish to use this package in a closed-source or commercial application, you MUST purchase a commercial license from Astrodienst AG.

For more details, see the full license text.

Quick Reference

What to Use When

Method selection guide
I want to… Use this method
Get complete panchanga for a day PanchangService::getDayDetails()
Get only festivals PanchangService::getFestivalSnapshot()
Get planetary positions AstronomyService::getPlanets()
Get sunrise/sunset SunService::getSunriseSunset()
Calculate Tithi manually PanchangaEngine::calculateTithi()
Get Nakshatra from Moon position PanchangaEngine::getNakshatraInfo()
Get Muhurta times MuhurtaService::calculateMuhurtaTable()
Get auspicious times MuhurtaService::calculateAbhijitMuhurta()
Get Brahma Muhurta MuhurtaService::calculateBrahmaMuhurta()
Get Rahu Kala, Gulika MuhurtaService::calculateBadTimes()
Get resolved festivals for a date PanchangService::getDayDetails() / FestivalService::resolveFestivalsForDate()
Get season (Ritu) PanchangaEngine::getRitu()
Get Samvatsara PanchangaEngine::getSamvatsara()

Classical Text References

All calculations are based on authentic Sanskrit texts:

  • Sūrya Siddhānta 1.29→ Tithi
  • Sūrya Siddhānta 8.1→ Nakṣatra
  • Sūrya Siddhānta→ Yoga, Karana
  • BPHS→ Vimśottarī Daśā, Horā
  • Bṛhat Saṃhitā 8→ Samvatsara, Ritu
  • Muhūrta Chintāmaṇi→ Muhūrta
  • Kāla Nirṇaya→ Choghadiya
  • Ashtānga Hṛdaya→ Brahma Muhūrta