blob: d9392c9de17cb9a96b4044f1bffe72990f3b930a (
plain) (
blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
|
;;; belf.el -- Bookshelf, ebook library management -*- lexical-binding: t -*-
;; Copyright (C) 2025 Free Software Foundation, Inc.
;; Author: Yuchen Pei <id@ypei.org>
;; Package-Requires: ((emacs "29.4"))
;; This file is part of dotted.
;; dotted is free software: you can redistribute it and/or modify it under
;; the terms of the GNU Affero General Public License as published by
;; the Free Software Foundation, either version 3 of the License, or
;; (at your option) any later version.
;; dotted is distributed in the hope that it will be useful, but WITHOUT
;; ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
;; or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General
;; Public License for more details.
;; You should have received a copy of the GNU Affero General Public
;; License along with dotted. If not, see <https://www.gnu.org/licenses/>.
;;; Commentary:
;; Bookshelf, ebook library management.
;;; Code:
(require 'tabulated-list)
(require 'infobox)
(defvar-keymap belf-mode-map
:parent tabulated-list-mode-map
"i" #'belf-book-infobox
"RET" #'belf-open-book
"o" #'belf-open-book-other-window)
(define-derived-mode belf-mode tabulated-list-mode "Bookshelf"
"Major mode for browsing a list of books."
(setq tabulated-list-format
[("Authors" 25 t)
("Title" 48 t)
("Year" 4 t)])
(setq tabulated-list-padding 2)
(tabulated-list-init-header)
(setq revert-buffer-function #'belf-list-refresh-contents)
(hl-line-mode))
(defun belf-list-books ()
(interactive)
(let ((buf (get-buffer-create "*Bookshelf*")))
(with-current-buffer buf
(belf-mode)
(belf-list-refresh-contents)
(tabulated-list-print))
(pop-to-buffer-same-window buf)))
(defun belf-list-refresh-contents (&rest _)
(setq-local tabulated-list-entries (belf-parse-all-file-names)))
(defvar belf-dir "~/Documents" "Directory of books.")
(defun belf-parse-all-file-names ()
(seq-filter
#'identity
(seq-map
(lambda (f)
(when-let ((parsed (belf-parse-file-name f)))
(let-alist parsed
(list f (vector .authors .title .year)))))
(directory-files belf-dir t))))
(defun belf-parse-file-name (file-name)
(let ((base (file-name-base file-name)))
(when (string-match "^\\(.*?\\) - \\(.*\\) (\\([0-9]*\\))" base)
`((authors . ,(match-string 1 base))
(title . ,(match-string 2 base))
(year . ,(match-string 3 base))))))
(defun belf-book-infobox ()
(interactive)
(infobox-exiftool (tabulated-list-get-id)))
(defun belf-open-book ()
(interactive)
(find-file (tabulated-list-get-id)))
(defun belf-open-book-other-window ()
(interactive)
(find-file-other-window (tabulated-list-get-id)))
(provide 'belf)
|