2014-11-16 05:30:26 +11:00
|
|
|
# What is Origami?
|
|
|
|
|
|
|
|
A text folding minor mode for Emacs.
|
|
|
|
|
|
|
|
With this minor mode enabled, you can collapse and expand regions of
|
|
|
|
text.
|
|
|
|
|
|
|
|
The actual buffer contents are never changed in any way. This works by
|
|
|
|
using overlays to affect how the buffer is presented. This also means
|
|
|
|
that all of your usual editing commands should work with folded
|
|
|
|
regions. For example killing and yanking folded text works as you
|
|
|
|
would expect.
|
|
|
|
|
|
|
|
There are many commands provided to make expanding and collapsing text
|
|
|
|
convenient.
|
|
|
|
|
|
|
|
# What does it look like?
|
|
|
|
|
|
|
|
![origami](http://www.gregsexton.org/images/origami-screen.png)
|
|
|
|
|
|
|
|
# How do I install it?
|
|
|
|
|
2015-01-18 02:44:56 +11:00
|
|
|
The easiest way is to just use MELPA. For manual installation:
|
|
|
|
|
2014-11-16 05:30:26 +11:00
|
|
|
Firstly, origami requires the following dependencies:
|
|
|
|
|
|
|
|
* https://github.com/magnars/dash.el
|
|
|
|
* https://github.com/magnars/s.el
|
|
|
|
|
|
|
|
You should install these anyway, they make working with elisp much
|
|
|
|
more comfortable.
|
|
|
|
|
|
|
|
Drop this package somewhere on your load-path or
|
|
|
|
|
|
|
|
(add-to-list 'load-path (expand-file-name "/path/to/origami.el/"))
|
|
|
|
|
|
|
|
Then
|
|
|
|
|
|
|
|
(require 'origami)
|
|
|
|
|
|
|
|
In a buffer run `M-x origami-mode`, and start experimenting with any
|
|
|
|
of the supplied origami interactive functions. I recommend binding
|
|
|
|
these to keys of your choice in the `origami-mode-map`.
|
|
|
|
|
|
|
|
This has been tested on Emacs 24.3 and 24.4.
|
|
|
|
|
|
|
|
# What can it do?
|
|
|
|
|
|
|
|
Origami works by parsing the buffer to determine a fold structure.
|
|
|
|
(Currently there is only support for determining the fold structure
|
|
|
|
using a parser.)
|
|
|
|
|
|
|
|
The following commands are supplied to manipulate folds in the buffer:
|
|
|
|
|
2014-11-16 05:39:48 +11:00
|
|
|
<table>
|
|
|
|
<tr>
|
|
|
|
<td>origami-open-node</td>
|
|
|
|
<td>Open a fold node.</td>
|
|
|
|
</tr>
|
|
|
|
|
|
|
|
<tr>
|
|
|
|
<td>origami-open-node-recursively</td>
|
|
|
|
<td>Open a fold node and all of its children.</td>
|
|
|
|
</tr>
|
|
|
|
|
|
|
|
<tr>
|
|
|
|
<td>origami-show-node</td>
|
|
|
|
<td>Like origami-open-node but also opens parent fold nodes recursively so as to ensure the position where point is is visible.</td>
|
|
|
|
</tr>
|
|
|
|
|
|
|
|
<tr>
|
|
|
|
<td>origami-close-node</td>
|
|
|
|
<td>Close a fold node.</td>
|
|
|
|
</tr>
|
|
|
|
|
|
|
|
<tr>
|
|
|
|
<td>origami-close-node-recursively</td>
|
|
|
|
<td>Close a fold node and all of its children.</td>
|
|
|
|
</tr>
|
|
|
|
|
|
|
|
<tr>
|
|
|
|
<td>origami-toggle-node</td>
|
|
|
|
<td>Toggle open or closed a fold node.</td>
|
|
|
|
</tr>
|
|
|
|
|
|
|
|
<tr>
|
|
|
|
<td>origami-forward-toggle-node</td>
|
|
|
|
<td>Search forward on this line for a node and toggle it open or closed. This makes toggling nodes much more convenient.</td>
|
|
|
|
</tr>
|
|
|
|
|
|
|
|
<tr>
|
|
|
|
<td>origami-recursively-toggle-node</td>
|
|
|
|
<td>Acts like org-mode header collapsing. Cycle a fold between open, recursively open, closed.</td>
|
|
|
|
</tr>
|
|
|
|
|
|
|
|
<tr>
|
|
|
|
<td>origami-open-all-nodes</td>
|
|
|
|
<td>Open every fold in the buffer.</td>
|
|
|
|
</tr>
|
|
|
|
|
|
|
|
<tr>
|
|
|
|
<td>origami-close-all-nodes</td>
|
|
|
|
<td>Close every fold in the buffer.</td>
|
|
|
|
</tr>
|
|
|
|
|
2014-11-17 05:09:19 +11:00
|
|
|
<tr>
|
|
|
|
<td>origami-toggle-all-nodes</td>
|
|
|
|
<td>Toggle open/closed every fold node in the buffer.</td>
|
|
|
|
</tr>
|
|
|
|
|
2014-11-16 05:39:48 +11:00
|
|
|
<tr>
|
|
|
|
<td>origami-show-only-node</td>
|
|
|
|
<td>Close everything but the folds necessary to see the point. Very useful for concentrating on an area of code.</td>
|
|
|
|
</tr>
|
|
|
|
|
|
|
|
<tr>
|
|
|
|
<td>origami-previous-fold</td>
|
|
|
|
<td>Move to the previous fold.</td>
|
|
|
|
</tr>
|
|
|
|
|
|
|
|
<tr>
|
|
|
|
<td>origami-next-fold</td>
|
|
|
|
<td>Move to the next fold.</td>
|
|
|
|
</tr>
|
|
|
|
|
|
|
|
<tr>
|
|
|
|
<td>origami-undo</td>
|
|
|
|
<td>Undo the last folding operation.</td>
|
|
|
|
</tr>
|
|
|
|
|
|
|
|
<tr>
|
|
|
|
<td>origami-redo</td>
|
|
|
|
<td>Redo the last undone folding operation.</td>
|
|
|
|
</tr>
|
|
|
|
|
|
|
|
<tr>
|
|
|
|
<td>origami-reset</td>
|
|
|
|
<td>Remove all folds from the buffer and reset all origami state. Useful if origami messes up!</td>
|
|
|
|
</tr>
|
|
|
|
</table>
|
2014-11-16 05:30:26 +11:00
|
|
|
|
|
|
|
# Does it support my favourite major-mode?
|
|
|
|
|
|
|
|
Probably not. Currently out of the box support is provided for:
|
|
|
|
|
|
|
|
* C
|
|
|
|
* C++
|
|
|
|
* Clojure
|
|
|
|
* Java
|
2014-11-23 08:57:01 +11:00
|
|
|
* Javascript
|
2014-11-16 05:30:26 +11:00
|
|
|
* Perl
|
|
|
|
* elisp
|
2015-04-26 00:20:06 +10:00
|
|
|
* Go
|
|
|
|
* PHP
|
2014-11-16 05:30:26 +11:00
|
|
|
|
|
|
|
It should be trivial to add support for any language that uses braces
|
|
|
|
to delimit blocks. Just add to `origami-parser-alist` something like:
|
|
|
|
`(mode-name . origami-c-style-parser)`. Adding support for another
|
|
|
|
lisp dialect should be almost as simple.
|
|
|
|
|
|
|
|
I'm happy to work on parsers for other languages if enough interest is
|
|
|
|
expressed.
|
|
|
|
|
|
|
|
It should be fairly easy to write a parser. An origami parser is a
|
|
|
|
function that takes a 'create function' and returns a function taking
|
|
|
|
the string to be parsed. The returned function should return a list of
|
|
|
|
fold nodes. Fold nodes are created using the passed-in create
|
|
|
|
function. Best to use an example:
|
|
|
|
|
|
|
|
(defun my-amazing-parser (create)
|
|
|
|
(lambda (content)
|
2014-11-16 08:15:28 +11:00
|
|
|
(list (funcall create beginning-of-the-fold-node-point-position ; inclusive
|
|
|
|
end-of-the-fold-node-point-position ; exclusive
|
2014-11-16 05:30:26 +11:00
|
|
|
offset ; this allows you to show some of the start of the folded text
|
2014-11-16 05:39:48 +11:00
|
|
|
child-nodes))))
|
2014-11-16 23:46:08 +11:00
|
|
|
|
|
|
|
# How is this different from [yafolding](https://github.com/zenozeng/yafolding.el)?
|
|
|
|
|
|
|
|
I wasn't aware of yafolding before writing this. It looks like origami
|
|
|
|
provides a richer set of functions for manipulating folds. It is also
|
|
|
|
smarter about folding for the supported modes - yafolding uses
|
|
|
|
indentation as a folding heuristic.
|
|
|
|
|
|
|
|
# How is this different from [hideshow](http://www.emacswiki.org/HideShow)?
|
|
|
|
|
|
|
|
Again, origami provides a much richer set of functions for
|
|
|
|
manipulating folds. I looked at extending hideshow but gave up when I
|
|
|
|
realised it kept all of its state in the buffer overlays. This makes
|
|
|
|
it quite difficult to write some of the more complex fold
|
|
|
|
manipulations.
|
|
|
|
|
|
|
|
Origami maintains a data structure representing the folds and provides
|
|
|
|
a rich library of functions for manipulating it. This makes adding new
|
|
|
|
folding operations easy.
|
|
|
|
|
|
|
|
# How is this different from [folding.el](http://www.emacswiki.org/emacs/folding.el)?
|
|
|
|
|
|
|
|
Folding.el uses markers in the buffer to annotate folds. It should be
|
|
|
|
very easy to add support for this to origami if anyone is looking for
|
|
|
|
this feature?
|
|
|
|
|
|
|
|
# How is this different from folding implemented by a specific mode?
|
|
|
|
|
|
|
|
It's general purpose and concentrates only on providing a decent
|
|
|
|
folding solution. You need only write a parser for origami to get all
|
|
|
|
of its folding features for free.
|