-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
+ Decks + Questions + Options + Shuffle + Full keyboard navigation
- Loading branch information
Showing
16 changed files
with
1,012 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,29 @@ | ||
# Betakat | ||
|
||
Study cards application, setup Decks fill it with Questions then challenge your self to Answer. | ||
|
||
![Betakat Image](https://i.imgur.com/K6IHHOW.png) | ||
|
||
> Version : 1.0 | ||
> [Guide](https://github.com/MustafaHi/Betakat/wiki/Guide) | ||
> [Dev Guide](https://github.com/MustafaHi/Betakat/wiki/Dev-Guide) | ||
> [Binary Release](https://github.com/MustafaHi/Betakat/releases) | ||
> [Change Log & Features](https://github.com/MustafaHi/Betakat/wiki/Change-log-&-Features) | ||
> More information in the [wiki](https://github.com/MustafaHi/Betakat/wiki) | ||
**Features** | ||
|
||
- Decks (sets of questions) | ||
- Shuffle | ||
- Full keyboard navigation | ||
- Cross-platfrom (Windows, Macos, Linux) | ||
- Lightweight `sizeof(app) < 10MB` | ||
|
||
`>` [RoadMap](https://github.com/MustafaHi/Betakat/wiki/RoadMap) | ||
|
||
|
||
[Download](https://github.com/MustafaHi/Betakat/releases) | ||
|
||
|
||
## Credit | ||
Built with [Sciter](https://github.com/c-smile/sciter-sdk), inspired by [GirkovArpa/slidercards](https://github.com/GirkovArpa/slidercards), using [Inter font](https://github.com/rsms/inter). |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,35 @@ | ||
<html lang="en" window-frame="standard"> | ||
<head> | ||
<meta charset="UTF-8"> | ||
<title>Betakat</title> | ||
<link rel="stylesheet" href="style/icons.css"> | ||
<link rel="stylesheet" href="style/main.css"> | ||
<link rel="stylesheet" href="style/decks.css"> | ||
<link rel="stylesheet" href="style/questions.css"> | ||
<script type="text/tiscript" src="script/main.tis"></script> | ||
|
||
<menu.context #deckMenu> | ||
<li click=ENTER>Play</li> | ||
<li click=Q>Questions</li> | ||
<li click=E>Edit</li> | ||
<li click=R>Delete</li> | ||
</menu> | ||
<menu.context #questionMenu> | ||
<li click=E>Edit</li> | ||
<li click=R>Delete</li> | ||
</menu> | ||
</head> | ||
<body> | ||
|
||
<nav> | ||
<b #title>Betakat</b> | ||
<!-- <button #bShuffle tabindex="-1"><b>S</b>huffle</button> --> | ||
<button #bShowOptions tabindex="-1"><b>O</b>ptions</button> | ||
</nav> | ||
|
||
<content> | ||
|
||
</content> | ||
|
||
</body> | ||
</html> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,119 @@ | ||
const dbPath = System.home("betaka.json"); | ||
|
||
function initFiles(forced = false) { | ||
if (!System.scanFiles(dbPath) || forced) { | ||
var file = Stream.openFile(dbPath, "wu"); | ||
var data = { | ||
decks: [{ | ||
id: "MainDeck", | ||
name: "Main Deck", | ||
questions: [{ | ||
i: "Q12345", | ||
q: "What is the name of this app?", | ||
a: "Betakat", | ||
t: [] | ||
}] | ||
}], | ||
options: { | ||
letters: false, | ||
random : false | ||
} | ||
}; | ||
// i : id, q : question, a : answer, d : deck, t : time, n : name | ||
file.print(JSON.stringify(data," ")); | ||
file.close(); | ||
} | ||
} | ||
initFiles(); | ||
|
||
|
||
namespace DB { | ||
var data; | ||
|
||
function load() { | ||
var file = Stream.openFile(dbPath, "ur"); | ||
data = parseData((file)); | ||
file.close(); | ||
if(!data) { initFiles(true); load(); } | ||
} | ||
function save() { | ||
var file = Stream.openFile(dbPath, "wu"); | ||
file.print(JSON.stringify(data, " ")); | ||
file.close(); | ||
} | ||
|
||
namespace decks { | ||
|
||
function list() { | ||
return data.decks; | ||
} | ||
|
||
function add(name) { | ||
const deck = { | ||
id: String.UID(), | ||
name: name, | ||
questions: [] | ||
}; | ||
data.decks.push(deck); | ||
|
||
save(); | ||
} | ||
|
||
function edit(D) { | ||
var (i, deck) = data.decks.find(:d: d.id == D.id); | ||
data.decks[i].name = D.name; | ||
|
||
save(); | ||
} | ||
|
||
function remove(id) { | ||
var (i, deck) = data.decks.find(:d: d.id == id); | ||
delete data.decks[i]; | ||
|
||
save(); | ||
} | ||
|
||
} | ||
|
||
namespace questions { | ||
|
||
function list() { | ||
var list = data.decks.find(:d: d.id == currentDeck).questions; | ||
QuestionsList = data.options.random ? list.shuffle() : list; | ||
return list; | ||
} | ||
|
||
function add(Q, A) { | ||
const question = { | ||
i: String.UID(), | ||
q: Q, | ||
a: A, | ||
t: [] | ||
}; | ||
|
||
var (i, deck) = data.decks.find(:d: d.id == currentDeck); | ||
data.decks[i].questions.push(question); | ||
|
||
save(); | ||
} | ||
|
||
function edit(Q) { | ||
var (ind1, deck) = data.decks.find(:d: d.id == currentDeck); | ||
var (ind2, question) = data.decks[ind1].questions.find(:q: q.i == Q.i); | ||
data.decks[ind1].questions[ind2] = Q; | ||
|
||
save(); | ||
} | ||
|
||
function remove(id) { | ||
var (ind1, deck) = data.decks.find(:d: d.id == currentDeck); | ||
var (ind2, question) = data.decks[ind1].questions.find(:q: q.i == id); | ||
delete data.decks[ind1].questions[ind2]; | ||
|
||
save(); | ||
} | ||
|
||
} | ||
} | ||
|
||
DB.load(); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,55 @@ | ||
// Betakat v1.0 | ||
// https://github.com/MustafaHi/Betakat | ||
|
||
include "data.tis"; | ||
include "navigation.tis"; | ||
|
||
function Element.focus() { this.state.focus = true; } | ||
function Element.current() { | ||
if (var el = $(:current)) el.state.current = false; | ||
this.state.current = true; | ||
this.focus(); | ||
} | ||
|
||
function Array.shuffle() { | ||
var ri; const rnd = rand; | ||
var shuffled = new Array(this.length); | ||
for(var (i,v) in this) { | ||
ri = rnd(i); | ||
shuffled[i] = shuffled[ri]; | ||
shuffled[ri] = v; | ||
} | ||
return shuffled; | ||
} | ||
|
||
|
||
const Content = self[1][1]; // $(content); | ||
var currentDeck; | ||
var qIndex = 0; | ||
|
||
var QuestionsList = []; | ||
|
||
|
||
function self.ready() { | ||
Nav.decks.list(); | ||
|
||
// center window on screen | ||
initWindow(); | ||
} | ||
|
||
|
||
function initWindow() { | ||
const w = 440, | ||
h = 650, | ||
(sw, sh) = view.screenBox(#frame, #dimension); | ||
view.move((sw / 2) - (w / 2), (sh / 2) - (h / 2), w, h, true); | ||
view.windowResizable = false; | ||
view.windowMaximizable = false; | ||
} | ||
function setDeck(deck) { | ||
currentDeck = deck.id; | ||
$(#title).text = "Betakat | " + deck[1].text; | ||
} | ||
|
||
event click $(a[href]) { Sciter.launch(this.@#href); return true; } | ||
event click $(#bShowOptions) { Nav.options(); } |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,85 @@ | ||
include "views/addDeck.tis"; | ||
include "views/decks.tis"; | ||
|
||
include "views/addQuestion.tis"; | ||
include "views/questions.tis"; | ||
include "views/ask.tis"; | ||
|
||
|
||
namespace Nav { | ||
|
||
namespace decks { | ||
// functions: | ||
// - list // decks.tis | ||
// - add|edit // addDeck.tis | ||
} | ||
|
||
namespace questions { | ||
// functions: | ||
// - list // questions.tis | ||
// - add|edit // addQuestion.tis | ||
// - ask // ask.tis | ||
} | ||
|
||
function options() { | ||
Content.$content( | ||
<div #form style="behavior: form;"> | ||
<button|checkbox(letters)>Normalize letters</button> | ||
<button|checkbox(random)>Randomize questions</button> | ||
</div> | ||
<p style="margin-top: *; line-height: 1.5em"> | ||
<a href="https://github.com/MustafaHi/Betakat" style="color: white;">Betakat v1.0 | ||
<br/> | ||
https://github.com/MustafaHi/Betakat | ||
</a> | ||
</p> | ||
<footer> | ||
<kbd>CTRL</kbd> | ||
<kbd>+</kbd> | ||
<kbd click=D><b>D</b>ecks</kbd> | ||
</footer> | ||
); | ||
Content[0].value = DB.data.options; | ||
Content[0][0].focus(); | ||
|
||
// Events: | ||
eventsOff(); | ||
self << event ~keydown(e) { | ||
if (e.shortcutKey) { | ||
globalKeyBind(e); | ||
} | ||
switch (e.keyCode) { | ||
case Event.VK_UP: | ||
Content.$(:focus)?.prior.focus(); | ||
break; | ||
case Event.VK_DOWN: | ||
Content.$(:focus)?.next.focus(); | ||
break; | ||
} | ||
} | ||
self.on("change", "#form", function() { DB.data.options = this.value; DB.save(); }); | ||
self.on("click", "[click]", function() { | ||
self.sendKeyEvent({type: Event.KEY_DOWN, keyCode: eval("Event.VK_"+this.@#click), shortcutKey: true}); | ||
}); | ||
} | ||
|
||
} | ||
|
||
|
||
function globalKeyBind(e) { | ||
switch (e.keyCode) { | ||
case Event.VK_D: | ||
Nav.decks.list(); | ||
break; | ||
case Event.VK_O: | ||
Nav.options(); | ||
break; | ||
} | ||
} | ||
|
||
function eventsOff() { | ||
self.off("~keydown"); | ||
self.off("dblclick"); | ||
self.off("change"); | ||
self.off("click"); | ||
} |
Oops, something went wrong.