aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/components/MainPanel.svelte21
-rw-r--r--src/components/RightPanel.svelte19
-rw-r--r--src/control/deck.js27
-rw-r--r--src/control/search.js7
-rw-r--r--src/utils.js46
5 files changed, 111 insertions, 9 deletions
diff --git a/src/components/MainPanel.svelte b/src/components/MainPanel.svelte
index b5f5f2e..5cef824 100644
--- a/src/components/MainPanel.svelte
+++ b/src/components/MainPanel.svelte
@@ -1,7 +1,12 @@
<script lang="js">
import CardThumb from './CardThumb.svelte';
import { deck, setDeck } from '../control/deck';
- import { parseYdk, genYdk, downloadStringAsFile} from '../utils'
+ import {
+ parseYdk,
+ genYdk,
+ genYdke,
+ downloadStringAsFile,
+ } from '../utils';
let fileInput;
@@ -26,6 +31,19 @@
downloadStringAsFile('mydeck.ydk', deckString)
}
+ function shareDeck() {
+ let url = window.location.href;
+ url = url.split('#')[0]
+ url = url + '#' + genYdke($deck);
+ navigator.clipboard.writeText(url)
+ .then(() => {
+ alert('分享链接已复制到剪贴板')
+ })
+ .catch(err => {
+ alert("失败!");
+ });
+ }
+
</script>
<input bind:this={fileInput} style="display:none;" onchange={loadDeck} type="file" class="file-input" accept=".ydk" />
@@ -34,6 +52,7 @@
<div class="control-bar">
<button class="btn" onclick={openDeck}>打开</button>
<button class="btn" onclick={saveDeck}>保存</button>
+ <button class="btn" onclick={shareDeck}>分享</button>
</div>
<div class="deck-section">
<div class="deck-group">
diff --git a/src/components/RightPanel.svelte b/src/components/RightPanel.svelte
index 5ede942..062e33c 100644
--- a/src/components/RightPanel.svelte
+++ b/src/components/RightPanel.svelte
@@ -1,9 +1,14 @@
-<script lang="ts">
+<script lang="js">
+ import CardThumb from './CardThumb.svelte';
+ import { resultCards } from '../control/search'
-import CardThumb from './CardThumb.svelte';
+ function onPrevPage() {
-let cardList = $state([]);
+ }
+ function onNextPage() {
+
+ }
</script>
<div class="right-panel">
@@ -11,9 +16,9 @@ let cardList = $state([]);
<input type="text" placeholder="搜索卡牌...">
</div>
<div class="card-list">
- {#if cardList.length > 0}
+ {#if $resultCards.length > 0}
<div class="card-item">
- {#each cardList as card}
+ {#each $resultCards as card}
<div class="card-thumbnail">
<CardThumb id= {card.id} />
</div>
@@ -23,8 +28,8 @@ let cardList = $state([]);
{/if}
</div>
<div class="pagination">
- <button class="page-btn">上一页</button>
- <button class="page-btn">下一页</button>
+ <button class="page-btn" onclick={onPrevPage}>上一页</button>
+ <button class="page-btn" onclick={onNextPage}>下一页</button>
</div>
</div>
diff --git a/src/control/deck.js b/src/control/deck.js
index 328e106..98c48fb 100644
--- a/src/control/deck.js
+++ b/src/control/deck.js
@@ -1,11 +1,36 @@
import { writable } from "svelte/store";
+import { parseYdke } from '../utils';
let deck = writable({main: [], extra: [], side: []});
-let setDeck = (d) => {
+function setDeck(d) {
+ d.main.sort();
+ d.extra.sort();
+ d.side.sort();
deck.set(d);
+ localStorage.setItem('cachedDeck', JSON.stringify(d));
};
+function initDeck() {
+ let url = window.location.href.split('#');
+ if (url.length === 2) {
+ let deck = parseYdke(url[1]);
+ if (deck.main.length > 0 || deck.extra.length > 0 || deck.extra.length > 0) {
+ setDeck(deck);
+ window.location.replace("/");
+ return;
+ }
+ }
+ let cachedDeck = localStorage.getItem('cachedDeck');
+ if (cachedDeck !== null) {
+ cachedDeck = JSON.parse(cachedDeck);
+ setDeck(cachedDeck)
+ return;
+ }
+}
+
+initDeck();
+
export {
deck,
setDeck,
diff --git a/src/control/search.js b/src/control/search.js
new file mode 100644
index 0000000..93a9fc9
--- /dev/null
+++ b/src/control/search.js
@@ -0,0 +1,7 @@
+import { writable } from 'svelte/store';
+
+let resultCards = writable([]);
+
+export {
+ resultCards,
+};
diff --git a/src/utils.js b/src/utils.js
index 3176400..ba5d905 100644
--- a/src/utils.js
+++ b/src/utils.js
@@ -55,10 +55,56 @@ function downloadStringAsFile(filename, text) {
URL.revokeObjectURL(link.href);
}
+function ydkeEncode(d) {
+ let deck = [];
+ for (let card of d) {
+ let num = parseInt(card);
+ if (isNaN(num)) continue;
+ deck.push(num);
+ }
+ const buffer = new ArrayBuffer(deck.length * 4);
+ const view = new DataView(buffer);
+ for (let i = 0; i < deck.length; i++) {
+ // Little-endian
+ view.setUint32(i * 4, deck[i], true);
+ }
+ return btoa(String.fromCharCode(...new Uint8Array(buffer)));
+}
+
+function ydkeDecode(encodedDeck) {
+ const binaryString = atob(encodedDeck);
+ const buffer = new ArrayBuffer(binaryString.length);
+ const view = new DataView(buffer);
+ for (let i = 0; i < binaryString.length; i++) {
+ view.setUint8(i, binaryString.charCodeAt(i));
+ }
+ const deck = [];
+ for (let i = 0; i < buffer.byteLength; i += 4) {
+ deck.push(String(view.getUint32(i, true))); // Little-endian
+ }
+ return deck;
+}
+
+function parseYdke(ydkeString) {
+ const [mainEncoded, extraEncoded, sideEncoded] = ydkeString.split('!');
+ const main = ydkeDecode(mainEncoded);
+ const extra = ydkeDecode(extraEncoded);
+ const side = ydkeDecode(sideEncoded);
+ return { main, extra, side };
+}
+
+function genYdke(deck) {
+ const mainEncoded = ydkeEncode(deck.main);
+ const extraEncoded = ydkeEncode(deck.extra);
+ const sideEncoded = ydkeEncode(deck.side);
+ return `${mainEncoded}!${extraEncoded}!${sideEncoded}`;
+}
export {
parseYdk,
genYdk,
+ parseYdke,
+ genYdke,
downloadStringAsFile,
};