fancy_buff 2.0.0 → 2.2.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/lib/fancy_buff.rb +138 -76
- metadata +31 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 919af51ebb70ff27b989e17db097db51eaae6c588200d86cc081c5e2c1e8d523
|
4
|
+
data.tar.gz: '049b9b7c4233e5aee2e807e16e5027fd703da72b6683231e348645df141889ee'
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: fcb544d92688baa82919afb8fafcbc7761bc83db052759a0b6d25f15532f3b0a5d23a93628aecc1882dfcbc3a856b38241e9c846d7edae3536a1629ad18513e3
|
7
|
+
data.tar.gz: 4aa39cc8ac44c11c0bc3b31bd9f9ba882611e752bed58248301cfec5e3ad85e71c85c1e88b1312beeed36552c9894980557c06a230b74768832729bc158860e8
|
data/lib/fancy_buff.rb
CHANGED
@@ -1,118 +1,180 @@
|
|
1
1
|
# a text buffer with marks, selections, and rudimentary editing
|
2
|
-
class
|
3
|
-
attr_reader :
|
2
|
+
class FancyBuff
|
3
|
+
attr_reader :chars,
|
4
|
+
:bytes,
|
5
|
+
:lines,
|
6
|
+
:length,
|
7
|
+
:max_char_width,
|
8
|
+
:marks,
|
9
|
+
:selections
|
10
|
+
|
11
|
+
# allows the consuming application to set the window size, since that
|
12
|
+
# application is probably mananging the other buffers in use
|
13
|
+
attr_accessor :win
|
14
|
+
|
15
|
+
# gives you a default, empty, zero slice
|
16
|
+
#
|
17
|
+
# formatter - a Rouge formatter
|
18
|
+
# lexer - a Rouge lexer
|
19
|
+
def initialize(formatter, lexer)
|
20
|
+
@formatter = formatter
|
21
|
+
@lexer = lexer
|
22
|
+
|
23
|
+
# size tracking
|
24
|
+
@chars = 0 # the number of characters in the buffer (not the same as the number of bytes)
|
25
|
+
@bytes = 0 # the number of bytes in the buffer (not the same as the number of characters)
|
26
|
+
@lines = []
|
27
|
+
@max_char_width = 0
|
28
|
+
@all_buff = @lines.join("\n")
|
4
29
|
|
5
|
-
# content: the starting content of the buffer as a String
|
6
|
-
def initialize(content='')
|
7
|
-
@content = content.lines.map(&:chomp)
|
8
30
|
@marks = {}
|
9
31
|
@selections = {}
|
32
|
+
@win = [0, 0, 0, 0] # the default slice is at the beginning of the buffer, and has a zero size
|
33
|
+
end
|
10
34
|
|
11
|
-
|
12
|
-
|
13
|
-
|
35
|
+
# index of first visible row
|
36
|
+
def r
|
37
|
+
@win[0]
|
14
38
|
end
|
15
39
|
|
16
|
-
#
|
17
|
-
def
|
18
|
-
@
|
40
|
+
# index of first visible column
|
41
|
+
def c
|
42
|
+
@win[1]
|
19
43
|
end
|
20
44
|
|
21
|
-
#
|
22
|
-
|
23
|
-
|
24
|
-
def [](line_range, max_len=nil)
|
25
|
-
!!max_len ? @content[line_range] : @content[line_range].map{|l| l[..max_len] }
|
45
|
+
# width of the buffer window
|
46
|
+
def w
|
47
|
+
@win[2]
|
26
48
|
end
|
27
49
|
|
28
|
-
#
|
29
|
-
|
30
|
-
|
31
|
-
# hgt: the number of rows
|
32
|
-
def rect(col, row, wid, hgt)
|
33
|
-
@content[row..(row + hgt - 1)]
|
34
|
-
.map{|row| row.chomp.chars[col..(col + wid - 1)].join }
|
50
|
+
# height of the buffer window
|
51
|
+
def h
|
52
|
+
@win[3]
|
35
53
|
end
|
36
54
|
|
37
|
-
#
|
38
|
-
#
|
39
|
-
|
40
|
-
|
41
|
-
# mark
|
42
|
-
def mark(sym, char_num)
|
43
|
-
@marks[sym] = char_num
|
55
|
+
# returns an array of strings representing the visible characters from this
|
56
|
+
# FancyBuffer's @rect
|
57
|
+
def win_s
|
58
|
+
r, c, w, h = @win
|
44
59
|
|
45
|
-
|
60
|
+
return [] if h == 0 || w == 0
|
61
|
+
|
62
|
+
text = @formatter
|
63
|
+
.format(@lexer.lex(@lines.join("\n")))
|
64
|
+
.lines[r..(r + visible_lines - 1)]
|
65
|
+
.map.with_index{|row, i| "#{(i + r + 1).to_s.rjust(3)} #{row.chars[c..(c + w - 1 - 4)]&.join}" }
|
66
|
+
.map{|l| l.chomp + "\e[0K" } +
|
67
|
+
Array.new(blank_lines) { "\e[0K" }
|
46
68
|
end
|
47
69
|
|
48
|
-
#
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
# selection
|
53
|
-
def select(sym, char_range)
|
54
|
-
@selections[sym] = char_range
|
70
|
+
# the number of visible lines from @lines at any given time
|
71
|
+
def visible_lines
|
72
|
+
[h, @lines.length - r].min
|
73
|
+
end
|
55
74
|
|
56
|
-
|
75
|
+
# the number of blank lines in the buffer after showing all visible lines
|
76
|
+
def blank_lines
|
77
|
+
[@win[3] - visible_lines, 0].max
|
57
78
|
end
|
58
79
|
|
59
|
-
#
|
60
|
-
|
61
|
-
|
62
|
-
@content.insert(line, index)
|
63
|
-
@length += line.length
|
80
|
+
# scrolls the visible window up
|
81
|
+
def win_up(n=1)
|
82
|
+
@win[0] = [@win[0] - n, 0].max
|
64
83
|
end
|
65
84
|
|
66
|
-
#
|
67
|
-
|
68
|
-
|
69
|
-
# TODO: this is tricky because if the string contains multiple lines then
|
70
|
-
# you're not just inserting in the middle of an existing line, you're
|
71
|
-
# inserting some text which may include multiple lines
|
85
|
+
# scrolls the visible window down
|
86
|
+
def win_down(n=1)
|
87
|
+
@win[0] = [@win[0] + n, @lines.length - 1].min
|
72
88
|
end
|
73
89
|
|
74
|
-
#
|
75
|
-
def
|
76
|
-
@
|
77
|
-
@content.delete_at(index)
|
90
|
+
# scrolls the visible window left
|
91
|
+
def win_left(n=1)
|
92
|
+
@win[1] = [@win[1] - n, 0].max
|
78
93
|
end
|
79
94
|
|
80
|
-
#
|
81
|
-
def
|
82
|
-
|
95
|
+
# scrolls the visible window right
|
96
|
+
def win_right(n=1)
|
97
|
+
@win[1] = [@win[1] + n, max_char_width - 1].min
|
83
98
|
end
|
84
99
|
|
85
|
-
#
|
86
|
-
|
87
|
-
|
88
|
-
|
100
|
+
# set a mark, as in the Vim sense
|
101
|
+
#
|
102
|
+
# sym: the name of the mark
|
103
|
+
# char_num: the number of characters from the top of the buffer to set the
|
104
|
+
# mark
|
105
|
+
def mark(sym, char_num)
|
106
|
+
@marks[sym] = [@chars, char_num].min
|
89
107
|
|
90
108
|
nil
|
91
109
|
end
|
92
|
-
alias << push
|
93
|
-
|
94
|
-
# deletes and returns the last line of this buffer
|
95
|
-
def pop
|
96
|
-
@length -= (@content.pop).length
|
97
110
|
|
111
|
+
# remote a mark by name
|
112
|
+
#
|
113
|
+
# sym: the name of the mark to remove
|
114
|
+
def unmark(sym)
|
115
|
+
@marks.delete(sym)
|
116
|
+
|
98
117
|
nil
|
99
118
|
end
|
100
119
|
|
101
|
-
#
|
102
|
-
|
103
|
-
|
104
|
-
|
120
|
+
# selects a named range of characters. selections are used to highlight
|
121
|
+
# chunks of text that you can refer to later. by giving them a name it's like
|
122
|
+
# having a clipboard with multiple clips on it.
|
123
|
+
#
|
124
|
+
# sym: the name of the selection
|
125
|
+
# char_range: a Range representing the starting and ending char of the
|
126
|
+
# selection
|
127
|
+
def select(sym, char_range)
|
128
|
+
@selections[sym] = char_range
|
105
129
|
|
106
130
|
nil
|
107
131
|
end
|
108
|
-
alias >> unshift
|
109
132
|
|
110
|
-
# deletes
|
111
|
-
|
112
|
-
|
133
|
+
# deletes a named selection
|
134
|
+
#
|
135
|
+
# sym: the name of the selection
|
136
|
+
# char_range: a Range representing the starting and ending char of the
|
137
|
+
# selection
|
138
|
+
def unselect(sym)
|
139
|
+
@selections.delete(sym)
|
140
|
+
|
141
|
+
nil
|
113
142
|
end
|
114
143
|
|
115
|
-
|
116
|
-
|
144
|
+
# line: the line to add to the end of the buffer
|
145
|
+
def <<(line)
|
146
|
+
line.chomp!
|
147
|
+
@lines << line
|
148
|
+
@bytes += line.length
|
149
|
+
@chars += line.chars.length
|
150
|
+
@max_char_width = line.chars.length if line.chars.length > @max_char_width
|
151
|
+
|
152
|
+
nil
|
117
153
|
end
|
154
|
+
#
|
155
|
+
# # deletes and returns the last line of this buffer
|
156
|
+
# def pop
|
157
|
+
# l = @lines.pop
|
158
|
+
# @bytes -= l.length
|
159
|
+
# @chars -= l.chars.length
|
160
|
+
#
|
161
|
+
# nil
|
162
|
+
# end
|
163
|
+
#
|
164
|
+
# # line: the line to be added to the beginning of the buffer
|
165
|
+
# def unshift(line)
|
166
|
+
# @lines.unshift(line)
|
167
|
+
# @bytes += line.length
|
168
|
+
# @chars += line.chars.length
|
169
|
+
#
|
170
|
+
# nil
|
171
|
+
# end
|
172
|
+
# alias >> unshift
|
173
|
+
#
|
174
|
+
# # deletes and returns the first line of the buffer
|
175
|
+
# def shift
|
176
|
+
# l = @lines.shift
|
177
|
+
# @bytes -= l.length
|
178
|
+
# @chars -= l.chars.length
|
179
|
+
# end
|
118
180
|
end
|
metadata
CHANGED
@@ -1,15 +1,43 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: fancy_buff
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 2.
|
4
|
+
version: 2.2.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Jeff Lunt
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2023-
|
12
|
-
dependencies:
|
11
|
+
date: 2023-06-25 00:00:00.000000000 Z
|
12
|
+
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: rouge
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - "~>"
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: '4.1'
|
20
|
+
type: :runtime
|
21
|
+
prerelease: false
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
23
|
+
requirements:
|
24
|
+
- - "~>"
|
25
|
+
- !ruby/object:Gem::Version
|
26
|
+
version: '4.1'
|
27
|
+
- !ruby/object:Gem::Dependency
|
28
|
+
name: minitest
|
29
|
+
requirement: !ruby/object:Gem::Requirement
|
30
|
+
requirements:
|
31
|
+
- - ">="
|
32
|
+
- !ruby/object:Gem::Version
|
33
|
+
version: '0'
|
34
|
+
type: :development
|
35
|
+
prerelease: false
|
36
|
+
version_requirements: !ruby/object:Gem::Requirement
|
37
|
+
requirements:
|
38
|
+
- - ">="
|
39
|
+
- !ruby/object:Gem::Version
|
40
|
+
version: '0'
|
13
41
|
description: a text buffer with marks, selections, and simple insert/delete
|
14
42
|
email: jefflunt@gmail.com
|
15
43
|
executables: []
|