import { maxAyahsInSurah, meta } from "./const";
type LessThan<TNumber extends number, TArray extends unknown[] = []> = TNumber extends TArray["length"] ? TArray[number] : LessThan<TNumber, [...TArray, TArray["length"]]>;
/**
 * Creates a type representing a range of numbers from TStart to TEnd (inclusive).
 *
 * @typeParam TStart - The starting number of the range
 * @typeParam TEnd - The ending number of the range
 *
 *
 * @remarks
 * This type uses the Exclude utility type along with a LessThan helper type
 * to generate a union of all numbers within the specified range.
 */
export type NumericRange<TStart extends number, TEnd extends number> = Exclude<TEnd | LessThan<TEnd>, LessThan<TStart>>;
/**
 * Represents a valid Surah number in the Quran.
 * A type that ensures the number is within the valid range of Surahs (1 to the total number of Surahs).
 */
export type Surah = NumericRange<1, typeof meta.numSurahs>;
/**
 * Represents the number of an ayah (verse) within a surah.
 * Valid values are between 1 and the maximum number of ayahs in any surah.
 *
 */
export type AyahNo = NumericRange<1, typeof maxAyahsInSurah>;
/**
 * Represents a valid Rub al-Hizb (quarter of a Hizb) identifier.
 * The value must be a number between 0 and the total number of Rub al-Hizbs in the Quran.
 */
export type RubAlHizbId = NumericRange<0, typeof meta.numRubAlHizbs>;
/**
 * Represents a valid Hizb number in the Quran.
 * A Hizb is one of 60 equal divisions of the Quran.
 * A number between 0 and the total number of Hizbs in the Quran
 */
export type HizbId = NumericRange<0, typeof meta.numHizbs>;
/**
 * Represents a numeric identifier for an Ayah (verse) in the Quran.
 * The value should be between 0 and the total number of Ayahs.
 */
export type AyahId = number;
/**
 * Represents a valid page number within the Quran.
 * The value must be within the range of 0 to the total number of pages (inclusive).
 *
 */
export type Page = NumericRange<0, typeof meta.numPages>;
/**
 * Represents a Manzil number in the Quran.
 * A Manzil is one of seven roughly equal parts of the Quran used for sequential reading over seven days.
 * A number between 0 and the total number of Manzils (7)
 */
export type Manzil = NumericRange<0, typeof meta.numManzils>;
/**
 * A type representing a valid Ruku (section) number in the Quran.
 * The value must be a number between 0 and the total number of Rukus defined in meta.
 */
export type Ruku = NumericRange<0, typeof meta.numRukus>;
/**
 * Represents a Juz (part) number in the Quran.
 * A numeric value ranging from 0 to the total number of Juzs in the Quran.
 * The Quran is traditionally divided into 30 Juzs for ease of recitation and memorization.
 *
 */
export type Juz = NumericRange<0, typeof meta.numJuzs>;
/**
 * Represents a part (rub') number within a Juz.
 * A numeric value ranging from 1 to the total number of rub's (quarters) in a Juz.
 * A number constrained between 1 and the total number of rub's in a Juz
 */
export type JuzPart = NumericRange<1, typeof meta.numRubsInJuz>;
export type SurahInfo = [
    startAyahId: AyahId,
    ayahCount: AyahNo,
    surahOrder: Surah,
    rukuCount: Ruku,
    name: string,
    isMeccan: boolean
];
export type SurahName = [name: string, translitName: string];
export type RangeMeta = {
    firstAyahId: AyahId;
    lastAyahId: AyahId;
    first: SurahAyah;
    last: SurahAyah;
};
/**
 * Represents the structure of a Juz and Hizb combination in the Quran
 */
export type RubAlHizb = {
    juz: Juz;
    juzPart: JuzPart;
    hizbId: HizbId;
    rubAlHizbId: RubAlHizbId;
};
export type RubAlHizbMeta = RubAlHizb & RangeMeta;
export type SurahAyah = [Surah, AyahNo];
export type AyahRange = [AyahId, AyahId];
export type SurahAyahSegment = [Surah, AyahNo | [AyahNo, AyahNo]];
export type SurahMeta = {
    name: string;
    surahNum: Surah;
    ayahCount: AyahNo;
    surahOrder: Surah;
    rukuCount: Ruku;
    isMeccan: boolean;
} & RangeMeta;
export type PageMeta = {
    pageNum: Page;
} & RangeMeta;
export type ManzilMeta = {
    manzilNum: Manzil;
} & RangeMeta;
export type JuzMeta = {
    juzNum: Juz;
} & RangeMeta;
export type RukuMeta = {
    rukuNum: Ruku;
} & RangeMeta;
export type AyahCountBetweenJuzSurah = NumericRange<0, typeof maxAyahsInSurah>;
export type SurahJuzMeta = {
    leftjuz: Juz;
    ayahsBetweenJuzSurah: AyahCountBetweenJuzSurah;
    rightJuz: Juz;
    leftAyahId: AyahId;
    rightAyahId: AyahId;
};
export type SajdaType = "recommended" | "obligatory";
export type Sajda = [AyahId, SajdaType];
export type RangeMode = "juz" | "surah" | "ayah" | "page" | "ruku" | "all";
export type AyahMeta = {
    juz: Juz;
    juzPart: JuzPart;
    hizbId: HizbId;
    rubAlHizbId: RubAlHizbId;
    page: Page;
    ruku: number;
    surah: Surah;
    ayah: AyahNo;
    isStartOfQuarter: boolean;
    isEndOfQuarter: boolean;
    isSajdahAyah: boolean;
    isStartOfPage: boolean;
    isEndOfPage: boolean;
    isStartOfJuz: boolean;
    isEndOfJuz: boolean;
    isStartOfSurah: boolean;
    isEndOfSurah: boolean;
    isStartOfRuku: boolean;
    isEndOfRuku: boolean;
};
export {};
