Skip to content

Commit

Permalink
Resolving the issues with types
Browse files Browse the repository at this point in the history
  • Loading branch information
Thomas-Gallant committed Oct 27, 2024
1 parent 2cc5209 commit 7d6c95d
Show file tree
Hide file tree
Showing 31 changed files with 502 additions and 821 deletions.
25 changes: 0 additions & 25 deletions app/Api/Drills.ts

This file was deleted.

468 changes: 202 additions & 266 deletions app/Api/Lessons.ts

Large diffs are not rendered by default.

125 changes: 61 additions & 64 deletions app/Api/Profile.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { profile } from "./Puzzle.Types";
import { Profile } from "./Puzzle.Types";
import { getKeyJSON, storeData } from "../Functions/AsyncStorage";
import { SUDOKU_STRATEGY_ARRAY } from "sudokuru";

Expand All @@ -10,74 +10,71 @@ type profileValue =
| "highlightRow"
| "previewMode"
| "strategyHintOrder";
export class Profile {
public static async getProfile(): Promise<profile> {
const value = await getKeyJSON("profile");

// deep clone to avoid manipulation of const value.
const sudokuStrategyArray = JSON.parse(
JSON.stringify(SUDOKU_STRATEGY_ARRAY)
);
export const getProfile = async (): Promise<Profile> => {
const value = await getKeyJSON("profile");

const defaultProfileValues: profile = {
theme: true,
highlightBox: true,
highlightColumn: true,
highlightRow: true,
highlightIdenticalValues: true,
previewMode: false,
strategyHintOrder: sudokuStrategyArray,
};
// deep clone to avoid manipulation of const value.
const sudokuStrategyArray = JSON.parse(JSON.stringify(SUDOKU_STRATEGY_ARRAY));

if (value == null) {
await this.setProfile(defaultProfileValues);
return defaultProfileValues;
}

// handle initialization if some data is present but not other data
// Not having this code caused a crash on mobile (web was ok for some reason)
// when a user had some but not all profile settings defined in their app storage
// TODO we will want to conver this scenario with end to end tests in the future
Object.entries(defaultProfileValues).forEach(([key, defaultValue]) => {
if (value[key] === undefined) {
value[key] = defaultValue;
}
});
return value;
}
const defaultProfileValues: Profile = {
theme: true,
highlightBox: true,
highlightColumn: true,
highlightRow: true,
highlightIdenticalValues: true,
previewMode: false,
strategyHintOrder: sudokuStrategyArray,
};

public static async setProfile(profile: profile) {
storeData("profile", JSON.stringify(profile));
if (value == null) {
await setProfile(defaultProfileValues);
return defaultProfileValues;
}

public static async setProfileValue(
profileValue: profileValue,
newValue?: any
) {
let value: profile = await this.getProfile();
switch (profileValue) {
case "theme":
value.theme = !value.theme;
break;
case "highlightBox":
value.highlightBox = !value.highlightBox;
break;
case "highlightColumn":
value.highlightColumn = !value.highlightColumn;
break;
case "highlightIdenticalValues":
value.highlightIdenticalValues = !value.highlightIdenticalValues;
break;
case "highlightRow":
value.highlightRow = !value.highlightRow;
break;
case "previewMode":
value.previewMode = !value.previewMode;
break;
case "strategyHintOrder":
value.strategyHintOrder = newValue;
break;
// handle initialization if some data is present but not other data
// Not having this code caused a crash on mobile (web was ok for some reason)
// when a user had some but not all profile settings defined in their app storage
// TODO we will want to convert this scenario with end to end tests in the future
Object.entries(defaultProfileValues).forEach(([key, defaultValue]) => {
if (value[key] === undefined) {
value[key] = defaultValue;
}
this.setProfile(value);
});
return value;
};

export const setProfile = (profile: Profile) => {
storeData("profile", JSON.stringify(profile));
};

export const setProfileValue = async (
profileValue: profileValue,
newValue?: any
) => {
let value: Profile = await getProfile();
switch (profileValue) {
case "theme":
value.theme = !value.theme;
break;
case "highlightBox":
value.highlightBox = !value.highlightBox;
break;
case "highlightColumn":
value.highlightColumn = !value.highlightColumn;
break;
case "highlightIdenticalValues":
value.highlightIdenticalValues = !value.highlightIdenticalValues;
break;
case "highlightRow":
value.highlightRow = !value.highlightRow;
break;
case "previewMode":
value.previewMode = !value.previewMode;
break;
case "strategyHintOrder":
value.strategyHintOrder = newValue;
break;
}
}
setProfile(value);
};
115 changes: 52 additions & 63 deletions app/Api/Puzzles.ts
Original file line number Diff line number Diff line change
@@ -1,78 +1,67 @@
import { difficulty } from "./../Components/Home/Cards";
import { statistics } from "./Puzzle.Types";
import { SudokuObjectProps } from "../Functions/LocalDatabase";
import { getKeyJSON, removeData, storeData } from "../Functions/AsyncStorage";
import { Statistics } from "./Statistics";
import {
GameDifficulty,
returnGameOfDifficulty,
} from "../Components/SudokuBoard/Functions/Difficulty";
import { Statistics } from "./Puzzle.Types";
import { getStatistics, saveStatisitics } from "./Statistics";

/**
* Functions to handle puzzle related operations
* Given a difficulty and an user auth token retrieves a random puzzle close to the difficulty that the user hasn't solved before
* @param difficulty - difficulty number (between 0 and 1)
* @param strategies - new game can have subset of these strategies
* @returns promise of puzzle JSON object
*/
export class Puzzles {
/**
* Given a difficulty and an user auth token retrieves a random puzzle close to the difficulty that the user hasn't solved before
* @param difficulty - difficulty number (between 0 and 1)
* @param strategies - new game can have subset of these strategies
* @returns promise of puzzle JSON object
*/
public static async startGame(
difficulty: GameDifficulty
): Promise<SudokuObjectProps> {
return returnGameOfDifficulty(difficulty);
// !uncomment below for dev testing
// return returnGameOfDifficulty("dev");
}

/**
* Given an user auth token retrieves the users active game or returns null if the user doesn't have an active game
* @returns promise of activeGame JSON object
*/
public static async getGame(): Promise<SudokuObjectProps[]> {
return await getKeyJSON("active_game");
}
export const startGame = (difficulty: GameDifficulty): SudokuObjectProps => {
return returnGameOfDifficulty(difficulty);
// !uncomment below for dev testing
// return returnGameOfDifficulty("dev");
};

/**
* Given a game saves it to AsyncStorage
* @param game - activeGame JSON object
*/
public static async saveGame(game: SudokuObjectProps) {
storeData("active_game", JSON.stringify([game]));
}
/**
* Given an user auth token retrieves the users active game or returns null if the user doesn't have an active game
* @returns promise of activeGame JSON object
*/
export const getGame = (): Promise<SudokuObjectProps[]> => {
return getKeyJSON("active_game");
};

/**
* Given deletes the users active game and returns game score
* @returns promise of game score
*/
public static async finishGame(
numHintsUsed: number,
numWrongCellsPlayed: number,
time: number,
score: number
) {
// remove the game from storage
await removeData("active_game");
/**
* Given a game saves it to AsyncStorage
* @param game - activeGame JSON object
*/
export const saveGame = (game: SudokuObjectProps) => {
storeData("active_game", JSON.stringify([game]));
};

// Create or update user's statistics
let statistics: statistics = await Statistics.getStatistics();
/**
* Given deletes the users active game and returns game score
* @returns promise of game score
*/
export const finishGame = async (
numHintsUsed: number,
numWrongCellsPlayed: number,
time: number,
score: number
) => {
// remove the game from storage
await removeData("active_game");

statistics.totalScore += score;
if (
time < statistics.fastestSolveTime ||
statistics.fastestSolveTime === 0
) {
statistics.fastestSolveTime = time;
}
statistics.totalSolveTime += time;
statistics.numGamesPlayed += 1;
statistics.numHintsUsed += numHintsUsed;
statistics.numWrongCellsPlayed += numWrongCellsPlayed;
statistics.averageSolveTime = Math.round(
statistics.totalSolveTime / statistics.numGamesPlayed
);
// Create or update user's statistics
let statistics: Statistics = await getStatistics();

Statistics.saveStatisitics(statistics);
statistics.totalScore += score;
if (time < statistics.fastestSolveTime || statistics.fastestSolveTime === 0) {
statistics.fastestSolveTime = time;
}
}
statistics.totalSolveTime += time;
statistics.numGamesPlayed += 1;
statistics.numHintsUsed += numHintsUsed;
statistics.numWrongCellsPlayed += numWrongCellsPlayed;
statistics.averageSolveTime = Math.round(
statistics.totalSolveTime / statistics.numGamesPlayed
);

saveStatisitics(statistics);
};
Loading

0 comments on commit 7d6c95d

Please sign in to comment.