sergeant 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,352 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Simple dialog modals (error, info, confirmation)
4
+
5
+ module Sergeant
6
+ module Modals
7
+ module Dialogs
8
+ def show_error_modal(message)
9
+ max_y = lines
10
+ max_x = cols
11
+
12
+ modal_height = 7
13
+ modal_width = [message.length + 10, 50].max
14
+ modal_y = (max_y - modal_height) / 2
15
+ modal_x = (max_x - modal_width) / 2
16
+
17
+ (modal_y..(modal_y + modal_height)).each do |y|
18
+ setpos(y, modal_x)
19
+ attron(color_pair(3)) do
20
+ addstr(' ' * modal_width)
21
+ end
22
+ end
23
+
24
+ setpos(modal_y, modal_x)
25
+ attron(color_pair(4) | Curses::A_BOLD) do
26
+ addstr("\u250C#{'─' * (modal_width - 2)}\u2510")
27
+ end
28
+
29
+ setpos(modal_y + 1, modal_x)
30
+ attron(color_pair(4) | Curses::A_BOLD) do
31
+ addstr('│')
32
+ end
33
+ attron(color_pair(4) | Curses::A_BOLD) do
34
+ addstr(' Error '.center(modal_width - 2))
35
+ end
36
+ attron(color_pair(4) | Curses::A_BOLD) do
37
+ addstr('│')
38
+ end
39
+
40
+ setpos(modal_y + 2, modal_x)
41
+ attron(color_pair(4)) do
42
+ addstr("\u251C#{'─' * (modal_width - 2)}\u2524")
43
+ end
44
+
45
+ setpos(modal_y + 3, modal_x)
46
+ attron(color_pair(4)) do
47
+ addstr('│ ')
48
+ end
49
+ addstr(message.center(modal_width - 4))
50
+ attron(color_pair(4)) do
51
+ addstr(' │')
52
+ end
53
+
54
+ setpos(modal_y + 4, modal_x)
55
+ attron(color_pair(4)) do
56
+ addstr("\u2502#{' ' * (modal_width - 2)}\u2502")
57
+ end
58
+
59
+ setpos(modal_y + 5, modal_x)
60
+ attron(color_pair(4)) do
61
+ addstr('│')
62
+ end
63
+ attron(color_pair(4) | Curses::A_DIM) do
64
+ addstr(' Press any key to continue '.center(modal_width - 2))
65
+ end
66
+ attron(color_pair(4)) do
67
+ addstr('│')
68
+ end
69
+
70
+ setpos(modal_y + modal_height - 1, modal_x)
71
+ attron(color_pair(4) | Curses::A_BOLD) do
72
+ addstr("\u2514#{'─' * (modal_width - 2)}\u2518")
73
+ end
74
+
75
+ refresh
76
+ getch
77
+ end
78
+
79
+ def show_info_modal(message)
80
+ max_y = lines
81
+ max_x = cols
82
+
83
+ modal_height = 7
84
+ modal_width = [message.length + 10, 50].max
85
+ modal_y = (max_y - modal_height) / 2
86
+ modal_x = (max_x - modal_width) / 2
87
+
88
+ (modal_y..(modal_y + modal_height)).each do |y|
89
+ setpos(y, modal_x)
90
+ attron(color_pair(3)) do
91
+ addstr(' ' * modal_width)
92
+ end
93
+ end
94
+
95
+ setpos(modal_y, modal_x)
96
+ attron(color_pair(4) | Curses::A_BOLD) do
97
+ addstr("\u250C#{'─' * (modal_width - 2)}\u2510")
98
+ end
99
+
100
+ setpos(modal_y + 1, modal_x)
101
+ attron(color_pair(4) | Curses::A_BOLD) do
102
+ addstr('│')
103
+ end
104
+ attron(color_pair(5) | Curses::A_BOLD) do
105
+ addstr(' Info '.center(modal_width - 2))
106
+ end
107
+ attron(color_pair(4) | Curses::A_BOLD) do
108
+ addstr('│')
109
+ end
110
+
111
+ setpos(modal_y + 2, modal_x)
112
+ attron(color_pair(4)) do
113
+ addstr("\u251C#{'─' * (modal_width - 2)}\u2524")
114
+ end
115
+
116
+ setpos(modal_y + 3, modal_x)
117
+ attron(color_pair(4)) do
118
+ addstr('│ ')
119
+ end
120
+ addstr(message.center(modal_width - 4))
121
+ attron(color_pair(4)) do
122
+ addstr(' │')
123
+ end
124
+
125
+ setpos(modal_y + 4, modal_x)
126
+ attron(color_pair(4)) do
127
+ addstr("\u2502#{' ' * (modal_width - 2)}\u2502")
128
+ end
129
+
130
+ setpos(modal_y + 5, modal_x)
131
+ attron(color_pair(4)) do
132
+ addstr('│')
133
+ end
134
+ attron(color_pair(4) | Curses::A_DIM) do
135
+ addstr(' Press any key to continue '.center(modal_width - 2))
136
+ end
137
+ attron(color_pair(4)) do
138
+ addstr('│')
139
+ end
140
+
141
+ setpos(modal_y + modal_height - 1, modal_x)
142
+ attron(color_pair(4) | Curses::A_BOLD) do
143
+ addstr("\u2514#{'─' * (modal_width - 2)}\u2518")
144
+ end
145
+
146
+ refresh
147
+ getch
148
+ end
149
+
150
+ def confirm_delete_modal(count)
151
+ max_y = lines
152
+ max_x = cols
153
+
154
+ modal_height = 9
155
+ modal_width = 60
156
+ modal_y = (max_y - modal_height) / 2
157
+ modal_x = (max_x - modal_width) / 2
158
+
159
+ (modal_y..(modal_y + modal_height)).each do |y|
160
+ setpos(y, modal_x)
161
+ attron(color_pair(3)) do
162
+ addstr(' ' * modal_width)
163
+ end
164
+ end
165
+
166
+ setpos(modal_y, modal_x)
167
+ attron(color_pair(4) | Curses::A_BOLD) do
168
+ addstr("\u250C#{'─' * (modal_width - 2)}\u2510")
169
+ end
170
+
171
+ setpos(modal_y + 1, modal_x)
172
+ attron(color_pair(4) | Curses::A_BOLD) do
173
+ addstr('│')
174
+ end
175
+ attron(color_pair(5) | Curses::A_BOLD) do
176
+ addstr(' Confirm Delete '.center(modal_width - 2))
177
+ end
178
+ attron(color_pair(4) | Curses::A_BOLD) do
179
+ addstr('│')
180
+ end
181
+
182
+ setpos(modal_y + 2, modal_x)
183
+ attron(color_pair(4)) do
184
+ addstr("\u251C#{'─' * (modal_width - 2)}\u2524")
185
+ end
186
+
187
+ msg1 = "Delete #{count} item(s) permanently?"
188
+ setpos(modal_y + 3, modal_x)
189
+ attron(color_pair(4)) do
190
+ addstr('│ ')
191
+ end
192
+ addstr(msg1.center(modal_width - 4))
193
+ attron(color_pair(4)) do
194
+ addstr(' │')
195
+ end
196
+
197
+ msg2 = 'This action cannot be undone!'
198
+ setpos(modal_y + 4, modal_x)
199
+ attron(color_pair(4)) do
200
+ addstr('│ ')
201
+ end
202
+ attron(Curses::A_BOLD) do
203
+ addstr(msg2.center(modal_width - 4))
204
+ end
205
+ attron(color_pair(4)) do
206
+ addstr(' │')
207
+ end
208
+
209
+ setpos(modal_y + 5, modal_x)
210
+ attron(color_pair(4)) do
211
+ addstr("\u2502#{' ' * (modal_width - 2)}\u2502")
212
+ end
213
+
214
+ options = [
215
+ 'y - Yes, delete',
216
+ 'n - No, cancel'
217
+ ]
218
+
219
+ options.each_with_index do |opt, idx|
220
+ setpos(modal_y + 6 + idx, modal_x)
221
+ attron(color_pair(4)) do
222
+ addstr('│ ')
223
+ end
224
+ addstr(opt.center(modal_width - 4))
225
+ attron(color_pair(4)) do
226
+ addstr(' │')
227
+ end
228
+ end
229
+
230
+ setpos(modal_y + modal_height - 1, modal_x)
231
+ attron(color_pair(4) | Curses::A_BOLD) do
232
+ addstr("\u2514#{'─' * (modal_width - 2)}\u2518")
233
+ end
234
+
235
+ refresh
236
+
237
+ loop do
238
+ ch = getch
239
+ case ch
240
+ when 'y', 'Y'
241
+ return true
242
+ when 'n', 'N', 27 # ESC
243
+ return false
244
+ end
245
+ end
246
+ end
247
+
248
+ def ask_conflict_resolution(filename)
249
+ max_y = lines
250
+ max_x = cols
251
+
252
+ modal_height = 10
253
+ modal_width = [filename.length + 30, 60].min
254
+ modal_y = (max_y - modal_height) / 2
255
+ modal_x = (max_x - modal_width) / 2
256
+
257
+ (modal_y..(modal_y + modal_height)).each do |y|
258
+ setpos(y, modal_x)
259
+ attron(color_pair(3)) do
260
+ addstr(' ' * modal_width)
261
+ end
262
+ end
263
+
264
+ setpos(modal_y, modal_x)
265
+ attron(color_pair(4) | Curses::A_BOLD) do
266
+ addstr("\u250C#{'─' * (modal_width - 2)}\u2510")
267
+ end
268
+
269
+ setpos(modal_y + 1, modal_x)
270
+ attron(color_pair(4) | Curses::A_BOLD) do
271
+ addstr('│')
272
+ end
273
+ attron(color_pair(5) | Curses::A_BOLD) do
274
+ addstr(' File Conflict '.center(modal_width - 2))
275
+ end
276
+ attron(color_pair(4) | Curses::A_BOLD) do
277
+ addstr('│')
278
+ end
279
+
280
+ setpos(modal_y + 2, modal_x)
281
+ attron(color_pair(4)) do
282
+ addstr("\u251C#{'─' * (modal_width - 2)}\u2524")
283
+ end
284
+
285
+ msg = 'File already exists:'
286
+ setpos(modal_y + 3, modal_x)
287
+ attron(color_pair(4)) do
288
+ addstr('│ ')
289
+ end
290
+ addstr(msg.ljust(modal_width - 4))
291
+ attron(color_pair(4)) do
292
+ addstr(' │')
293
+ end
294
+
295
+ setpos(modal_y + 4, modal_x)
296
+ attron(color_pair(4)) do
297
+ addstr('│ ')
298
+ end
299
+ attron(color_pair(1) | Curses::A_BOLD) do
300
+ display_name = filename.length > modal_width - 6 ? "#{filename[0..(modal_width - 10)]}..." : filename
301
+ addstr(display_name.ljust(modal_width - 4))
302
+ end
303
+ attron(color_pair(4)) do
304
+ addstr(' │')
305
+ end
306
+
307
+ setpos(modal_y + 5, modal_x)
308
+ attron(color_pair(4)) do
309
+ addstr("\u2502#{' ' * (modal_width - 2)}\u2502")
310
+ end
311
+
312
+ options = [
313
+ 's - Skip',
314
+ 'o - Overwrite',
315
+ 'r - Rename'
316
+ ]
317
+
318
+ options.each_with_index do |opt, idx|
319
+ setpos(modal_y + 6 + idx, modal_x)
320
+ attron(color_pair(4)) do
321
+ addstr('│ ')
322
+ end
323
+ addstr(opt.ljust(modal_width - 4))
324
+ attron(color_pair(4)) do
325
+ addstr(' │')
326
+ end
327
+ end
328
+
329
+ setpos(modal_y + modal_height - 1, modal_x)
330
+ attron(color_pair(4) | Curses::A_BOLD) do
331
+ addstr("\u2514#{'─' * (modal_width - 2)}\u2518")
332
+ end
333
+
334
+ refresh
335
+
336
+ loop do
337
+ ch = getch
338
+ case ch
339
+ when 's', 'S'
340
+ return :skip
341
+ when 'o', 'O'
342
+ return :overwrite
343
+ when 'r', 'R'
344
+ return :rename
345
+ when 27 # ESC
346
+ return :skip
347
+ end
348
+ end
349
+ end
350
+ end
351
+ end
352
+ end