Last active
January 13, 2019 16:24
-
-
Save xcodebuild/87b116291aa87fde72cb to your computer and use it in GitHub Desktop.
Keeping the context when archiving in Emacs org-mode
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
;; org-archive-subtree-hierarchical.el | |
;; modified from https://lists.gnu.org/archive/html/emacs-orgmode/2014-08/msg00109.html | |
;; In orgmode | |
;; * A | |
;; ** AA | |
;; *** AAA | |
;; ** AB | |
;; *** ABA | |
;; Archiving AA will remove the subtree from the original file and create | |
;; it like that in archive target: | |
;; * AA | |
;; ** AAA | |
;; And this give you | |
;; * A | |
;; ** AA | |
;; *** AAA | |
(require 'org-archive) | |
(defun org-archive-subtree-hierarchical--line-content-as-string () | |
"Returns the content of the current line as a string" | |
(save-excursion | |
(beginning-of-line) | |
(buffer-substring-no-properties | |
(line-beginning-position) (line-end-position)))) | |
(defun org-archive-subtree-hierarchical--org-child-list () | |
"This function returns all children of a heading as a list. " | |
(interactive) | |
(save-excursion | |
;; this only works with org-version > 8.0, since in previous | |
;; org-mode versions the function (org-outline-level) returns | |
;; gargabe when the point is not on a heading. | |
(if (= (org-outline-level) 0) | |
(outline-next-visible-heading 1) | |
(org-goto-first-child)) | |
(let ((child-list (list (org-archive-subtree-hierarchical--line-content-as-string)))) | |
(while (org-goto-sibling) | |
(setq child-list (cons (org-archive-subtree-hierarchical--line-content-as-string) child-list))) | |
child-list))) | |
(defun org-archive-subtree-hierarchical--org-struct-subtree () | |
"This function returns the tree structure in which a subtree | |
belongs as a list." | |
(interactive) | |
(let ((archive-tree nil)) | |
(save-excursion | |
(while (org-up-heading-safe) | |
(let ((heading | |
(buffer-substring-no-properties | |
(line-beginning-position) (line-end-position)))) | |
(if (eq archive-tree nil) | |
(setq archive-tree (list heading)) | |
(setq archive-tree (cons heading archive-tree)))))) | |
archive-tree)) | |
(defun org-archive-subtree-hierarchical () | |
"This function archives a subtree hierarchical" | |
(interactive) | |
(let ((org-tree (org-archive-subtree-hierarchical--org-struct-subtree)) | |
(this-buffer (current-buffer)) | |
(file (abbreviate-file-name | |
(or (buffer-file-name (buffer-base-buffer)) | |
(error "No file associated to buffer"))))) | |
(save-excursion | |
(setq location (org-get-local-archive-location) | |
afile (org-extract-archive-file location) | |
heading (org-extract-archive-heading location) | |
infile-p (equal file (abbreviate-file-name (or afile "")))) | |
(unless afile | |
(error "Invalid `org-archive-location'")) | |
(if (> (length afile) 0) | |
(setq newfile-p (not (file-exists-p afile)) | |
visiting (find-buffer-visiting afile) | |
buffer (or visiting (find-file-noselect afile))) | |
(setq buffer (current-buffer))) | |
(unless buffer | |
(error "Cannot access file \"%s\"" afile)) | |
(org-cut-subtree) | |
(set-buffer buffer) | |
(org-mode) | |
(goto-char (point-min)) | |
(while (not (equal org-tree nil)) | |
(let ((child-list (org-archive-subtree-hierarchical--org-child-list))) | |
(if (member (car org-tree) child-list) | |
(progn | |
(search-forward (car org-tree) nil t) | |
(setq org-tree (cdr org-tree))) | |
(progn | |
(goto-char (point-max)) | |
(newline) | |
(org-insert-struct org-tree) | |
(setq org-tree nil))))) | |
(newline) | |
(org-yank) | |
(when (not (eq this-buffer buffer)) | |
(save-buffer)) | |
(message "Subtree archived %s" | |
(concat "in file: " (abbreviate-file-name afile)))))) | |
(defun org-insert-struct (struct) | |
"TODO" | |
(interactive) | |
(when struct | |
(insert (car struct)) | |
(newline) | |
(org-insert-struct (cdr struct)))) | |
(defun org-archive-subtree () | |
(org-archive-subtree-hierarchical) | |
) |
Firstly,
I could not use spacemacs default keybindings to use this.
I added:
(setq org-archive-default-command 'org-archive-subtree-hierarchical)
and used C-c C-x C-a.
When a subheading has been archived prior to a parent heading, it will create a duplicate parent heading.
I have a .org-file that looks like this:
* 1a-heading
** 2a-Heading
Foo bar text
*** 3a-heading
*** 3b-heading
When i archive *** 3b it correctly creates the following archive:
* 1a-heading
** 2a-Heading
*** 3b-heading
However, when i later archive the parent heading (** 2a)
The archive looks like the following:
* 1a-heading
** 2a-Heading
Foo bar text
*** 3a-heading
** 2a-Heading
*** 3b-heading
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
和二楼有同样需求,设置location后不报错,但没反应,原条目还在