🎨 Flashcard support review mode https://github.com/siyuan-note/siyuan/issues/10303
This commit is contained in:
parent
0dc8f1752d
commit
882466e10d
9 changed files with 63 additions and 7 deletions
|
@ -1,4 +1,9 @@
|
|||
{
|
||||
"reviewMode": "Review mode",
|
||||
"reviewModeTip": "Select the order in which new and old cards appear during review",
|
||||
"reviewMode0": "New and old mix",
|
||||
"reviewMode1": "New first",
|
||||
"reviewMode2": "Old first",
|
||||
"fileAnnoRefPlaceholder": "Please enter block ID",
|
||||
"addToDatabase": "Add to Database",
|
||||
"clearContext": "Clear context",
|
||||
|
|
|
@ -1,4 +1,9 @@
|
|||
{
|
||||
"reviewMode": "Modo de revisión",
|
||||
"reviewModeTip": "Seleccione el orden en que aparecen las tarjetas nuevas y antiguas durante la revisión",
|
||||
"reviewMode0": "Nuevo y viejo mezclado",
|
||||
"reviewMode1": "Nuevo primero",
|
||||
"reviewMode2": "Viejo primero",
|
||||
"fileAnnoRefPlaceholder": "Ingrese el ID del bloque",
|
||||
"addToDatabase": "Agregar a la base de datos",
|
||||
"clearContext": "Borrar contexto",
|
||||
|
|
|
@ -1,4 +1,9 @@
|
|||
{
|
||||
"reviewMode": "Mode de révision",
|
||||
"reviewModeTip": "Sélectionnez l'ordre dans lequel les nouvelles et anciennes cartes apparaissent lors de la révision",
|
||||
"reviewMode0": "Nouveau et ancien mélange",
|
||||
"reviewMode1": "Nouveau d'abord",
|
||||
"reviewMode2": "Ancien d'abord",
|
||||
"fileAnnoRefPlaceholder": "Veuillez saisir l'ID de bloc",
|
||||
"addToDatabase": "Ajouter à la base de données",
|
||||
"clearContext": "Effacer le contexte",
|
||||
|
|
|
@ -1,4 +1,9 @@
|
|||
{
|
||||
"reviewMode": "複習模式",
|
||||
"reviewModeTip": "選擇複習時新卡和舊卡出現的順序",
|
||||
"reviewMode0": "新舊混合",
|
||||
"reviewMode1": "新卡優先",
|
||||
"reviewMode2": "舊卡優先",
|
||||
"fileAnnoRefPlaceholder": "請輸入區塊 ID",
|
||||
"addToDatabase": "新增至資料庫",
|
||||
"clearContext": "清空上下文",
|
||||
|
|
|
@ -1,4 +1,9 @@
|
|||
{
|
||||
"reviewMode": "复习模式",
|
||||
"reviewModeTip": "选择复习时新卡和旧卡出现的顺序",
|
||||
"reviewMode0": "新旧混合",
|
||||
"reviewMode1": "新卡优先",
|
||||
"reviewMode2": "旧卡优先",
|
||||
"fileAnnoRefPlaceholder": "请输入块 ID",
|
||||
"addToDatabase": "添加到数据库",
|
||||
"clearContext": "清空上下文",
|
||||
|
|
|
@ -42,7 +42,19 @@ export const flashcard = {
|
|||
</div>
|
||||
<span class="fn__space"></span>
|
||||
<input class="b3-switch fn__flex-center" id="deck" type="checkbox"${window.siyuan.config.flashcard.deck ? " checked" : ""}/>
|
||||
</label>`;
|
||||
</label>
|
||||
<div class="fn__flex b3-label config__item">
|
||||
<div class="fn__flex-1">
|
||||
${window.siyuan.languages.reviewMode}
|
||||
<div class="b3-label__text">${window.siyuan.languages.reviewModeTip}</div>
|
||||
</div>
|
||||
<span class="fn__space"></span>
|
||||
<select class="b3-select fn__flex-center fn__size200" id="reviewMode">
|
||||
<option value="0" ${window.siyuan.config.flashcard.reviewMode === 0 ? "selected" : ""}>${window.siyuan.languages.reviewMode0}</option>
|
||||
<option value="1" ${window.siyuan.config.flashcard.reviewMode === 1 ? "selected" : ""}>${window.siyuan.languages.reviewMode1}</option>
|
||||
<option value="2" ${window.siyuan.config.flashcard.reviewMode === 2 ? "selected" : ""}>${window.siyuan.languages.reviewMode2}</option>
|
||||
</select>
|
||||
</div>`;
|
||||
/// #if MOBILE
|
||||
responsiveHTML = `${responsiveHTML}<div class="b3-label">
|
||||
${window.siyuan.languages.flashcardNewCardLimit}
|
||||
|
@ -119,9 +131,10 @@ export const flashcard = {
|
|||
return responsiveHTML;
|
||||
},
|
||||
bindEvent: () => {
|
||||
flashcard.element.querySelectorAll("input").forEach((item) => {
|
||||
flashcard.element.querySelectorAll("input, select.b3-select").forEach((item) => {
|
||||
item.addEventListener("change", () => {
|
||||
fetchPost("/api/setting/setFlashcard", {
|
||||
reviewMode: parseInt((flashcard.element.querySelector("#reviewMode") as HTMLSelectElement).value),
|
||||
newCardLimit: parseInt((flashcard.element.querySelector("#newCardLimit") as HTMLInputElement).value),
|
||||
reviewCardLimit: parseInt((flashcard.element.querySelector("#reviewCardLimit") as HTMLInputElement).value),
|
||||
mark: (flashcard.element.querySelector("#mark") as HTMLInputElement).checked,
|
||||
|
|
1
app/src/types/index.d.ts
vendored
1
app/src/types/index.d.ts
vendored
|
@ -716,6 +716,7 @@ interface IConfig {
|
|||
superBlock: boolean
|
||||
heading: boolean
|
||||
deck: boolean
|
||||
reviewMode: number
|
||||
requestRetention: number
|
||||
maximumInterval: number
|
||||
weights: string
|
||||
|
|
|
@ -30,6 +30,7 @@ type Flashcard struct {
|
|||
SuperBlock bool `json:"superBlock"` // 是否启用超级块制卡 https://github.com/siyuan-note/siyuan/issues/7702
|
||||
Heading bool `json:"heading"` // 是否启用标题块制卡 https://github.com/siyuan-note/siyuan/issues/9005
|
||||
Deck bool `json:"deck"` // 是否启用卡包制卡 https://github.com/siyuan-note/siyuan/issues/7724
|
||||
ReviewMode int `json:"reviewMode"` // 复习模式,0:新旧混合,1:新卡优先,2:旧卡优先 https://github.com/siyuan-note/siyuan/issues/10303
|
||||
|
||||
// Apply result optimized by FSRS optimizer https://github.com/siyuan-note/siyuan/issues/9309
|
||||
RequestRetention float64 `json:"requestRetention"`
|
||||
|
@ -55,6 +56,7 @@ func NewFlashcard() *Flashcard {
|
|||
SuperBlock: true,
|
||||
Heading: true,
|
||||
Deck: false,
|
||||
ReviewMode: 0,
|
||||
RequestRetention: param.RequestRetention,
|
||||
MaximumInterval: int(param.MaximumInterval),
|
||||
Weights: weightsBuilder.String(),
|
||||
|
|
|
@ -490,7 +490,7 @@ func GetNotebookDueFlashcards(boxID string, reviewedCardIDs []string) (ret []*Fl
|
|||
return
|
||||
}
|
||||
|
||||
cards, unreviewedCnt, unreviewedNewCardCnt, unreviewedOldCardCnt := getDeckDueCards(deck, reviewedCardIDs, treeBlockIDs, Conf.Flashcard.NewCardLimit, Conf.Flashcard.ReviewCardLimit)
|
||||
cards, unreviewedCnt, unreviewedNewCardCnt, unreviewedOldCardCnt := getDeckDueCards(deck, reviewedCardIDs, treeBlockIDs, Conf.Flashcard.NewCardLimit, Conf.Flashcard.ReviewCardLimit, Conf.Flashcard.ReviewMode)
|
||||
now := time.Now()
|
||||
for _, card := range cards {
|
||||
ret = append(ret, newFlashcard(card, card.BlockID(), builtinDeckID, now))
|
||||
|
@ -535,7 +535,7 @@ func GetTreeDueFlashcards(rootID string, reviewedCardIDs []string) (ret []*Flash
|
|||
}
|
||||
}
|
||||
|
||||
cards, unreviewedCnt, unreviewedNewCardCnt, unreviewedOldCardCnt := getDeckDueCards(deck, reviewedCardIDs, treeBlockIDs, newCardLimit, reviewCardLimit)
|
||||
cards, unreviewedCnt, unreviewedNewCardCnt, unreviewedOldCardCnt := getDeckDueCards(deck, reviewedCardIDs, treeBlockIDs, newCardLimit, reviewCardLimit, Conf.Flashcard.ReviewMode)
|
||||
now := time.Now()
|
||||
for _, card := range cards {
|
||||
ret = append(ret, newFlashcard(card, card.BlockID(), builtinDeckID, now))
|
||||
|
@ -606,7 +606,7 @@ func getDueFlashcards(deckID string, reviewedCardIDs []string) (ret []*Flashcard
|
|||
return
|
||||
}
|
||||
|
||||
cards, unreviewedCnt, unreviewedNewCardCnt, unreviewedOldCardCnt := getDeckDueCards(deck, reviewedCardIDs, nil, Conf.Flashcard.NewCardLimit, Conf.Flashcard.ReviewCardLimit)
|
||||
cards, unreviewedCnt, unreviewedNewCardCnt, unreviewedOldCardCnt := getDeckDueCards(deck, reviewedCardIDs, nil, Conf.Flashcard.NewCardLimit, Conf.Flashcard.ReviewCardLimit, Conf.Flashcard.ReviewMode)
|
||||
now := time.Now()
|
||||
for _, card := range cards {
|
||||
ret = append(ret, newFlashcard(card, card.BlockID(), deckID, now))
|
||||
|
@ -623,7 +623,7 @@ func getDueFlashcards(deckID string, reviewedCardIDs []string) (ret []*Flashcard
|
|||
func getAllDueFlashcards(reviewedCardIDs []string) (ret []*Flashcard, unreviewedCount, unreviewedNewCardCount, unreviewedOldCardCount int) {
|
||||
now := time.Now()
|
||||
for _, deck := range Decks {
|
||||
cards, unreviewedCnt, unreviewedNewCardCnt, unreviewedOldCardCnt := getDeckDueCards(deck, reviewedCardIDs, nil, Conf.Flashcard.NewCardLimit, Conf.Flashcard.ReviewCardLimit)
|
||||
cards, unreviewedCnt, unreviewedNewCardCnt, unreviewedOldCardCnt := getDeckDueCards(deck, reviewedCardIDs, nil, Conf.Flashcard.NewCardLimit, Conf.Flashcard.ReviewCardLimit, Conf.Flashcard.ReviewMode)
|
||||
unreviewedCount += unreviewedCnt
|
||||
unreviewedNewCardCount += unreviewedNewCardCnt
|
||||
unreviewedOldCardCount += unreviewedOldCardCnt
|
||||
|
@ -988,8 +988,10 @@ func getDeckIDs() (deckIDs []string) {
|
|||
return
|
||||
}
|
||||
|
||||
func getDeckDueCards(deck *riff.Deck, reviewedCardIDs, blockIDs []string, newCardLimit, reviewCardLimit int) (ret []riff.Card, unreviewedCount, unreviewedNewCardCountInRound, unreviewedOldCardCountInRound int) {
|
||||
func getDeckDueCards(deck *riff.Deck, reviewedCardIDs, blockIDs []string, newCardLimit, reviewCardLimit, reviewMode int) (ret []riff.Card, unreviewedCount, unreviewedNewCardCountInRound, unreviewedOldCardCountInRound int) {
|
||||
ret = []riff.Card{}
|
||||
var retNew, retOld []riff.Card
|
||||
|
||||
dues := deck.Dues()
|
||||
|
||||
var tmp []riff.Card
|
||||
|
@ -1060,15 +1062,28 @@ func getDeckDueCards(deck *riff.Deck, reviewedCardIDs, blockIDs []string, newCar
|
|||
}
|
||||
|
||||
newCount++
|
||||
retNew = append(retNew, c)
|
||||
} else {
|
||||
if reviewCount >= reviewCardLimit {
|
||||
continue
|
||||
}
|
||||
|
||||
reviewCount++
|
||||
retOld = append(retOld, c)
|
||||
}
|
||||
|
||||
ret = append(ret, c)
|
||||
}
|
||||
|
||||
switch reviewMode {
|
||||
case 1: // 优先复习新卡
|
||||
ret = nil
|
||||
ret = append(ret, retNew...)
|
||||
ret = append(ret, retOld...)
|
||||
case 2: // 优先复习旧卡
|
||||
ret = nil
|
||||
ret = append(ret, retOld...)
|
||||
ret = append(ret, retNew...)
|
||||
}
|
||||
return
|
||||
}
|
||||
|
|
Loading…
Add table
Reference in a new issue