Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions database/schema.sql
Original file line number Diff line number Diff line change
Expand Up @@ -390,6 +390,9 @@ INSERT OR IGNORE INTO settings (key, value) VALUES
-- transient and deliberately not persisted — see docs/tafsir-popover-plan.md.
('show_tafsir', 'false'),
('tafsir_panel_width', '420'),
-- The floating card's size from its resize grip; 0 = automatic.
('tafsir_card_width', '0'),
('tafsir_card_height', '0'),
('tafsir_view', 'popover'), -- 'popover' | 'panel'
('show_transliteration', 'false'),
('show_ayah_numbers', 'true'),
Expand Down
8 changes: 8 additions & 0 deletions src-tauri/src/db/queries.rs
Original file line number Diff line number Diff line change
Expand Up @@ -960,6 +960,14 @@ pub fn load_settings(conn: &Connection) -> DbResult<Settings> {
.get("tafsir_panel_width")
.and_then(|v| v.parse().ok())
.unwrap_or(420),
tafsir_card_width: map
.get("tafsir_card_width")
.and_then(|v| v.parse().ok())
.unwrap_or(0),
tafsir_card_height: map
.get("tafsir_card_height")
.and_then(|v| v.parse().ok())
.unwrap_or(0),
// Absent in databases predating the popover, which is why the default
// lives here as well as in schema.sql — no migration is needed for a
// settings key.
Expand Down
5 changes: 5 additions & 0 deletions src-tauri/src/models/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -187,6 +187,9 @@ pub struct Settings {
/// persisted at all — see docs/tafsir-popover-plan.md.
pub show_tafsir: bool,
pub tafsir_panel_width: u32,
/// The floating card's size from its resize grip. 0 = automatic.
pub tafsir_card_width: u32,
pub tafsir_card_height: u32,
/// "popover" | "panel" — which surface a tafsir trigger opens.
pub tafsir_view: String,
/// Whether clicking a verse opens its commentary. Off by default: with the
Expand Down Expand Up @@ -240,6 +243,8 @@ impl Default for Settings {
tafsir_id: None,
show_tafsir: false,
tafsir_panel_width: 420,
tafsir_card_width: 0,
tafsir_card_height: 0,
tafsir_view: "popover".to_string(),
tafsir_click: false,
show_transliteration: false,
Expand Down
20 changes: 13 additions & 7 deletions src/lib/components/tafsir/TafsirBody.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -24,15 +24,20 @@
return surahsStore.get(entry.surah_id)?.transliteration ?? null;
});

/** "2:255", or "2:1–5" where the edition comments on a run of verses. */
const verseLabel = $derived.by(() => {
/** "2:255" — always the verse on show, which the card's audio also plays. */
const verseLabel = $derived(entry ? `${entry.surah_id}:${entry.ayah_number}` : null);

/**
* "on 2:1–5" where the edition comments on a run of verses at once. Stepping
* verse by verse through a run keeps the same text, and this is what says
* the step still happened.
*/
const groupLabel = $derived.by(() => {
if (!entry) return null;
const { group_start_key: start, group_end_key: end } = entry;
if (start && end && start !== end) {
const endAyah = end.split(':')[1] ?? end;
return `${start}–${endAyah}`;
}
return `${entry.surah_id}:${entry.ayah_number}`;
if (!start || !end || start === end) return null;
const endAyah = end.split(':')[1] ?? end;
return `on ${start}–${endAyah}`;
});

// Paragraphs rather than one block: the importer keeps blank-line breaks and
Expand All @@ -55,6 +60,7 @@
<p class="verse-ref">
{#if surahName}<span class="surah">{surahName}</span>{/if}
<span class="key">{verseLabel}</span>
{#if groupLabel}<span class="group">{groupLabel}</span>{/if}
</p>
<div class="text" dir={edition.direction} class:rtl={edition.direction === 'rtl'}>
{#each paragraphs as para, i (i)}
Expand Down
27 changes: 25 additions & 2 deletions src/lib/components/tafsir/TafsirPanel.svelte
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
<script lang="ts">
import { X, PanelBottom, Library } from 'lucide-svelte';
import { X, PanelBottom, Library, ChevronLeft, ChevronRight } from 'lucide-svelte';
import { tafsirStore, clampTafsirWidth } from '$lib/stores/tafsir.svelte';
import { uiStore } from '$lib/stores/ui.svelte';
import TafsirMeta from './TafsirMeta.svelte';
Expand Down Expand Up @@ -71,6 +71,24 @@
<header class="panel-header">
<TafsirMeta />
<div class="actions">
<button
class="icon-btn"
onclick={() => tafsirStore.step(-1)}
disabled={!tafsirStore.canStepBack}
aria-label="Previous verse"
title="Previous verse"
>
<ChevronLeft size={16} />
</button>
<button
class="icon-btn"
onclick={() => tafsirStore.step(1)}
disabled={!tafsirStore.canStepForward}
aria-label="Next verse"
title="Next verse"
>
<ChevronRight size={16} />
</button>
<!-- The shelf lives in Settings now. It used to open in place here,
which meant that in card view — the default — there was no route to
it at all. -->
Expand Down Expand Up @@ -185,11 +203,16 @@
cursor: pointer;
}

.icon-btn:hover {
.icon-btn:hover:not(:disabled) {
background: var(--color-bg-hover);
color: var(--color-text);
}

.icon-btn:disabled {
opacity: 0.35;
cursor: default;
}

.panel-body {
flex: 1;
min-height: 0;
Expand Down
Loading
Loading