-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathcodedit_buffer.html
478 lines (471 loc) · 21.9 KB
/
codedit_buffer.html
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
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
<!DOCTYPE html>
<html>
<head>
<meta charset='utf-8'>
<title> codedit_buffer - text manipulation </title>
<script src="jquery.js"></script>
<script src="jquery-cookie.js"></script>
<script src="jquery-tablesorter.js"></script>
<script src="strftime.js"></script>
<script src="mustache.js"></script>
<script src="config.js"></script>
<script src="main.js"></script>
<link rel="stylesheet" type="text/css" href="templates/reset.css" />
<link rel="stylesheet" type="text/css" href="templates/hack.css" />
<link rel="stylesheet" type="text/css" id="lights_css" />
<script>
var DOCNAME = 'codedit_buffer'
var PROJECT = 'codedit'
//set the lights before rendering starts
set_lights()
</script>
</head>
<body>
<header>
<div class="container">
<div class="btn-container btn-lights-container">
<a href="#" class="btn btn-lights" id="lights">lights</a>
</div>
<div class="btn-container btn-home-container">
<a href="/" class="btn btn-home">luapower</a>
</div>
<table id="header_table">
<tr>
<td style="vertical-align: middle;" width="100%">
<h1> codedit_buffer </h1>
<h2> text manipulation </h2>
</td>
<td style="vertical-align: middle;" align="right" style="height: 150px">
<table><tr><td>
<div class="doc" id="package_info_container">
<div id="package_info"> </div>
<div id="commit_log"> </div>
</div>
<a href="https://github.com/luapower/codedit" class="btn btn-rightside btn-github"><span class="icon"></span>View on GitHub</a>
</td></tr><tr><td>
<a href="https://github.com/luapower/codedit/tarball/master" class="btn btn-rightside">Download as .tar.gz</a>
</td></tr><tr><td>
<a href="https://github.com/luapower/codedit/zipball/master" class="btn btn-rightside">Download as .zip</a>
</td></tr></table>
</td>
</tr>
</table>
<div class="btn-container btn-discuss-container">
<a href="https://github.com/luapower/codedit/issues/new" target="_blank"
class="btn btn-rightside btn-discuss"><span class="icon"></span>Discuss</a>
</div>
</div>
</header>
<div class="bg-container">
<div class="bg-center-container">
<div class="bg bg-codedit" style="background-image: url('bg/codedit.png');"></div>
</div>
</div>
<div class="under-header">
<div class="container">
<div id="toc_container" class="toc_container doc"></div>
<button id=tab1_button class="tab_button hidden">Documentation</button>
<button id=tab2_button class="tab_button hidden">Package Info</button>
<div id="tabs_cointainer">
<div id="tab1_container">
<section class="doc">
<span id="module_info"></span>
<h2 id="local-buffer-requirecodedit_buffer"><code>local buffer = require'codedit_buffer'</code></h2>
<p>Buffers are the core of text editing. A buffer stores the text as a list of lines and contains methods for analyzing, navigating, selecting and editing the text at a logical level, independent of how the text is rendered. The buffer contains methods that deal with text at various levels of abstraction.</p>
<ol style="list-style-type: decimal">
<li><p>At the bottom we have lines of bytes, let's call that the binary space.</p></li>
<li><p>Over that there's the char space, the space of lines and columns, where each char has a (line, col) pair. Since the chars are utf8 codepoints, the correspondence between char space and binary space is not linear. We don't deal much in binary space, only in char space (we use the utf8 library to traverse the codepoints).</p></li>
<li><p>The space outside of the available text is called the unclamped char space. We cannot select text from this space, but we can navigate it as if it was made of empty lines.</p></li>
<li><p>Higher up there's the visual space, which is how the text looks after tab expansion, for a fixed tab size. Again, the correspondence between char space (let's call it real space) and visual space is not linear.</p></li>
</ol>
<blockquote>
<p>Since we don't support automatic line wrapping, lines have a 1:1 correspondence between all these spaces, only the columns are different.</p>
</blockquote>
<h2 id="properties">Properties</h2>
<pre class="sourceCode lua"><code class="sourceCode lua"><span class="kw">buffer</span><span class="ot">.</span><span class="kw">line_terminator</span> <span class="ot">=</span> <span class="kw">nil</span> <span class="co">--line terminator to use when retrieving lines as a string. nil means autodetect.</span>
<span class="kw">buffer</span><span class="ot">.</span><span class="kw">default_line_terminator</span> <span class="ot">=</span> <span class="st">'</span><span class="ot">\n</span><span class="st">'</span> <span class="co">--line terminator to use when autodetection fails.</span>
<span class="co">--view overrides</span>
<span class="kw">buffer</span><span class="ot">.</span><span class="kw">background_color</span> <span class="ot">=</span> <span class="kw">nil</span>
<span class="kw">buffer</span><span class="ot">.</span><span class="kw">text_color</span> <span class="ot">=</span> <span class="kw">nil</span>
<span class="kw">buffer</span><span class="ot">.</span><span class="kw">line_highlight_color</span> <span class="ot">=</span> <span class="kw">nil</span></code></pre>
<h2 id="methods">Methods</h2>
<table>
<col width="50%" />
<col width="50%" />
<tbody>
<tr class="odd">
<td align="left"><code>buffer:new(editor, view, [text]) -> buf</code></td>
<td align="left">create a buffer object, optionally filled with an initial text.</td>
</tr>
<tr class="even">
<td align="left"><code>buffer:detect_line_terminator(text) -> term</code></td>
<td align="left">get the most common line terminator in a string</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:detect_indent()</code></td>
<td align="left">detect indentation and set tabsize</td>
</tr>
<tr class="even">
<td align="left"><strong>text boundaries</strong></td>
<td align="left"></td>
</tr>
<tr class="odd">
<td align="left"><code>buf:last_line() -> line</code></td>
<td align="left">last line number (also the number of lines)</td>
</tr>
<tr class="even">
<td align="left"><code>buf:getline(line) -> s</code></td>
<td align="left">line contents (without line terminator)</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:contents([lines_t]) -> s</code></td>
<td align="left">array of lines to text, using current line terminator</td>
</tr>
<tr class="even">
<td align="left"><strong>line-level editing</strong></td>
<td align="left"></td>
</tr>
<tr class="odd">
<td align="left"><code>buf:insert_line(line, s)</code></td>
<td align="left">insert a line</td>
</tr>
<tr class="even">
<td align="left"><code>buf:remove_line(line)</code></td>
<td align="left">remove a line</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:set_line(line, s)</code></td>
<td align="left">replace a line</td>
</tr>
<tr class="even">
<td align="left"><code>buf:move_line(line1, line2)</code></td>
<td align="left">switch lines</td>
</tr>
<tr class="odd">
<td align="left"><strong>line boundaries</strong></td>
<td align="left"></td>
</tr>
<tr class="even">
<td align="left"><code>buf:last_col(line) -> col</code></td>
<td align="left">last column (char index) on a valid line</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:end_pos() -> last_line, last_col</code></td>
<td align="left">the position right after the last char in the text</td>
</tr>
<tr class="even">
<td align="left"><code>buf:next_char_pos(line, col, [restrict_eol]) -> line, col</code></td>
<td align="left">position after some char, unclamped</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:prev_char_pos(line, col, [restrict_eol]) -> line, col</code></td>
<td align="left">position before some char, unclamped</td>
</tr>
<tr class="even">
<td align="left"><code>buf:near_char_pos(line, col, chars, [restrict_eol]) -> line, col</code></td>
<td align="left">position that is a number of chars after or before some char, unclamped</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:clamp_pos(line, col) -> line, col</code></td>
<td align="left">clamp a position to the available text</td>
</tr>
<tr class="even">
<td align="left"><strong>selecting</strong></td>
<td align="left"></td>
</tr>
<tr class="odd">
<td align="left"><code>buf:sub(line, col1, col2) -> s</code></td>
<td align="left">line slice between two columns on a valid line</td>
</tr>
<tr class="even">
<td align="left"><code>buf:select_string(line1, col1, line2, col2) -> s</code></td>
<td align="left">select the string between two valid, subsequent positions in the text</td>
</tr>
<tr class="odd">
<td align="left"><strong>editing</strong></td>
<td align="left"></td>
</tr>
<tr class="even">
<td align="left"><code>buf:extend(line, col)</code></td>
<td align="left">extend the buffer up to (line,col-1) with newlines and spaces so we can edit there.</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:insert_string(line, col, s) -> line, col</code></td>
<td align="left">insert a multiline string at a specific position in the text, returning the position after the last character. if the position is outside the text, the buffer is extended. return the position after the string.</td>
</tr>
<tr class="even">
<td align="left"><code>buf:remove_string(line1, col1, line2, col2)</code></td>
<td align="left">remove the string between two arbitrary, subsequent positions in the text. line2,col2 is the position after the last character to be removed.</td>
</tr>
<tr class="odd">
<td align="left"><strong>tab expansion</strong></td>
<td align="left"></td>
</tr>
<tr class="even">
<td align="left"><code>buf:tab_width(vcol) -> w</code></td>
<td align="left">how many spaces till the next tabstop</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:next_tabstop(vcol) -> vcol</code></td>
<td align="left">visual col of the next tabstop</td>
</tr>
<tr class="even">
<td align="left"><code>buf:prev_tabstop(vcol) -> vcol</code></td>
<td align="left">visual col of the prev. tabstop</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:visual_col(line, col) -> vcol</code></td>
<td align="left">real col -> visual col. outside eof visual columns have the same width as real columns.</td>
</tr>
<tr class="even">
<td align="left"><code>buf:real_col(line, vcol) -> col</code></td>
<td align="left">visual col -> char col. outside eof visual columns have the same width as real columns.</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:aligned_col(target_line, line, col) -> col</code></td>
<td align="left">real col on a line that is vertically aligned (in the visual space) to the same col on a different line.</td>
</tr>
<tr class="even">
<td align="left"><code>buf:max_visual_col() -> vcol</code></td>
<td align="left">number of columns needed to fit the entire text (for computing the client area for horizontal scrolling)</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:istab(line, col) -> true | false</code></td>
<td align="left">is that a tab?</td>
</tr>
<tr class="even">
<td align="left"><code>buf:next_tabstop_col(line, col) -> col</code></td>
<td align="left">real col on the next tabstop</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:prev_tabstop_col(line, col) -> col</code></td>
<td align="left">real col on the prev tabstop</td>
</tr>
<tr class="even">
<td align="left"><strong>selecting text based on tab expansion</strong></td>
<td align="left"></td>
</tr>
<tr class="odd">
<td align="left"><code>buf:select_indent(line, [col]) -> s</code></td>
<td align="left">the indent of the line, optionally up to some column</td>
</tr>
<tr class="even">
<td align="left"><code>buf:indent(line, col, use_tab) -> line, col</code></td>
<td align="left">insert a tab or spaces from a position up to the next tabstop. return the cursor at the tabstop, where the indented text is.</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:indent_line(line, use_tab) -> line, col</code></td>
<td align="left">insert a tab or spaces at col 1</td>
</tr>
<tr class="even">
<td align="left"><code>buf:tabs_and_spaces(vcol1, vcol2) -> tabs, spaces</code></td>
<td align="left">find the maximum number of tabs and minimum of spaces that fit between two visual columns</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:gen_whitespace(vcol1, vcol2, use_tabs) -> s</code></td>
<td align="left">generate whitespace (tabs and spaces or just spaces, depending on the use_tabs flag) between two vcols.</td>
</tr>
<tr class="even">
<td align="left"><code>buf:insert_whitespace(line, col, vcol2, use_tabs)</code></td>
<td align="left">insert whitespace on a line, from a position up to (but excluding) a visual col on the same line.</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:next_nonspace_col(line, col)</code><br /><code>buf:prev_nonspace_col(line, col)</code></td>
<td align="left">find non-space boundaries (jump any whitespace)</td>
</tr>
<tr class="even">
<td align="left"><code>buf:isempty(line)</code></td>
<td align="left">check if a line is either invalid, empty or made entirely of whitespace</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:indenting(line, col) -> true | false</code></td>
<td align="left">check if a position is before the first non-space char, that is, in the indentation area.</td>
</tr>
<tr class="even">
<td align="left"><code>buf:next_tabful_col(line, col, [restrict_eol]) -> col</code></td>
<td align="left">find tabful boundaries. a tabful is the whitespace between two tabstops. the tabful column after some char is either the next tabstop or the first non-space char after the prev. char or the char after the last col, whichever comes first, and if after the given char.</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:prev_tabful_col(line, col) -> col</code></td>
<td align="left">the tabful column before some char, which is either the prev. tabstop or the char after the prev. non-space char, whichever comes first, and if before the given char.</td>
</tr>
<tr class="even">
<td align="left"><strong>editing based on tabfuls</strong></td>
<td align="left"></td>
</tr>
<tr class="odd">
<td align="left"><code>buf:outdent(line, col)</code></td>
<td align="left">remove the space up to the next tabstop or non-space char, in other words, remove a tabful.</td>
</tr>
<tr class="even">
<td align="left"><code>buf:outdent_line(line)</code></td>
<td align="left">outdent at col 1.</td>
</tr>
<tr class="odd">
<td align="left"><strong>word boundaries</strong></td>
<td align="left"></td>
</tr>
<tr class="even">
<td align="left"><code>buf:next_word_break_col(line, col, [word_chars]) -> col</code><br /><code>buf:prev_word_break_col(line, col, [word_chars]) -> col</code></td>
<td align="left">word breaking semantics per [codedit_str]</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:word_cols(line, col, [word_chars]) -> col1, col2</code></td>
<td align="left">word boundaries surrounding a char position</td>
</tr>
<tr class="even">
<td align="left"><code>buf:next_list_aligned_vcol(line, col, [restrict_eol]) -> vcol</code></td>
<td align="left">find the visual col that is aligned with the next word on the line above</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:next_args_aligned_vcol(line, col, [restrict_eol) -> vcol</code></td>
<td align="left">find the visual col that is aligned with the next open bracket on the line above</td>
</tr>
<tr class="even">
<td align="left"><strong>paragraph boundaries</strong></td>
<td align="left"></td>
</tr>
<tr class="odd">
<td align="left"><code>buf:reflow_lines(line1, line2, line_width, tabsize, align, wrap) -> line2, col2</code></td>
<td align="left">reflow the text between two lines. return the position after the last inserted character. align can be 'left', 'right', 'justify'. wrap can be 'greedy', or 'knuth'.</td>
</tr>
<tr class="even">
<td align="left"><strong>saving to disk</strong></td>
<td align="left"></td>
</tr>
<tr class="odd">
<td align="left"><code>buf:save_to_file(filename)</code></td>
<td align="left">save the buffer to disk atomically</td>
</tr>
<tr class="even">
<td align="left"><strong>TODO</strong></td>
<td align="left"></td>
</tr>
<tr class="odd">
<td align="left"><code>buf:invalidate()</code></td>
<td align="left"></td>
</tr>
</tbody>
</table>
<h2 id="undoredo-stack">Undo/redo stack</h2>
<h2 id="requirecodedit_undo"><code>require'codedit_undo'</code></h2>
<p>Extends the buffer class with methods for undo/redo.</p>
<p>The undo stack is a stack of undo groups. An undo group is a list of editor commands to be executed in reverse order, which together perform what the user perceives as a single undo operation. Consecutive undo groups of the same group type are merged together. The undo commands in the group can be any editor method with any arguments.</p>
<table>
<tbody>
<tr class="odd">
<td align="left"><code>buf:start_undo_group(group_type)</code></td>
<td align="left">auto-close the current undo group and start a new one</td>
</tr>
<tr class="even">
<td align="left"><code>buf:end_undo_group()</code></td>
<td align="left">close and commit the current undo group</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:undo_command(...)</code></td>
<td align="left">add an undo command to the current undo group, if any</td>
</tr>
<tr class="even">
<td align="left"><code>buf:undo()</code></td>
<td align="left">exec the last undo group, recording a redo group</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:redo()</code></td>
<td align="left">exec the last redo group, recording a undo group</td>
</tr>
</tbody>
</table>
<h2 id="normalization">Normalization</h2>
<h2 id="requirecodedit_normal"><code>require'codedit_normal'</code></h2>
<p>Extends the buffer class with properties and methods for text normalization.</p>
<pre class="sourceCode lua"><code class="sourceCode lua"><span class="kw">buffer</span><span class="ot">.</span><span class="kw">eol_spaces</span> <span class="ot">=</span> <span class="st">'remove'</span> <span class="co">--leave, remove.</span>
<span class="kw">buffer</span><span class="ot">.</span><span class="kw">eof_lines</span> <span class="ot">=</span> <span class="st">'leave'</span> <span class="co">--leave, remove, ensure, or a number.</span>
<span class="kw">buffer</span><span class="ot">.</span><span class="kw">convert_indent</span> <span class="ot">=</span> <span class="st">'tabs'</span> <span class="co">--tabs, spaces, leave: convert indentation to tabs or spaces based on tabsize</span></code></pre>
<table>
<tbody>
<tr class="odd">
<td align="left"><code>buf:remove_eol_spaces()</code></td>
<td align="left">remove any spaces past eol</td>
</tr>
<tr class="even">
<td align="left"><code>buf:ensure_eof_line()</code></td>
<td align="left">add an empty line at eof if there is none</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:remove_eof_lines()</code></td>
<td align="left">remove any empty lines at eof, except the first line</td>
</tr>
<tr class="even">
<td align="left"><code>buf:convert_indent_to_tabs()</code></td>
<td align="left">indent to tabs</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:convert_indent_to_spaces()</code></td>
<td align="left">indent to spaces</td>
</tr>
<tr class="even">
<td align="left"><code>buf:normalize()</code></td>
<td align="left">normalize based on properties</td>
</tr>
</tbody>
</table>
<h2 id="text-blocks">Text Blocks</h2>
<h2 id="requirecodedit_blocks"><code>require'codedit_blocks'</code></h2>
<p>Extends the buffer class with methods for selecting and editing text blocks, i.e. vertically aligned text between two subsequent text positions.</p>
<p>Blocks are defined as (line1, col1, line2, col2), where line1 and line2 must be valid, subsequent lines in the buffer, and col1 and col2 can be anything.</p>
<table>
<col width="50%" />
<col width="50%" />
<tbody>
<tr class="odd">
<td align="left"><code>buf:block_cols(line, line1, col1, line2, col2) -> s</code></td>
<td align="left">clamped line segment on a line that intersects the rectangle formed by two arbitrary text positions.</td>
</tr>
<tr class="even">
<td align="left"><code>buf:select_block(line1, col1, line2, col2) -> lines_t</code></td>
<td align="left">select the block between two subsequent text positions as a multi-line string.</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:insert_block(line1, col1, s) -> line2, col2</code></td>
<td align="left">insert a multi-line string as a block at some position in the text. return the position after the string.</td>
</tr>
<tr class="even">
<td align="left"><code>buf:remove_block(line1, col1, line2, col2)</code></td>
<td align="left">remove the block between two subsequent positions in the text</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:indent_block(line1, col1, line2, col2, use_tab) -> n</code></td>
<td align="left">indent the block between two subsequent positions in the text returns max(visual-length(added-text)).</td>
</tr>
<tr class="even">
<td align="left"><code>buf:outdent_block(line1, col1, line2, col2)</code></td>
<td align="left">outdent the block between two subsequent positions in the text</td>
</tr>
<tr class="odd">
<td align="left"><code>buf:reflow_block(line1, col1, line2, col2, line_width, tabsize, align, wrap)</code></td>
<td align="left">reflow a block to its width. return the position after the last inserted character.</td>
</tr>
</tbody>
</table>
</section>
</div>
<div id="tab2_container" class="doc"></div>
</div>
</div>
<div class="container">
<footer>
<div id="disqus_thread"></div>
<div class="faint">cosmin.apreutesei@gmail.com | <a href="http://unlicense.org/">public domain</a></div>
</footer>
</div>
</div>
<script type="text/x-mustache" id=info_tab_template>
<h3>Modules</h3>
<ul>
{{#module_array}}
<li>{{name}}</li>
{{/module_array}}
</ul>
</script>
</body>
</html>