From 9f4618c5ef618521ce1ab680d82ed9cc941d10d8 Mon Sep 17 00:00:00 2001
From: Maksymilian Jopek <maks@jopek.eu>
Date: Mon, 12 Dec 2022 23:00:12 +0100
Subject: Added saving and loading Fix same value for each column Add showing
 errors

---
 src/App.svelte | 98 ++++++++++++++++++++++++++++++++++++++++++++++------------
 1 file changed, 79 insertions(+), 19 deletions(-)

(limited to 'src/App.svelte')

diff --git a/src/App.svelte b/src/App.svelte
index 9aab903..3a1a685 100644
--- a/src/App.svelte
+++ b/src/App.svelte
@@ -1,45 +1,99 @@
 <script lang="ts">
-  import { validate } from "./lib/Sudoku";
+  import { readGridFromFile, save } from "./lib/Saving";
+
+  import { validate, type Coord } from "./lib/Sudoku";
 
   let selTile: HTMLDivElement | EventTarget;
+  let fileInput: HTMLInputElement;
   const getSelTile = () => selTile as HTMLDivElement;
-  const grid = (new Array(10)).fill((new Array(10)).fill(".")) as string[][];
+  const getCoord = (): Coord => ({
+    x: parseInt(getSelTile().dataset.i),
+    y: parseInt(getSelTile().dataset.j),
+  });
+  let grid = [] as string[][]; //new Array(9).fill(new Array(9).fill("."));
+  let immutableTiles = [] as Coord[]; //new Array(9).fill(new Array(9).fill("."));
+  const tiles = [] as HTMLDivElement[][]; //new Array(9).fill(new Array(9).fill("."));
+  for (let i = 0; i < 9; i++) {
+    grid.push([]);
+    tiles.push([]);
+    for (let j = 0; j < 9; j++) {
+      grid[i].push(".");
+      tiles[i].push(null);
+    }
+  }
 
   function keyDownHandler(e: KeyboardEvent) {
-    if(e.key === "Backspace") {
-      setSelTile(".")
+    const foundImmu = immutableTiles.find(
+      (el) => el.x === getCoord().x && el.y === getCoord().y
+    );
+    console.log(immutableTiles);
+    console.log(foundImmu);
+    if (foundImmu) return;
+
+    if (e.key === "Backspace") {
+      setSelTile(".");
     }
     const num = parseInt(e.key);
-    if(Number.isNaN(num) || num === 0) return;
-    setSelTile(num)
-    validate(grid)
-  }
-  function showTile(val: string) {
-    return val === "." ? "" : val;
+    if (Number.isNaN(num) || selTile == null || num === 0) return;
+    setSelTile(num);
+    for (const tile of tiles.flat()) {
+      tile.classList.remove("err");
+      tile.classList.remove("good");
+    }
+    const bads = validate(grid);
+    for (const bad of bads) {
+      tiles[bad.x][bad.y].classList.add("err");
+    }
   }
+  // function showTile(val: string) {
+  //   return val === "." ? "" : val;
+  // }
   function setSelTile(val: string | number) {
-    grid[parseInt(getSelTile().dataset.i)][parseInt(getSelTile().dataset.j)] = val.toString();
-    getSelTile().innerText = val === "." ? "" : val.toString();
+    grid[getCoord().x][getCoord().y] = val.toString();
+    // getSelTile().innerText = val === "." ? "" : val.toString();
+  }
+
+  async function load() {
+    const maybeGrid = await readGridFromFile(fileInput.files[0]);
+    if (!maybeGrid) {
+      alert("Error while loading file");
+      return;
+    }
+    for (const [i, row] of maybeGrid.entries()) {
+      for (const [j, tile] of row.entries()) {
+        if (tile === ".") continue;
+        immutableTiles.push({ x: i, y: j });
+        tiles[i][j].classList.add("const");
+      }
+    }
+    grid = maybeGrid;
+    fileInput.value = null;
   }
 </script>
 
-<!-- <svelte:body on:keydown|preventDefaultstopPropagation={keyDownHandler} /> -->
+<!-- <svelte:body on:keydown|preventDefault|stopPropagation={keyDownHandler} /> -->
 <svelte:body on:keydown={keyDownHandler} />
 <main>
   <div class="grid">
-    {#each {length: 9} as _, i}
-      {#each {length: 9} as _, j}
-        <div 
-          class="tile" 
+    {#each grid as row, i}
+      {#each row as tile, j}
+        <div
+          class="tile"
           class:br={j % 3 === 2 && j !== 8}
           class:bb={i % 3 === 2 && i !== 8}
-          on:click|self={e => selTile = e.target}
+          on:click|self={(e) => (selTile = e.target)}
           data-i={i}
           data-j={j}
-          on:keypress={null}>{grid[i][j] === "." ? "" : grid[i][j]}</div>
+          bind:this={tiles[i][j]}
+          on:keypress={null}
+        >
+          {tile === "." ? "" : tile}
+        </div>
       {/each}
     {/each}
   </div>
+  <button on:click={() => save(grid)}>Save</button>
+  <input type="file" on:change={load} bind:this={fileInput} />
 </main>
 
 <style>
@@ -70,4 +124,10 @@
   .br {
     border-right: 3px solid black;
   }
+  :global(.err) {
+    background-color: rgba(150, 0, 0, 0.6) !important;
+  }
+  :global(.const) {
+    color: rebeccapurple;
+  }
 </style>
-- 
cgit v1.3.1

