@sudobility/sudojo_lib 0.0.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/hooks/index.d.ts +27 -0
- package/dist/hooks/index.d.ts.map +1 -0
- package/dist/hooks/index.js +27 -0
- package/dist/hooks/index.js.map +1 -0
- package/dist/hooks/useDailyGame.d.ts +64 -0
- package/dist/hooks/useDailyGame.d.ts.map +1 -0
- package/dist/hooks/useDailyGame.js +120 -0
- package/dist/hooks/useDailyGame.js.map +1 -0
- package/dist/hooks/useGame.d.ts +104 -0
- package/dist/hooks/useGame.d.ts.map +1 -0
- package/dist/hooks/useGame.js +546 -0
- package/dist/hooks/useGame.js.map +1 -0
- package/dist/hooks/useGamePersistence.d.ts +63 -0
- package/dist/hooks/useGamePersistence.d.ts.map +1 -0
- package/dist/hooks/useGamePersistence.js +124 -0
- package/dist/hooks/useGamePersistence.js.map +1 -0
- package/dist/hooks/useGameTeaching.d.ts +89 -0
- package/dist/hooks/useGameTeaching.d.ts.map +1 -0
- package/dist/hooks/useGameTeaching.js +230 -0
- package/dist/hooks/useGameTeaching.js.map +1 -0
- package/dist/hooks/useGameTimer.d.ts +43 -0
- package/dist/hooks/useGameTimer.d.ts.map +1 -0
- package/dist/hooks/useGameTimer.js +68 -0
- package/dist/hooks/useGameTimer.js.map +1 -0
- package/dist/hooks/useHint.d.ts +105 -0
- package/dist/hooks/useHint.d.ts.map +1 -0
- package/dist/hooks/useHint.js +179 -0
- package/dist/hooks/useHint.js.map +1 -0
- package/dist/hooks/useLearning.d.ts +100 -0
- package/dist/hooks/useLearning.d.ts.map +1 -0
- package/dist/hooks/useLearning.js +127 -0
- package/dist/hooks/useLearning.js.map +1 -0
- package/dist/hooks/useLevelGame.d.ts +68 -0
- package/dist/hooks/useLevelGame.d.ts.map +1 -0
- package/dist/hooks/useLevelGame.js +128 -0
- package/dist/hooks/useLevelGame.js.map +1 -0
- package/dist/hooks/useLevels.d.ts +93 -0
- package/dist/hooks/useLevels.d.ts.map +1 -0
- package/dist/hooks/useLevels.js +98 -0
- package/dist/hooks/useLevels.js.map +1 -0
- package/dist/hooks/useLocalStorage.d.ts +26 -0
- package/dist/hooks/useLocalStorage.d.ts.map +1 -0
- package/dist/hooks/useLocalStorage.js +75 -0
- package/dist/hooks/useLocalStorage.js.map +1 -0
- package/dist/hooks/useSudoku.d.ts +125 -0
- package/dist/hooks/useSudoku.d.ts.map +1 -0
- package/dist/hooks/useSudoku.js +655 -0
- package/dist/hooks/useSudoku.js.map +1 -0
- package/dist/hooks/useTechniques.d.ts +92 -0
- package/dist/hooks/useTechniques.d.ts.map +1 -0
- package/dist/hooks/useTechniques.js +108 -0
- package/dist/hooks/useTechniques.js.map +1 -0
- package/dist/index.d.ts +42 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +64 -0
- package/dist/index.js.map +1 -0
- package/dist/test/setup.d.ts +2 -0
- package/dist/test/setup.d.ts.map +1 -0
- package/dist/test/setup.js +35 -0
- package/dist/test/setup.js.map +1 -0
- package/dist/types/display.d.ts +142 -0
- package/dist/types/display.d.ts.map +1 -0
- package/dist/types/display.js +94 -0
- package/dist/types/display.js.map +1 -0
- package/dist/types/game.d.ts +201 -0
- package/dist/types/game.d.ts.map +1 -0
- package/dist/types/game.js +26 -0
- package/dist/types/game.js.map +1 -0
- package/dist/types/gamePersistence.d.ts +31 -0
- package/dist/types/gamePersistence.d.ts.map +1 -0
- package/dist/types/gamePersistence.js +15 -0
- package/dist/types/gamePersistence.js.map +1 -0
- package/dist/types/index.d.ts +18 -0
- package/dist/types/index.d.ts.map +1 -0
- package/dist/types/index.js +11 -0
- package/dist/types/index.js.map +1 -0
- package/dist/types/progress.d.ts +43 -0
- package/dist/types/progress.d.ts.map +1 -0
- package/dist/types/progress.js +19 -0
- package/dist/types/progress.js.map +1 -0
- package/dist/types/settings.d.ts +19 -0
- package/dist/types/settings.d.ts.map +1 -0
- package/dist/types/settings.js +12 -0
- package/dist/types/settings.js.map +1 -0
- package/dist/types/subscription.d.ts +27 -0
- package/dist/types/subscription.d.ts.map +1 -0
- package/dist/types/subscription.js +8 -0
- package/dist/types/subscription.js.map +1 -0
- package/dist/types/sudoku.d.ts +147 -0
- package/dist/types/sudoku.d.ts.map +1 -0
- package/dist/types/sudoku.js +125 -0
- package/dist/types/sudoku.js.map +1 -0
- package/dist/utils/auth.d.ts +25 -0
- package/dist/utils/auth.d.ts.map +1 -0
- package/dist/utils/auth.js +47 -0
- package/dist/utils/auth.js.map +1 -0
- package/dist/utils/board.d.ts +116 -0
- package/dist/utils/board.d.ts.map +1 -0
- package/dist/utils/board.js +291 -0
- package/dist/utils/board.js.map +1 -0
- package/dist/utils/index.d.ts +18 -0
- package/dist/utils/index.d.ts.map +1 -0
- package/dist/utils/index.js +23 -0
- package/dist/utils/index.js.map +1 -0
- package/dist/utils/progress.d.ts +44 -0
- package/dist/utils/progress.d.ts.map +1 -0
- package/dist/utils/progress.js +104 -0
- package/dist/utils/progress.js.map +1 -0
- package/dist/utils/scramble.d.ts +35 -0
- package/dist/utils/scramble.d.ts.map +1 -0
- package/dist/utils/scramble.js +270 -0
- package/dist/utils/scramble.js.map +1 -0
- package/dist/utils/subscription.d.ts +82 -0
- package/dist/utils/subscription.d.ts.map +1 -0
- package/dist/utils/subscription.js +117 -0
- package/dist/utils/subscription.js.map +1 -0
- package/dist/utils/sudokuPresenter.d.ts +62 -0
- package/dist/utils/sudokuPresenter.d.ts.map +1 -0
- package/dist/utils/sudokuPresenter.js +403 -0
- package/dist/utils/sudokuPresenter.js.map +1 -0
- package/dist/utils/sudokuScrambler.d.ts +61 -0
- package/dist/utils/sudokuScrambler.d.ts.map +1 -0
- package/dist/utils/sudokuScrambler.js +223 -0
- package/dist/utils/sudokuScrambler.js.map +1 -0
- package/dist/utils/technique.d.ts +41 -0
- package/dist/utils/technique.d.ts.map +1 -0
- package/dist/utils/technique.js +106 -0
- package/dist/utils/technique.js.map +1 -0
- package/dist/utils/theme.d.ts +31 -0
- package/dist/utils/theme.d.ts.map +1 -0
- package/dist/utils/theme.js +40 -0
- package/dist/utils/theme.js.map +1 -0
- package/dist/utils/time.d.ts +22 -0
- package/dist/utils/time.d.ts.map +1 -0
- package/dist/utils/time.js +41 -0
- package/dist/utils/time.js.map +1 -0
- package/dist/utils/validation.d.ts +107 -0
- package/dist/utils/validation.d.ts.map +1 -0
- package/dist/utils/validation.js +248 -0
- package/dist/utils/validation.js.map +1 -0
- package/package.json +79 -0
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Hook exports for Sudojo library
|
|
3
|
+
*/
|
|
4
|
+
export { useLevel, useLevels } from './useLevels';
|
|
5
|
+
export type { UseLevelOptions, UseLevelResult, UseLevelsOptions, UseLevelsResult, } from './useLevels';
|
|
6
|
+
export { useTechnique, useTechniques } from './useTechniques';
|
|
7
|
+
export type { UseTechniqueOptions, UseTechniqueResult, UseTechniquesOptions, UseTechniquesResult, } from './useTechniques';
|
|
8
|
+
export { useLearning, useLearningItem } from './useLearning';
|
|
9
|
+
export type { UseLearningItemOptions, UseLearningItemResult, UseLearningOptions, UseLearningResult, } from './useLearning';
|
|
10
|
+
export { useGame } from './useGame';
|
|
11
|
+
export type { UseGameOptions, UseGameResult } from './useGame';
|
|
12
|
+
export { useGameTeaching } from './useGameTeaching';
|
|
13
|
+
export type { UseGameTeachingOptions, UseGameTeachingResult, } from './useGameTeaching';
|
|
14
|
+
export { useSudoku } from './useSudoku';
|
|
15
|
+
export type { UseSudokuOptions, UseSudokuResult } from './useSudoku';
|
|
16
|
+
export { useLevelGame } from './useLevelGame';
|
|
17
|
+
export type { UseLevelGameOptions, UseLevelGameResult, GameFetchStatus, } from './useLevelGame';
|
|
18
|
+
export { useDailyGame } from './useDailyGame';
|
|
19
|
+
export type { UseDailyGameOptions, UseDailyGameResult } from './useDailyGame';
|
|
20
|
+
export { useGameTimer } from './useGameTimer';
|
|
21
|
+
export type { UseGameTimerOptions, UseGameTimerResult } from './useGameTimer';
|
|
22
|
+
export { useGamePersistence, useAutoSave } from './useGamePersistence';
|
|
23
|
+
export type { UseGamePersistenceOptions, UseGamePersistenceResult, } from './useGamePersistence';
|
|
24
|
+
export { useLocalStorage } from './useLocalStorage';
|
|
25
|
+
export { useHint } from './useHint';
|
|
26
|
+
export type { UseHintOptions, UseHintResult, HintBoardData } from './useHint';
|
|
27
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/hooks/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AAGH,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AAClD,YAAY,EACV,eAAe,EACf,cAAc,EACd,gBAAgB,EAChB,eAAe,GAChB,MAAM,aAAa,CAAC;AAGrB,OAAO,EAAE,YAAY,EAAE,aAAa,EAAE,MAAM,iBAAiB,CAAC;AAC9D,YAAY,EACV,mBAAmB,EACnB,kBAAkB,EAClB,oBAAoB,EACpB,mBAAmB,GACpB,MAAM,iBAAiB,CAAC;AAGzB,OAAO,EAAE,WAAW,EAAE,eAAe,EAAE,MAAM,eAAe,CAAC;AAC7D,YAAY,EACV,sBAAsB,EACtB,qBAAqB,EACrB,kBAAkB,EAClB,iBAAiB,GAClB,MAAM,eAAe,CAAC;AAGvB,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AACpC,YAAY,EAAE,cAAc,EAAE,aAAa,EAAE,MAAM,WAAW,CAAC;AAG/D,OAAO,EAAE,eAAe,EAAE,MAAM,mBAAmB,CAAC;AACpD,YAAY,EACV,sBAAsB,EACtB,qBAAqB,GACtB,MAAM,mBAAmB,CAAC;AAG3B,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AACxC,YAAY,EAAE,gBAAgB,EAAE,eAAe,EAAE,MAAM,aAAa,CAAC;AAGrE,OAAO,EAAE,YAAY,EAAE,MAAM,gBAAgB,CAAC;AAC9C,YAAY,EACV,mBAAmB,EACnB,kBAAkB,EAClB,eAAe,GAChB,MAAM,gBAAgB,CAAC;AAExB,OAAO,EAAE,YAAY,EAAE,MAAM,gBAAgB,CAAC;AAC9C,YAAY,EAAE,mBAAmB,EAAE,kBAAkB,EAAE,MAAM,gBAAgB,CAAC;AAG9E,OAAO,EAAE,YAAY,EAAE,MAAM,gBAAgB,CAAC;AAC9C,YAAY,EAAE,mBAAmB,EAAE,kBAAkB,EAAE,MAAM,gBAAgB,CAAC;AAG9E,OAAO,EAAE,kBAAkB,EAAE,WAAW,EAAE,MAAM,sBAAsB,CAAC;AACvE,YAAY,EACV,yBAAyB,EACzB,wBAAwB,GACzB,MAAM,sBAAsB,CAAC;AAG9B,OAAO,EAAE,eAAe,EAAE,MAAM,mBAAmB,CAAC;AAGpD,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AACpC,YAAY,EAAE,cAAc,EAAE,aAAa,EAAE,aAAa,EAAE,MAAM,WAAW,CAAC"}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Hook exports for Sudojo library
|
|
3
|
+
*/
|
|
4
|
+
// Levels hooks
|
|
5
|
+
export { useLevel, useLevels } from './useLevels';
|
|
6
|
+
// Techniques hooks
|
|
7
|
+
export { useTechnique, useTechniques } from './useTechniques';
|
|
8
|
+
// Learning hooks
|
|
9
|
+
export { useLearning, useLearningItem } from './useLearning';
|
|
10
|
+
// Game hooks (legacy)
|
|
11
|
+
export { useGame } from './useGame';
|
|
12
|
+
// Teaching hooks
|
|
13
|
+
export { useGameTeaching } from './useGameTeaching';
|
|
14
|
+
// Sudoku hooks (ported from renderable)
|
|
15
|
+
export { useSudoku } from './useSudoku';
|
|
16
|
+
// Game fetching hooks (with auth/subscription handling)
|
|
17
|
+
export { useLevelGame } from './useLevelGame';
|
|
18
|
+
export { useDailyGame } from './useDailyGame';
|
|
19
|
+
// Game timer hook
|
|
20
|
+
export { useGameTimer } from './useGameTimer';
|
|
21
|
+
// Game persistence hooks
|
|
22
|
+
export { useGamePersistence, useAutoSave } from './useGamePersistence';
|
|
23
|
+
// Local storage hook
|
|
24
|
+
export { useLocalStorage } from './useLocalStorage';
|
|
25
|
+
// Hint hook
|
|
26
|
+
export { useHint } from './useHint';
|
|
27
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/hooks/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,eAAe;AACf,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AAQlD,mBAAmB;AACnB,OAAO,EAAE,YAAY,EAAE,aAAa,EAAE,MAAM,iBAAiB,CAAC;AAQ9D,iBAAiB;AACjB,OAAO,EAAE,WAAW,EAAE,eAAe,EAAE,MAAM,eAAe,CAAC;AAQ7D,sBAAsB;AACtB,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAGpC,iBAAiB;AACjB,OAAO,EAAE,eAAe,EAAE,MAAM,mBAAmB,CAAC;AAMpD,wCAAwC;AACxC,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AAGxC,wDAAwD;AACxD,OAAO,EAAE,YAAY,EAAE,MAAM,gBAAgB,CAAC;AAO9C,OAAO,EAAE,YAAY,EAAE,MAAM,gBAAgB,CAAC;AAG9C,kBAAkB;AAClB,OAAO,EAAE,YAAY,EAAE,MAAM,gBAAgB,CAAC;AAG9C,yBAAyB;AACzB,OAAO,EAAE,kBAAkB,EAAE,WAAW,EAAE,MAAM,sBAAsB,CAAC;AAMvE,qBAAqB;AACrB,OAAO,EAAE,eAAe,EAAE,MAAM,mBAAmB,CAAC;AAEpD,YAAY;AACZ,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC"}
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Hook for fetching and managing today's daily puzzle
|
|
3
|
+
* Handles auth and subscription status with automatic refresh
|
|
4
|
+
*/
|
|
5
|
+
import type { Daily } from '@sudobility/sudojo_types';
|
|
6
|
+
import type { NetworkClient } from '@sudobility/types';
|
|
7
|
+
import { type SudojoAuth, type SudojoConfig } from '@sudobility/sudojo_client';
|
|
8
|
+
import type { GameFetchStatus } from './useLevelGame';
|
|
9
|
+
export interface UseDailyGameOptions {
|
|
10
|
+
/** Network client for API calls */
|
|
11
|
+
networkClient: NetworkClient;
|
|
12
|
+
/** Sudojo API configuration */
|
|
13
|
+
config: SudojoConfig;
|
|
14
|
+
/** Auth credentials with access token */
|
|
15
|
+
auth: SudojoAuth;
|
|
16
|
+
/** Whether subscription is currently active */
|
|
17
|
+
subscriptionActive?: boolean;
|
|
18
|
+
/** Whether to enable the query */
|
|
19
|
+
enabled?: boolean;
|
|
20
|
+
}
|
|
21
|
+
export interface UseDailyGameResult {
|
|
22
|
+
/** Today's daily puzzle */
|
|
23
|
+
daily: Daily | null;
|
|
24
|
+
/** The date string for this daily (YYYY-MM-DD) */
|
|
25
|
+
dailyDate: string | null;
|
|
26
|
+
/** Current status of the game fetch */
|
|
27
|
+
status: GameFetchStatus;
|
|
28
|
+
/** Whether data is loading */
|
|
29
|
+
isLoading: boolean;
|
|
30
|
+
/** Error if fetch failed */
|
|
31
|
+
error: Error | null;
|
|
32
|
+
/** Refetch the daily puzzle */
|
|
33
|
+
refetch: () => void;
|
|
34
|
+
}
|
|
35
|
+
/**
|
|
36
|
+
* Hook for fetching today's daily puzzle
|
|
37
|
+
*
|
|
38
|
+
* Automatically refetches when auth token or subscription status changes.
|
|
39
|
+
* Returns status indicating whether auth or subscription is required.
|
|
40
|
+
*
|
|
41
|
+
* @param options - Hook options
|
|
42
|
+
* @returns Daily puzzle data and status
|
|
43
|
+
*
|
|
44
|
+
* @example
|
|
45
|
+
* ```tsx
|
|
46
|
+
* function DailyPage() {
|
|
47
|
+
* const { daily, dailyDate, status, refetch } = useDailyGame({
|
|
48
|
+
* networkClient,
|
|
49
|
+
* config,
|
|
50
|
+
* auth,
|
|
51
|
+
* subscriptionActive: subscription.isActive,
|
|
52
|
+
* });
|
|
53
|
+
*
|
|
54
|
+
* if (status === 'loading') return <Loading />;
|
|
55
|
+
* if (status === 'auth_required') return <AuthRequired onLogin={openAuthModal} />;
|
|
56
|
+
* if (status === 'subscription_required') return <SubscriptionPaywall onSuccess={refetch} />;
|
|
57
|
+
* if (status === 'error') return <Error />;
|
|
58
|
+
*
|
|
59
|
+
* return <SudokuGame puzzle={daily.board} solution={daily.solution} />;
|
|
60
|
+
* }
|
|
61
|
+
* ```
|
|
62
|
+
*/
|
|
63
|
+
export declare function useDailyGame(options: UseDailyGameOptions): UseDailyGameResult;
|
|
64
|
+
//# sourceMappingURL=useDailyGame.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"useDailyGame.d.ts","sourceRoot":"","sources":["../../src/hooks/useDailyGame.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAGH,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,0BAA0B,CAAC;AACtD,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,mBAAmB,CAAC;AACvD,OAAO,EACL,KAAK,UAAU,EACf,KAAK,YAAY,EAElB,MAAM,2BAA2B,CAAC;AACnC,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,gBAAgB,CAAC;AAuDtD,MAAM,WAAW,mBAAmB;IAClC,mCAAmC;IACnC,aAAa,EAAE,aAAa,CAAC;IAC7B,+BAA+B;IAC/B,MAAM,EAAE,YAAY,CAAC;IACrB,yCAAyC;IACzC,IAAI,EAAE,UAAU,CAAC;IACjB,+CAA+C;IAC/C,kBAAkB,CAAC,EAAE,OAAO,CAAC;IAC7B,kCAAkC;IAClC,OAAO,CAAC,EAAE,OAAO,CAAC;CACnB;AAED,MAAM,WAAW,kBAAkB;IACjC,2BAA2B;IAC3B,KAAK,EAAE,KAAK,GAAG,IAAI,CAAC;IACpB,kDAAkD;IAClD,SAAS,EAAE,MAAM,GAAG,IAAI,CAAC;IACzB,uCAAuC;IACvC,MAAM,EAAE,eAAe,CAAC;IACxB,8BAA8B;IAC9B,SAAS,EAAE,OAAO,CAAC;IACnB,4BAA4B;IAC5B,KAAK,EAAE,KAAK,GAAG,IAAI,CAAC;IACpB,+BAA+B;IAC/B,OAAO,EAAE,MAAM,IAAI,CAAC;CACrB;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;GA2BG;AACH,wBAAgB,YAAY,CAAC,OAAO,EAAE,mBAAmB,GAAG,kBAAkB,CAsE7E"}
|
|
@@ -0,0 +1,120 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Hook for fetching and managing today's daily puzzle
|
|
3
|
+
* Handles auth and subscription status with automatic refresh
|
|
4
|
+
*/
|
|
5
|
+
import { useEffect, useMemo, useRef } from 'react';
|
|
6
|
+
import { useSudojoTodayDaily, } from '@sudobility/sudojo_client';
|
|
7
|
+
/** Check if response indicates auth is required */
|
|
8
|
+
function isAuthRequired(response, error) {
|
|
9
|
+
if (response?.success === false &&
|
|
10
|
+
response.action?.type === 'auth_required') {
|
|
11
|
+
return true;
|
|
12
|
+
}
|
|
13
|
+
if (error && typeof error === 'object') {
|
|
14
|
+
const err = error;
|
|
15
|
+
if (err.message?.includes('Account required'))
|
|
16
|
+
return true;
|
|
17
|
+
}
|
|
18
|
+
return false;
|
|
19
|
+
}
|
|
20
|
+
/** Check if response indicates subscription is required */
|
|
21
|
+
function isSubscriptionRequired(response, error) {
|
|
22
|
+
if (response?.success === false &&
|
|
23
|
+
response.action?.type === 'subscription_required') {
|
|
24
|
+
return true;
|
|
25
|
+
}
|
|
26
|
+
if (error && typeof error === 'object') {
|
|
27
|
+
const err = error;
|
|
28
|
+
if (err.message?.includes('Daily limit reached') ||
|
|
29
|
+
err.message?.includes('subscription')) {
|
|
30
|
+
return true;
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
return false;
|
|
34
|
+
}
|
|
35
|
+
/**
|
|
36
|
+
* Hook for fetching today's daily puzzle
|
|
37
|
+
*
|
|
38
|
+
* Automatically refetches when auth token or subscription status changes.
|
|
39
|
+
* Returns status indicating whether auth or subscription is required.
|
|
40
|
+
*
|
|
41
|
+
* @param options - Hook options
|
|
42
|
+
* @returns Daily puzzle data and status
|
|
43
|
+
*
|
|
44
|
+
* @example
|
|
45
|
+
* ```tsx
|
|
46
|
+
* function DailyPage() {
|
|
47
|
+
* const { daily, dailyDate, status, refetch } = useDailyGame({
|
|
48
|
+
* networkClient,
|
|
49
|
+
* config,
|
|
50
|
+
* auth,
|
|
51
|
+
* subscriptionActive: subscription.isActive,
|
|
52
|
+
* });
|
|
53
|
+
*
|
|
54
|
+
* if (status === 'loading') return <Loading />;
|
|
55
|
+
* if (status === 'auth_required') return <AuthRequired onLogin={openAuthModal} />;
|
|
56
|
+
* if (status === 'subscription_required') return <SubscriptionPaywall onSuccess={refetch} />;
|
|
57
|
+
* if (status === 'error') return <Error />;
|
|
58
|
+
*
|
|
59
|
+
* return <SudokuGame puzzle={daily.board} solution={daily.solution} />;
|
|
60
|
+
* }
|
|
61
|
+
* ```
|
|
62
|
+
*/
|
|
63
|
+
export function useDailyGame(options) {
|
|
64
|
+
const { networkClient, config, auth, subscriptionActive = false, enabled: _enabled = true, } = options;
|
|
65
|
+
// Track previous state to detect changes
|
|
66
|
+
const prevStateRef = useRef({
|
|
67
|
+
authToken: auth.accessToken,
|
|
68
|
+
subscriptionActive,
|
|
69
|
+
});
|
|
70
|
+
// Note: useSudojoTodayDaily doesn't support enabled option directly
|
|
71
|
+
// We handle enabled by conditionally using the data
|
|
72
|
+
const { data, isLoading, error, refetch } = useSudojoTodayDaily(networkClient, config, auth);
|
|
73
|
+
// Determine status based on response
|
|
74
|
+
const status = useMemo(() => {
|
|
75
|
+
if (isLoading)
|
|
76
|
+
return 'loading';
|
|
77
|
+
if (isAuthRequired(data, error))
|
|
78
|
+
return 'auth_required';
|
|
79
|
+
if (isSubscriptionRequired(data, error))
|
|
80
|
+
return 'subscription_required';
|
|
81
|
+
if (error)
|
|
82
|
+
return 'error';
|
|
83
|
+
if (data?.success && data.data)
|
|
84
|
+
return 'success';
|
|
85
|
+
return 'loading';
|
|
86
|
+
}, [isLoading, data, error]);
|
|
87
|
+
const daily = useMemo(() => {
|
|
88
|
+
if (data?.success && data.data) {
|
|
89
|
+
return data.data;
|
|
90
|
+
}
|
|
91
|
+
return null;
|
|
92
|
+
}, [data]);
|
|
93
|
+
const dailyDate = useMemo(() => {
|
|
94
|
+
if (daily?.date) {
|
|
95
|
+
const dateStr = new Date(daily.date).toISOString().split('T')[0];
|
|
96
|
+
return dateStr ?? null;
|
|
97
|
+
}
|
|
98
|
+
return null;
|
|
99
|
+
}, [daily]);
|
|
100
|
+
// Auto-refresh when auth token or subscription status changes
|
|
101
|
+
useEffect(() => {
|
|
102
|
+
const prev = prevStateRef.current;
|
|
103
|
+
const authChanged = prev.authToken !== auth.accessToken;
|
|
104
|
+
const subscriptionChanged = !prev.subscriptionActive && subscriptionActive;
|
|
105
|
+
if (authChanged || subscriptionChanged) {
|
|
106
|
+
refetch();
|
|
107
|
+
}
|
|
108
|
+
// Update ref for next comparison
|
|
109
|
+
prevStateRef.current = { authToken: auth.accessToken, subscriptionActive };
|
|
110
|
+
}, [auth.accessToken, subscriptionActive, refetch]);
|
|
111
|
+
return {
|
|
112
|
+
daily,
|
|
113
|
+
dailyDate,
|
|
114
|
+
status,
|
|
115
|
+
isLoading,
|
|
116
|
+
error: error ?? (data?.error ? new Error(data.error) : null),
|
|
117
|
+
refetch: () => refetch(),
|
|
118
|
+
};
|
|
119
|
+
}
|
|
120
|
+
//# sourceMappingURL=useDailyGame.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"useDailyGame.js","sourceRoot":"","sources":["../../src/hooks/useDailyGame.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,104 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Main game state management hook for Sudoku gameplay
|
|
3
|
+
*/
|
|
4
|
+
import type { GameSettings, GameState, ScrambleConfig } from '../types';
|
|
5
|
+
export interface UseGameOptions {
|
|
6
|
+
/** Maximum mistakes allowed (0 = unlimited) */
|
|
7
|
+
maxMistakes?: number;
|
|
8
|
+
/** Initial settings */
|
|
9
|
+
initialSettings?: Partial<GameSettings>;
|
|
10
|
+
}
|
|
11
|
+
export interface UseGameResult {
|
|
12
|
+
/** Current game state */
|
|
13
|
+
state: GameState;
|
|
14
|
+
/** Whether the game is active (playing or paused) */
|
|
15
|
+
isActive: boolean;
|
|
16
|
+
/** Whether the game is complete */
|
|
17
|
+
isComplete: boolean;
|
|
18
|
+
/** Whether the game failed (too many mistakes) */
|
|
19
|
+
isFailed: boolean;
|
|
20
|
+
/** Can undo */
|
|
21
|
+
canUndo: boolean;
|
|
22
|
+
/** Can redo */
|
|
23
|
+
canRedo: boolean;
|
|
24
|
+
/** Load a new board */
|
|
25
|
+
loadBoard: (puzzle: string, solution: string, options?: {
|
|
26
|
+
scramble?: boolean;
|
|
27
|
+
scrambleConfig?: ScrambleConfig;
|
|
28
|
+
boardUuid?: string;
|
|
29
|
+
levelUuid?: string;
|
|
30
|
+
}) => void;
|
|
31
|
+
/** Select a cell */
|
|
32
|
+
selectCell: (row: number, column: number) => void;
|
|
33
|
+
/** Deselect the current cell */
|
|
34
|
+
deselectCell: () => void;
|
|
35
|
+
/** Set a value in the selected cell */
|
|
36
|
+
setValue: (value: number) => void;
|
|
37
|
+
/** Clear the value in the selected cell */
|
|
38
|
+
clearValue: () => void;
|
|
39
|
+
/** Toggle a pencilmark in the selected cell */
|
|
40
|
+
togglePencilmark: (value: number) => void;
|
|
41
|
+
/** Set pencilmarks in the selected cell */
|
|
42
|
+
setPencilmarks: (values: number[]) => void;
|
|
43
|
+
/** Clear pencilmarks in the selected cell */
|
|
44
|
+
clearPencilmarks: () => void;
|
|
45
|
+
/** Undo the last move */
|
|
46
|
+
undo: () => void;
|
|
47
|
+
/** Redo the last undone move */
|
|
48
|
+
redo: () => void;
|
|
49
|
+
/** Update game settings */
|
|
50
|
+
updateSettings: (settings: Partial<GameSettings>) => void;
|
|
51
|
+
/** Pause the game */
|
|
52
|
+
pause: () => void;
|
|
53
|
+
/** Resume the game */
|
|
54
|
+
resume: () => void;
|
|
55
|
+
/** Reset the game to initial state */
|
|
56
|
+
reset: () => void;
|
|
57
|
+
/** Update elapsed time */
|
|
58
|
+
tick: (seconds: number) => void;
|
|
59
|
+
/** Set hint mode */
|
|
60
|
+
setHintMode: (enabled: boolean) => void;
|
|
61
|
+
/** Get current board state as string (for solver API) */
|
|
62
|
+
getBoardString: () => string;
|
|
63
|
+
/** Get pencilmarks as string (for solver API) */
|
|
64
|
+
getPencilmarksString: () => string;
|
|
65
|
+
/** Get the original (unscrambled) puzzle string */
|
|
66
|
+
getOriginalPuzzle: () => string;
|
|
67
|
+
}
|
|
68
|
+
/**
|
|
69
|
+
* Main hook for managing Sudoku game state
|
|
70
|
+
*
|
|
71
|
+
* @param options - Hook options
|
|
72
|
+
* @returns Game state and actions
|
|
73
|
+
*
|
|
74
|
+
* @example
|
|
75
|
+
* ```tsx
|
|
76
|
+
* function GameScreen() {
|
|
77
|
+
* const {
|
|
78
|
+
* state,
|
|
79
|
+
* loadBoard,
|
|
80
|
+
* selectCell,
|
|
81
|
+
* setValue,
|
|
82
|
+
* isComplete,
|
|
83
|
+
* } = useGame({ maxMistakes: 3 });
|
|
84
|
+
*
|
|
85
|
+
* useEffect(() => {
|
|
86
|
+
* // Load a puzzle from the API
|
|
87
|
+
* loadBoard(puzzle, solution, { scramble: true });
|
|
88
|
+
* }, []);
|
|
89
|
+
*
|
|
90
|
+
* if (isComplete) {
|
|
91
|
+
* return <Congratulations />;
|
|
92
|
+
* }
|
|
93
|
+
*
|
|
94
|
+
* return (
|
|
95
|
+
* <Board
|
|
96
|
+
* cells={state.board}
|
|
97
|
+
* onCellPress={(row, col) => selectCell(row, col)}
|
|
98
|
+
* />
|
|
99
|
+
* );
|
|
100
|
+
* }
|
|
101
|
+
* ```
|
|
102
|
+
*/
|
|
103
|
+
export declare function useGame(options?: UseGameOptions): UseGameResult;
|
|
104
|
+
//# sourceMappingURL=useGame.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"useGame.d.ts","sourceRoot":"","sources":["../../src/hooks/useGame.ts"],"names":[],"mappings":"AAAA;;GAEG;AAGH,OAAO,KAAK,EAGV,YAAY,EACZ,SAAS,EACT,cAAc,EACf,MAAM,UAAU,CAAC;AAijBlB,MAAM,WAAW,cAAc;IAC7B,+CAA+C;IAC/C,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,uBAAuB;IACvB,eAAe,CAAC,EAAE,OAAO,CAAC,YAAY,CAAC,CAAC;CACzC;AAED,MAAM,WAAW,aAAa;IAC5B,yBAAyB;IACzB,KAAK,EAAE,SAAS,CAAC;IACjB,qDAAqD;IACrD,QAAQ,EAAE,OAAO,CAAC;IAClB,mCAAmC;IACnC,UAAU,EAAE,OAAO,CAAC;IACpB,kDAAkD;IAClD,QAAQ,EAAE,OAAO,CAAC;IAClB,eAAe;IACf,OAAO,EAAE,OAAO,CAAC;IACjB,eAAe;IACf,OAAO,EAAE,OAAO,CAAC;IAGjB,uBAAuB;IACvB,SAAS,EAAE,CACT,MAAM,EAAE,MAAM,EACd,QAAQ,EAAE,MAAM,EAChB,OAAO,CAAC,EAAE;QACR,QAAQ,CAAC,EAAE,OAAO,CAAC;QACnB,cAAc,CAAC,EAAE,cAAc,CAAC;QAChC,SAAS,CAAC,EAAE,MAAM,CAAC;QACnB,SAAS,CAAC,EAAE,MAAM,CAAC;KACpB,KACE,IAAI,CAAC;IACV,oBAAoB;IACpB,UAAU,EAAE,CAAC,GAAG,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,KAAK,IAAI,CAAC;IAClD,gCAAgC;IAChC,YAAY,EAAE,MAAM,IAAI,CAAC;IACzB,uCAAuC;IACvC,QAAQ,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IAClC,2CAA2C;IAC3C,UAAU,EAAE,MAAM,IAAI,CAAC;IACvB,+CAA+C;IAC/C,gBAAgB,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IAC1C,2CAA2C;IAC3C,cAAc,EAAE,CAAC,MAAM,EAAE,MAAM,EAAE,KAAK,IAAI,CAAC;IAC3C,6CAA6C;IAC7C,gBAAgB,EAAE,MAAM,IAAI,CAAC;IAC7B,yBAAyB;IACzB,IAAI,EAAE,MAAM,IAAI,CAAC;IACjB,gCAAgC;IAChC,IAAI,EAAE,MAAM,IAAI,CAAC;IACjB,2BAA2B;IAC3B,cAAc,EAAE,CAAC,QAAQ,EAAE,OAAO,CAAC,YAAY,CAAC,KAAK,IAAI,CAAC;IAC1D,qBAAqB;IACrB,KAAK,EAAE,MAAM,IAAI,CAAC;IAClB,sBAAsB;IACtB,MAAM,EAAE,MAAM,IAAI,CAAC;IACnB,sCAAsC;IACtC,KAAK,EAAE,MAAM,IAAI,CAAC;IAClB,0BAA0B;IAC1B,IAAI,EAAE,CAAC,OAAO,EAAE,MAAM,KAAK,IAAI,CAAC;IAChC,oBAAoB;IACpB,WAAW,EAAE,CAAC,OAAO,EAAE,OAAO,KAAK,IAAI,CAAC;IAGxC,yDAAyD;IACzD,cAAc,EAAE,MAAM,MAAM,CAAC;IAC7B,iDAAiD;IACjD,oBAAoB,EAAE,MAAM,MAAM,CAAC;IACnC,mDAAmD;IACnD,iBAAiB,EAAE,MAAM,MAAM,CAAC;CACjC;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAkCG;AACH,wBAAgB,OAAO,CAAC,OAAO,GAAE,cAAmB,GAAG,aAAa,CAwKnE"}
|