rtfm-filemanager 8.2.4 → 8.2.5

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 9578236347587df8d2eb07db00d7a667093344d95a60103a5df3fc2819df9f9a
4
- data.tar.gz: 36ba2c5bc4b229d53200708da04fc29cc7e013fc9fee7c4abc8d10a6ba055eb7
3
+ metadata.gz: 55f253cbd09298960a51935b850697796c238f360ef914336e54c322efe76a96
4
+ data.tar.gz: c7f072d903abd7dd5210b035db90cfab3f3132e41f6a151c154b73dad3b78139
5
5
  SHA512:
6
- metadata.gz: f11d1c5405086f0a90ab186fb349a571c2af82c1e0d9b9f7513758a678db299dec69d8b9bde1c8b6f5eed91fc86d511457a29ba24287dbe2c57a04925e149240
7
- data.tar.gz: bc1f862bdb325cfa015dbb6ba31146a338ef105b9e5400bdd5988b4d616d6b9788dd6ac7c7f1e41adcad5773d71a691c83a7f11233a9f7d93b7dd45df8007d33
6
+ metadata.gz: d960c43162a9a4be724eddcc7fa42a43f2ba26a473ca6446d69b3d64226811a8f620e2b071dff33c12baf7c6ea39d089919ebd7efd0af4890e68e3a8ff700f44
7
+ data.tar.gz: 7ee2d078a318db445c040afda05301183821b3488581ac0e2c88d85e01a1fa511c3025527501dc7fc135ca6832134b2c360ca6b0f802af239a6abfb3cfc7a97d
data/README.md CHANGED
@@ -599,9 +599,9 @@ clear_image
599
599
  # Text formatting
600
600
  "text".fg(112) # foreground color (0-255)
601
601
  "text".bg(236) # background color
602
- "text".b # bold
603
- "text".u # underline
604
- "text".r # reverse
602
+ "text".bd # bold
603
+ "text".ul # underline
604
+ "text".rv # reverse
605
605
  ```
606
606
 
607
607
  ---
data/bin/rtfm CHANGED
@@ -18,7 +18,7 @@
18
18
  # get a great understanding of the code itself by simply sending
19
19
  # or pasting this whole file into you favorite AI for coding with
20
20
  # a prompt like this: "Help me understand every part of this code".
21
- @version = '8.2.4' # Performance: cache MIME type lookups
21
+ @version = '8.2.5' # rcurses 7.0: rename .b/.i/.u/.r to .bd/.it/.ul/.rv
22
22
 
23
23
  # SAVE & STORE TERMINAL {{{1
24
24
  ORIG_STTY = `stty -g`.chomp
@@ -446,7 +446,7 @@ def display_welcome_message # {{{2
446
446
  @firstrun = "
447
447
  Welcome to RTFM - the Ruby Terminal File Manager. This help text is shown on the first run.
448
448
  Next time you run RTFM, you can launch it from your terminal with a one letter command: 'r'
449
- When launched this way, RTFM will also exit in the directory you are currently in.\n".b.fg(226)
449
+ When launched this way, RTFM will also exit in the directory you are currently in.\n".bd.fg(226)
450
450
  @firstrun += "
451
451
  To benefit fully from all the features, you need to install some auxiliary software.\n".fg(230)
452
452
  @firstrun += "
@@ -480,7 +480,7 @@ def display_welcome_message # {{{2
480
480
  For users of ArchLinux and derivatives, install all dependencies available outside of AUR with:
481
481
  sudo pacman -Syu ruby git ncurses xdotool bat pandoc poppler odt2txt docx2txt unzip gnumeric catdoc w3m imagemagick ffmpegthumbnailer
482
482
 
483
- Note: Package names may vary between platforms. The 'libncurses-dev' package is Linux-specific.".b.fg(87)
483
+ Note: Package names may vary between platforms. The 'libncurses-dev' package is Linux-specific.".bd.fg(87)
484
484
  @firstrun += "\n\n
485
485
  You need to install the basic requirements and you should install the viewers before you...
486
486
  ... hit any key to start RTFM. Hit ? inside RTFM to show the full help text. Enjoy :-)\n".fg(214)
@@ -812,7 +812,7 @@ def render_tab_bar # {{{2
812
812
 
813
813
  if i == @current_tab
814
814
  # Active tab with bright background and bold text
815
- tab_display << " #{i+1}:#{display_name} ".bg(226).fg(0).b # Yellow background, black text, bold
815
+ tab_display << " #{i+1}:#{display_name} ".bg(226).fg(0).bd # Yellow background, black text, bold
816
816
  else
817
817
  # Inactive tab with subtle styling
818
818
  tab_display << " #{i+1}:#{display_name} ".fg(244) # Gray text
@@ -1201,7 +1201,7 @@ def show_help # {{{3
1201
1201
  end
1202
1202
 
1203
1203
  def help_info # {{{3
1204
- help_text = "RTFM Help\n".b.fg(156)
1204
+ help_text = "RTFM Help\n".bd.fg(156)
1205
1205
  help_text << "=" * 50 + "\n\n"
1206
1206
 
1207
1207
  # First pass: find the longest key to determine column alignment
@@ -1223,9 +1223,9 @@ def help_info # {{{3
1223
1223
 
1224
1224
  case content
1225
1225
  when /^[A-Z][A-Z \/]+$/ # Section headers like "BASIC KEYS", "GIT/HASH/OPENAI" (no leading spaces)
1226
- help_text << content.b.fg(156) + "\n" # Removed extra newline before
1226
+ help_text << content.bd.fg(156) + "\n" # Removed extra newline before
1227
1227
  when /^ RTFM - Ruby Terminal File Manager/ # Title
1228
- help_text << content.b.fg(154) + "\n"
1228
+ help_text << content.bd.fg(154) + "\n"
1229
1229
  when /^COPYRIGHT:/ # Copyright line (no leading spaces)
1230
1230
  help_text << "\n" + content.fg(242) + "\n"
1231
1231
  when /^ (\S+)\s+=\s+/ # Key lines: " key = description"
@@ -1253,7 +1253,7 @@ end
1253
1253
  def show_version # {{{3
1254
1254
  protocol_info = @termpix ? " [Image protocol: #{@termpix.protocol || 'none'}]" : ""
1255
1255
  version_text = " RTFM version = #{@version}#{protocol_info} (latest RubyGems version is #{Gem.latest_version_for('rtfm-filemanager').version} - https://github.com/isene/RTFM)"
1256
- @pB.say(version_text.b)
1256
+ @pB.say(version_text.bd)
1257
1257
  @pB.update = false # Prevent terminal clearing on next render
1258
1258
  end
1259
1259
 
@@ -1285,20 +1285,20 @@ end
1285
1285
 
1286
1286
  def show_config
1287
1287
  clear_image
1288
- @pR.say('Configuration'.u.fg(254) + ":\n\n" + @conf.fg(249))
1288
+ @pR.say('Configuration'.ul.fg(254) + ":\n\n" + @conf.fg(249))
1289
1289
  end
1290
1290
 
1291
1291
  def plugin_manager # {{{3
1292
1292
  clear_image
1293
1293
  names = @plugins.keys.sort
1294
1294
  if names.empty?
1295
- @pR.say("Plugins".u.fg(254) + "\n\nNo plugins found in ~/.rtfm/plugins/\n\nPlace .rb files there to make them available.")
1295
+ @pR.say("Plugins".ul.fg(254) + "\n\nNo plugins found in ~/.rtfm/plugins/\n\nPlace .rb files there to make them available.")
1296
1296
  return
1297
1297
  end
1298
1298
  sel = 0
1299
1299
  loop do
1300
1300
  lines = []
1301
- lines << "Plugins".b.fg(254)
1301
+ lines << "Plugins".bd.fg(254)
1302
1302
  lines << ""
1303
1303
  names.each_with_index do |name, i|
1304
1304
  p = @plugins[name]
@@ -1306,7 +1306,7 @@ def plugin_manager # {{{3
1306
1306
  key_info = p[:meta][:key].empty? ? '' : " [#{p[:meta][:key]}]".fg(240)
1307
1307
  desc = p[:meta][:description].empty? ? '' : " #{p[:meta][:description]}".fg(249)
1308
1308
  line = "#{status} #{name}#{key_info}#{desc}"
1309
- line = i == sel ? line.u : line
1309
+ line = i == sel ? line.ul : line
1310
1310
  lines << line
1311
1311
  end
1312
1312
  lines << ""
@@ -1329,7 +1329,7 @@ def plugin_manager # {{{3
1329
1329
  help = PLUGIN_HELP[name]
1330
1330
  if help
1331
1331
  @pR.update = true
1332
- @pR.say(name.b.fg(254) + " help\n\n" + help)
1332
+ @pR.say(name.bd.fg(254) + " help\n\n" + help)
1333
1333
  getchr
1334
1334
  else
1335
1335
  @pB.say("No help available for #{name}.")
@@ -2048,7 +2048,7 @@ end
2048
2048
 
2049
2049
  def show_recent_files # {{{3
2050
2050
  clear_image
2051
- text = "Recently Accessed Files and Directories\n".b.fg(156)
2051
+ text = "Recently Accessed Files and Directories\n".bd.fg(156)
2052
2052
  text << "=" * 40 + "\n\n"
2053
2053
 
2054
2054
  unless @recent_files.empty?
@@ -2126,7 +2126,7 @@ def show_file_properties # {{{3
2126
2126
 
2127
2127
  begin
2128
2128
  stat = File.stat(@selected)
2129
- text = "File Properties: #{File.basename(@selected)}\n".b.fg(156)
2129
+ text = "File Properties: #{File.basename(@selected)}\n".bd.fg(156)
2130
2130
  text << "=" * 50 + "\n\n"
2131
2131
 
2132
2132
  # Basic information
@@ -2449,7 +2449,7 @@ def build_pattern_help # {{{3
2449
2449
  end
2450
2450
 
2451
2451
  def show_rename_preview(operations, errors, pattern) # {{{3
2452
- text = "Bulk Rename Preview: #{pattern}\n".b.fg(156)
2452
+ text = "Bulk Rename Preview: #{pattern}\n".bd.fg(156)
2453
2453
  text << "=" * 50 + "\n\n"
2454
2454
 
2455
2455
  unless operations.empty?
@@ -2513,7 +2513,7 @@ def show_file_comparison(file1, file2) # {{{3
2513
2513
  basename1 = File.basename(file1)
2514
2514
  basename2 = File.basename(file2)
2515
2515
 
2516
- header = "File Comparison\n".b.fg(156)
2516
+ header = "File Comparison\n".bd.fg(156)
2517
2517
  header << "=" * 50 + "\n\n"
2518
2518
  header << sprintf("%-25s vs %s\n", basename1.fg(156), basename2.fg(156))
2519
2519
  header << "=" * 50 + "\n\n"
@@ -2530,7 +2530,7 @@ def show_file_comparison(file1, file2) # {{{3
2530
2530
  # Check if files are identical
2531
2531
  if stat1.size == stat2.size && files_identical?(file1, file2)
2532
2532
  header << "\n"
2533
- header << "Files are identical!\n".fg(156).b
2533
+ header << "Files are identical!\n".fg(156).bd
2534
2534
  header << "\nPress any key to close...".fg(240)
2535
2535
  @pR.say(header)
2536
2536
  @pR.update = false
@@ -3119,7 +3119,7 @@ def exit_archive_mode # {{{3
3119
3119
  end
3120
3120
 
3121
3121
  def show_archive_file_info(entry) # {{{3
3122
- info_text = "Archive File Information\n".b.fg(226)
3122
+ info_text = "Archive File Information\n".bd.fg(226)
3123
3123
  info_text << "=" * 40 + "\n\n"
3124
3124
  info_text << "Archive: #{File.basename(@archive_path)}\n".fg(255)
3125
3125
  info_text << "Name: #{entry[:name]}\n".fg(255)
@@ -3190,14 +3190,14 @@ def archive_delete_entries # {{{3
3190
3190
 
3191
3191
  clear_image
3192
3192
  names = entries.map { |e| e[:name] }
3193
- warning = "\nDelete from Archive\n".b.fg(196)
3193
+ warning = "\nDelete from Archive\n".bd.fg(196)
3194
3194
  warning << "=" * 40 + "\n\n"
3195
3195
  warning << "Archive: #{File.basename(@archive_path)}\n".fg(255)
3196
3196
  warning << "\nItems to delete:\n".fg(226)
3197
3197
  entries.first(10).each { |e| warning << " #{e[:full_path]}\n".fg(255) }
3198
3198
  warning << " ... and #{entries.size - 10} more\n".fg(240) if entries.size > 10
3199
- warning << "\nThis modifies the archive file permanently!\n".fg(196).b
3200
- warning << "Press " + "y".fg(156).b + " to confirm, any other key to cancel".fg(249)
3199
+ warning << "\nThis modifies the archive file permanently!\n".fg(196).bd
3200
+ warning << "Press " + "y".fg(156).bd + " to confirm, any other key to cancel".fg(249)
3201
3201
  @pR.say(warning)
3202
3202
  @pB.say(" Delete #{entries.size} item(s) from archive? (y/n)".fg(196))
3203
3203
 
@@ -3250,7 +3250,7 @@ def archive_add_files # {{{3
3250
3250
  end
3251
3251
 
3252
3252
  clear_image
3253
- info = "\nAdd Files to Archive\n".b.fg(226)
3253
+ info = "\nAdd Files to Archive\n".bd.fg(226)
3254
3254
  info << "=" * 40 + "\n\n"
3255
3255
  info << "Archive: #{File.basename(@archive_path)}\n".fg(255)
3256
3256
  target = @archive_current_dir.empty? ? "archive root" : @archive_current_dir
@@ -3258,7 +3258,7 @@ def archive_add_files # {{{3
3258
3258
  info << "\nFiles to add:\n".fg(226)
3259
3259
  files_to_add.first(10).each { |f| info << " #{File.basename(f)}\n".fg(255) }
3260
3260
  info << " ... and #{files_to_add.size - 10} more\n".fg(240) if files_to_add.size > 10
3261
- info << "\nPress " + "y".fg(156).b + " to confirm, any other key to cancel".fg(249)
3261
+ info << "\nPress " + "y".fg(156).bd + " to confirm, any other key to cancel".fg(249)
3262
3262
  @pR.say(info)
3263
3263
  @pB.say(" Add #{files_to_add.size} file(s) to archive? (y/n)".fg(226))
3264
3264
 
@@ -3405,7 +3405,7 @@ def archive_refresh # {{{3
3405
3405
  end
3406
3406
 
3407
3407
  def show_remote_file_info(file) # {{{3
3408
- info_text = "Remote File Information\n".b.fg(156)
3408
+ info_text = "Remote File Information\n".bd.fg(156)
3409
3409
  info_text << "=" * 40 + "\n\n"
3410
3410
 
3411
3411
  info_text << "Name: #{file[:name]}\n".fg(255)
@@ -3966,7 +3966,7 @@ end
3966
3966
 
3967
3967
 
3968
3968
  def build_remote_help # {{{3
3969
- help_text = "Remote Connection Setup\n".b.fg(156)
3969
+ help_text = "Remote Connection Setup\n".bd.fg(156)
3970
3970
  help_text << "=" * 50 + "\n\n"
3971
3971
 
3972
3972
  # Show recent SSH connections if any exist
@@ -4116,19 +4116,19 @@ def delete_items # {{{3
4116
4116
  warning_text = "\n" + "=" * 50 + "\n"
4117
4117
  action = @trash ? 'Move to Trash' : 'PERMANENT DELETE'
4118
4118
  action_color = @trash ? 220 : 196
4119
- warning_text << action.fg(action_color).b + "\n\n"
4119
+ warning_text << action.fg(action_color).bd + "\n\n"
4120
4120
 
4121
4121
  if @trash
4122
4122
  warning_text << "Items will be moved to:\n".fg(249)
4123
4123
  warning_text << " ~/.rtfm/trash/\n".fg(240)
4124
4124
  warning_text << "\nYou can restore them with " + "U".fg(156) + " (undo)\n".fg(249)
4125
4125
  else
4126
- warning_text << "⚠️ WARNING: PERMANENT DELETION!\n".fg(196).b
4126
+ warning_text << "⚠️ WARNING: PERMANENT DELETION!\n".fg(196).bd
4127
4127
  warning_text << "Files will be permanently removed\n".fg(196)
4128
- warning_text << "This action CANNOT be undone!\n".fg(196).b
4128
+ warning_text << "This action CANNOT be undone!\n".fg(196).bd
4129
4129
  end
4130
4130
 
4131
- warning_text << "\n" + "Press " + "y".fg(156).b + " to confirm, any other key to cancel".fg(249)
4131
+ warning_text << "\n" + "Press " + "y".fg(156).bd + " to confirm, any other key to cancel".fg(249)
4132
4132
 
4133
4133
  @pR.text << warning_text
4134
4134
  @pR.refresh
@@ -4265,7 +4265,7 @@ def trash_browser # TRASH BROWSER {{{3
4265
4265
 
4266
4266
  lines = []
4267
4267
  lines << "j/k:move r:restore d:delete E:empty all q:close".fg(240)
4268
- lines << "Trash".b.fg(254) + " (#{items.size} items)".fg(240)
4268
+ lines << "Trash".bd.fg(254) + " (#{items.size} items)".fg(240)
4269
4269
  lines << ""
4270
4270
 
4271
4271
  if items.empty?
@@ -4279,7 +4279,7 @@ def trash_browser # TRASH BROWSER {{{3
4279
4279
  name = item[:orig_name] + type_indicator
4280
4280
  origin = item[:orig_path] ? " #{File.dirname(item[:orig_path])}".fg(240) : ""
4281
4281
  line = "#{size_s.rjust(8).fg(249)} #{age.rjust(6).fg(240)} #{name}#{origin}"
4282
- line = idx == sel ? line.u : line
4282
+ line = idx == sel ? line.ul : line
4283
4283
  lines << line
4284
4284
  end
4285
4285
  lines << "(#{sel + 1}/#{items.size})".fg(240) if items.size > page_h
@@ -4663,7 +4663,7 @@ def git_status # {{{3
4663
4663
 
4664
4664
  # Check if we're in a git repository
4665
4665
  unless Dir.exist?('.git') || system('git rev-parse --git-dir > /dev/null 2>&1')
4666
- @pR.say("Not a Git Repository".b.fg(196) + "\n\n" + "This directory is not under Git version control.".fg(240))
4666
+ @pR.say("Not a Git Repository".bd.fg(196) + "\n\n" + "This directory is not under Git version control.".fg(240))
4667
4667
  @pR.update = false
4668
4668
  @pB.update = true
4669
4669
  return
@@ -4680,7 +4680,7 @@ def git_status # {{{3
4680
4680
  commit_out, commit_err = command('git log --oneline -n 5 2>/dev/null || echo "No commits"', return_both: true)
4681
4681
 
4682
4682
  # Build formatted output
4683
- info = "Git Status".b.fg(156) + "\n"
4683
+ info = "Git Status".bd.fg(156) + "\n"
4684
4684
  info << "=" * 50 + "\n\n"
4685
4685
 
4686
4686
  # Show errors if any
@@ -4695,7 +4695,7 @@ def git_status # {{{3
4695
4695
  if current_branch.empty?
4696
4696
  info << "Branch: ".fg(226) + "Not on any branch".fg(240) + "\n\n"
4697
4697
  else
4698
- info << "Branch: ".fg(226) + current_branch.fg(156).b + "\n\n"
4698
+ info << "Branch: ".fg(226) + current_branch.fg(156).bd + "\n\n"
4699
4699
  end
4700
4700
 
4701
4701
  # Parse and categorize changes
@@ -4997,12 +4997,12 @@ end
4997
4997
  # SYSTEM SHORTCUTS {{{2
4998
4998
  def system_info # {{{3
4999
4999
  clear_image
5000
- text = "SYSTEM INFORMATION".b.fg(156) + " - " + Time.now.strftime("%Y-%m-%d %H:%M:%S").fg(249) + "\n"
5000
+ text = "SYSTEM INFORMATION".bd.fg(156) + " - " + Time.now.strftime("%Y-%m-%d %H:%M:%S").fg(249) + "\n"
5001
5001
  text << "=" * 50 + "\n\n"
5002
5002
 
5003
5003
  begin
5004
5004
  # System Overview
5005
- text << "System Overview".fg(226).b + "\n"
5005
+ text << "System Overview".fg(226).bd + "\n"
5006
5006
  text << "─" * 20 + "\n"
5007
5007
 
5008
5008
  # Hostname and uptime
@@ -5028,7 +5028,7 @@ def system_info # {{{3
5028
5028
 
5029
5029
  begin
5030
5030
  # Hardware Information
5031
- text << "Hardware".fg(226).b + "\n"
5031
+ text << "Hardware".fg(226).bd + "\n"
5032
5032
  text << "─" * 20 + "\n"
5033
5033
 
5034
5034
  # CPU Info
@@ -5061,7 +5061,7 @@ def system_info # {{{3
5061
5061
 
5062
5062
  begin
5063
5063
  # Memory Information with visual bar
5064
- text << "Memory".fg(226).b + "\n"
5064
+ text << "Memory".fg(226).bd + "\n"
5065
5065
  text << "─" * 20 + "\n"
5066
5066
 
5067
5067
  mem_info = `free -b 2>/dev/null | grep Mem:`
@@ -5107,7 +5107,7 @@ def system_info # {{{3
5107
5107
 
5108
5108
  begin
5109
5109
  # Storage Information with visual bars
5110
- text << "Storage".fg(226).b + "\n"
5110
+ text << "Storage".fg(226).bd + "\n"
5111
5111
  text << "─" * 20 + "\n"
5112
5112
 
5113
5113
  # Get disk usage for main filesystems only
@@ -5149,7 +5149,7 @@ def system_info # {{{3
5149
5149
 
5150
5150
  begin
5151
5151
  # Network Information
5152
- text << "Network".fg(226).b + "\n"
5152
+ text << "Network".fg(226).bd + "\n"
5153
5153
  text << "─" * 20 + "\n"
5154
5154
 
5155
5155
  # Get active network interfaces
@@ -5190,7 +5190,7 @@ def system_info # {{{3
5190
5190
 
5191
5191
  begin
5192
5192
  # Environment Information
5193
- text << "Environment".fg(226).b + "\n"
5193
+ text << "Environment".fg(226).bd + "\n"
5194
5194
  text << "─" * 20 + "\n"
5195
5195
 
5196
5196
  # Shell and terminal
@@ -5227,7 +5227,7 @@ def system_info # {{{3
5227
5227
 
5228
5228
  begin
5229
5229
  # Services & Processes
5230
- text << "Services & Processes".fg(226).b + "\n"
5230
+ text << "Services & Processes".fg(226).bd + "\n"
5231
5231
  text << "─" * 20 + "\n"
5232
5232
 
5233
5233
  # Running services count
@@ -5405,7 +5405,7 @@ end
5405
5405
 
5406
5406
  def show_ssh_history # {{{3
5407
5407
  clear_image
5408
- history_text = "SSH Connection History\n".b.fg(156)
5408
+ history_text = "SSH Connection History\n".bd.fg(156)
5409
5409
  history_text << "=" * 50 + "\n\n"
5410
5410
 
5411
5411
  if @pSsh.history.empty?
@@ -5589,11 +5589,11 @@ def dirlist_archive # {{{2
5589
5589
  n = n.inject('/', -1) if entry[:type] == 'directory'
5590
5590
  n = n.bg(238) if search_regex && name.match(search_regex)
5591
5591
  tag_key = "#{@archive_path}:#{entry[:full_path]}"
5592
- n = n.r if @tagged.include?(tag_key)
5592
+ n = n.rv if @tagged.include?(tag_key)
5593
5593
  n = n.shorten(width - 5).inject('...', -1) if name.length > width - 6
5594
5594
 
5595
5595
  if i == current_index
5596
- n = '→ ' + n.u.bg(58) # Yellow-green background for archive mode selection
5596
+ n = '→ ' + n.ul.bg(58) # Yellow-green background for archive mode selection
5597
5597
  else
5598
5598
  n = ' ' + n.bg(58) # Yellow-green background for archive mode
5599
5599
  end
@@ -5670,7 +5670,7 @@ def dirlist_remote # {{{2
5670
5670
 
5671
5671
  # Add selection indicator and remote mode indicator (red background)
5672
5672
  if i == current_index
5673
- n = '→ ' + n.u.bg(52) # Red background for remote mode selection
5673
+ n = '→ ' + n.ul.bg(52) # Red background for remote mode selection
5674
5674
  else
5675
5675
  n = ' ' + n.bg(52) # Red background for remote mode
5676
5676
  end
@@ -5782,11 +5782,11 @@ def dirlist(left: true, directory: nil) # LIST DIRECTORIES {{{2
5782
5782
  n = n.inject('@', -1) if is_symlink
5783
5783
  n = n.inject('/', -1) if is_directory
5784
5784
  n = n.bg(238) if search_regex && raw_name.match(search_regex)
5785
- n = n.r if @tagged.include?(fullpath)
5785
+ n = n.rv if @tagged.include?(fullpath)
5786
5786
 
5787
5787
  if left
5788
5788
  if i == current_index
5789
- n = '→ ' + n.u # Default terminal color
5789
+ n = '→ ' + n.ul # Default terminal color
5790
5790
  else
5791
5791
  n = ' ' + n
5792
5792
  end
@@ -6011,10 +6011,10 @@ def render # RENDER ALL PANES {{{2
6011
6011
  if @pB.update
6012
6012
  bottomtext = @pB.text
6013
6013
  info = ': for command (use @s for selected item, @t for tagged items) - press ? for help'
6014
- info = " Showing only files matching '#{@lsmatch}'".fg(130).u if @lsmatch != ''
6015
- info = " Showing only file type '#{@lsfiles}'".fg(129).u if @lsfiles != ''
6016
- info = " Showing only file types '#{@lsfiles}'".fg(129).u if @lsfiles =~ /,/
6017
- info += " and only files matching '#{@lsmatch}'".fg(129).u if @lsfiles != '' && @lsmatch != ''
6014
+ info = " Showing only files matching '#{@lsmatch}'".fg(130).ul if @lsmatch != ''
6015
+ info = " Showing only file type '#{@lsfiles}'".fg(129).ul if @lsfiles != ''
6016
+ info = " Showing only file types '#{@lsfiles}'".fg(129).ul if @lsfiles =~ /,/
6017
+ info += " and only files matching '#{@lsmatch}'".fg(129).ul if @lsfiles != '' && @lsmatch != ''
6018
6018
  @pB.text = info
6019
6019
  # Ensure screen output is complete before continuing
6020
6020
  if @pB.text != bottomtext
@@ -6933,7 +6933,7 @@ end
6933
6933
  def marks_info # SHOW MARKS IN RIGHT WINDOW {{{2
6934
6934
  clear_image
6935
6935
  @marks = @marks.sort.to_h
6936
- info = "Directory Marks".b.fg(156) + "\n"
6936
+ info = "Directory Marks".bd.fg(156) + "\n"
6937
6937
  info << "=" * 50 + "\n\n"
6938
6938
 
6939
6939
  if @marks.empty?
@@ -6952,7 +6952,7 @@ def marks_info # SHOW MARKS IN RIGHT WINDOW {{{2
6952
6952
 
6953
6953
  # Truncate long paths for better display
6954
6954
  display_dir = dir.length > 45 ? "..." + dir[-42..-1] : dir
6955
- info << sprintf(" %s → %s\n", mark.fg(mark_color).b, display_dir.fg(249))
6955
+ info << sprintf(" %s → %s\n", mark.fg(mark_color).bd, display_dir.fg(249))
6956
6956
 
6957
6957
  # Add spacing after special marks
6958
6958
  info << "\n" if mark == "'"
@@ -6966,7 +6966,7 @@ end
6966
6966
 
6967
6967
  def tagged_info # SHOW THE LIST OF TAGGED ITEMS IN @pR {{{2
6968
6968
  clear_image
6969
- info = "Tagged Items".b.fg(204) + "\n"
6969
+ info = "Tagged Items".bd.fg(204) + "\n"
6970
6970
  info << "=" * 50 + "\n\n"
6971
6971
 
6972
6972
  # Summary information
@@ -7000,7 +7000,7 @@ def tagged_info # SHOW THE LIST OF TAGGED ITEMS IN @pR {{{2
7000
7000
  info << "\n" + "Currently selected:\n".fg(226)
7001
7001
  selected_name = File.basename(@selected)
7002
7002
  selected_color = File.directory?(@selected) ? 156 : 249
7003
- info << " \u2192 " + selected_name.fg(selected_color).b + "\n"
7003
+ info << " \u2192 " + selected_name.fg(selected_color).bd + "\n"
7004
7004
  if @selected.length > 50
7005
7005
  info << " " + @selected.fg(240) + "\n"
7006
7006
  end
@@ -11,7 +11,7 @@ PLUGIN_HELP['Bookmarks'] = <<~HELP
11
11
 
12
12
  Press F6 to open the bookmark manager.
13
13
 
14
- #{"Commands:".b}
14
+ #{"Commands:".bd}
15
15
  a Add current directory to bookmarks
16
16
  d Delete selected bookmark
17
17
  j/k Navigate up/down
@@ -19,7 +19,7 @@ PLUGIN_HELP['Bookmarks'] = <<~HELP
19
19
  / Filter bookmarks (fuzzy search)
20
20
  q/ESC Close
21
21
 
22
- #{"Difference from marks:".b}
22
+ #{"Difference from marks:".bd}
23
23
  Marks (m/') are single-letter slots (a-z) that
24
24
  save a directory path for quick recall. You get
25
25
  26 slots max, and must remember which letter
@@ -51,7 +51,7 @@ def bookmark_menu
51
51
  visible = filter ? bookmarks.select { |b| b.downcase.include?(filter.downcase) } : bookmarks
52
52
 
53
53
  lines = []
54
- lines << "Bookmarks".b.fg(254)
54
+ lines << "Bookmarks".bd.fg(254)
55
55
  lines << "filter: #{filter}".fg(240) if filter
56
56
  lines << ""
57
57
 
@@ -74,15 +74,15 @@ def bookmark_menu
74
74
  prefix = common.empty? ? "" : path[0, common.length].fg(240)
75
75
  suffix = common.empty? ? path.fg(112) : path[common.length..].fg(112)
76
76
  line = "#{idx.to_s.rjust(2).fg(240)} #{prefix}#{suffix}"
77
- line = i == sel ? line.u : line
77
+ line = i == sel ? line.ul : line
78
78
  lines << line
79
79
  end
80
80
  end
81
81
 
82
82
  lines << ""
83
- lines << "a".b.fg(112) + ":add " + "d".b.fg(112) + ":del " +
84
- "/".b.fg(112) + ":filter " + "ENTER".b.fg(112) + ":jump " +
85
- "q".b.fg(112) + ":close"
83
+ lines << "a".bd.fg(112) + ":add " + "d".bd.fg(112) + ":del " +
84
+ "/".bd.fg(112) + ":filter " + "ENTER".bd.fg(112) + ":jump " +
85
+ "q".bd.fg(112) + ":close"
86
86
 
87
87
  @pR.update = true
88
88
  @pR.say(lines.join("\n"))
@@ -9,11 +9,11 @@ PLUGIN_HELP['Disk Usage'] = <<~HELP
9
9
 
10
10
  Press S to open the system/disk usage menu.
11
11
 
12
- #{"Menu:".b}
12
+ #{"Menu:".bd}
13
13
  s Show system info (original S behavior)
14
14
  d Open disk usage analyzer
15
15
 
16
- #{"Disk Usage Analyzer:".b}
16
+ #{"Disk Usage Analyzer:".bd}
17
17
  j/k Navigate up/down
18
18
  ENTER Drill into selected directory
19
19
  LEFT/h Go up to parent directory
@@ -29,10 +29,10 @@ def diskusage_menu
29
29
  clear_image
30
30
 
31
31
  lines = []
32
- lines << "System / Disk Usage".b.fg(254)
32
+ lines << "System / Disk Usage".bd.fg(254)
33
33
  lines << ""
34
- lines << "s".b.fg(112) + " System info"
35
- lines << "d".b.fg(112) + " Disk usage analyzer"
34
+ lines << "s".bd.fg(112) + " System info"
35
+ lines << "d".bd.fg(112) + " Disk usage analyzer"
36
36
  lines << ""
37
37
  lines << "q/ESC: close".fg(240)
38
38
 
@@ -77,7 +77,7 @@ def diskusage_browse(start_dir)
77
77
  visible = entries[offset, page_h] || []
78
78
 
79
79
  lines = []
80
- lines << "Disk Usage".b.fg(254) + " " + browse_dir.fg(240)
80
+ lines << "Disk Usage".bd.fg(254) + " " + browse_dir.fg(240)
81
81
  lines << ("Total: " + diskusage_human(total)).fg(249)
82
82
  lines << ""
83
83
 
@@ -98,7 +98,7 @@ def diskusage_browse(start_dir)
98
98
  line = bar.fg(entry[:dir] ? 69 : 243) + " " +
99
99
  size_str.fg(156) + " " +
100
100
  name.fg(name_color)
101
- line = idx == sel ? line.u : line
101
+ line = idx == sel ? line.ul : line
102
102
  lines << line
103
103
  end
104
104
 
data/examples/dupes.rb CHANGED
@@ -13,13 +13,13 @@ PLUGIN_HELP['Dupes'] = <<~HELP
13
13
  Press F7 to scan the current directory for files
14
14
  that share identical content.
15
15
 
16
- #{"Scanning:".b}
16
+ #{"Scanning:".bd}
17
17
  Files are first grouped by size, then only
18
18
  same-size files are hashed (SHA256) to confirm
19
19
  duplicates. Press 'r' at the start prompt to
20
20
  scan recursively.
21
21
 
22
- #{"Navigation:".b}
22
+ #{"Navigation:".bd}
23
23
  j/k Move between duplicate groups
24
24
  PgDn/PgUp Jump 10 groups
25
25
  LEFT/RIGHT Move between files in a group
@@ -27,12 +27,12 @@ PLUGIN_HELP['Dupes'] = <<~HELP
27
27
  d Delete all untagged files in group
28
28
  q/ESC Close
29
29
 
30
- #{"Deletion:".b}
30
+ #{"Deletion:".bd}
31
31
  If trash mode is enabled, deleted files are
32
32
  moved to the trash and can be undone. Otherwise
33
33
  files are permanently removed.
34
34
 
35
- #{"Display:".b}
35
+ #{"Display:".bd}
36
36
  Groups are sorted by wasted space (largest
37
37
  first). Each group shows a partial hash, file
38
38
  size, and the list of duplicate paths.
@@ -184,18 +184,18 @@ def find_dupes
184
184
 
185
185
  lines = []
186
186
  lines << "j/k:group LEFT/RIGHT:file t:keep d:delete untagged q:close".fg(240)
187
- lines << "Duplicate Files".b.fg(254) + " (#{group_idx + 1}/#{dupes.size} groups, #{format_bytes(wasted_total)} wasted)".fg(240)
187
+ lines << "Duplicate Files".bd.fg(254) + " (#{group_idx + 1}/#{dupes.size} groups, #{format_bytes(wasted_total)} wasted)".fg(240)
188
188
  lines << ""
189
189
 
190
190
  header = "#{format_bytes(meta[:size])} x#{group.size} (#{format_bytes(meta[:waste])} wasted)"
191
- lines << header.b.fg(112)
191
+ lines << header.bd.fg(112)
192
192
 
193
193
  group.each_with_index do |f, fi|
194
194
  rel = f.start_with?(Dir.pwd + '/') ? f.sub(Dir.pwd + '/', '') : f
195
195
  is_kept = kept[group_idx].include?(fi)
196
196
  marker = is_kept ? " KEEP ".bg(22).fg(255) : " "
197
197
  label = "#{marker} #{rel}"
198
- label = fi == file_idx ? label.u.fg(254) : label.fg(250)
198
+ label = fi == file_idx ? label.ul.fg(254) : label.fg(250)
199
199
  lines << label
200
200
  end
201
201
 
data/examples/git.rb CHANGED
@@ -9,7 +9,7 @@ PLUGIN_HELP['Git'] = <<~HELP
9
9
 
10
10
  Press Ctrl-G to open the git menu.
11
11
 
12
- #{"Commands:".b}
12
+ #{"Commands:".bd}
13
13
  s Show git status
14
14
  d Show git diff
15
15
  c Stage all, commit (prompts for message), push
@@ -26,12 +26,12 @@ def git_menu
26
26
 
27
27
  loop do
28
28
  lines = []
29
- lines << "Git".b.fg(254)
29
+ lines << "Git".bd.fg(254)
30
30
  lines << ""
31
- lines << "s".b.fg(112) + " git status"
32
- lines << "d".b.fg(112) + " git diff"
33
- lines << "c".b.fg(112) + " git add + commit + push"
34
- lines << "l".b.fg(112) + " git log (last 20)"
31
+ lines << "s".bd.fg(112) + " git status"
32
+ lines << "d".bd.fg(112) + " git diff"
33
+ lines << "c".bd.fg(112) + " git add + commit + push"
34
+ lines << "l".bd.fg(112) + " git log (last 20)"
35
35
  lines << ""
36
36
  lines << "q/ESC: close".fg(240)
37
37
 
@@ -43,12 +43,12 @@ def git_menu
43
43
  when 's'
44
44
  output = command("git status 2>&1")
45
45
  @pR.update = true
46
- @pR.say("git status".b.fg(254) + "\n\n" + output)
46
+ @pR.say("git status".bd.fg(254) + "\n\n" + output)
47
47
  when 'd'
48
48
  output = command("git diff 2>&1")
49
49
  output = "No changes." if output.strip.empty?
50
50
  @pR.update = true
51
- @pR.say("git diff".b.fg(254) + "\n\n" + output)
51
+ @pR.say("git diff".bd.fg(254) + "\n\n" + output)
52
52
  when 'c'
53
53
  message = @pCmd.ask('Commit message: ', '')
54
54
  if message.strip.empty?
@@ -61,7 +61,7 @@ def git_menu
61
61
  when 'l'
62
62
  output = command("git log --oneline -20 2>&1")
63
63
  @pR.update = true
64
- @pR.say("git log".b.fg(254) + "\n\n" + output)
64
+ @pR.say("git log".bd.fg(254) + "\n\n" + output)
65
65
  when 'q', 'ESC'
66
66
  break
67
67
  end
data/examples/notes.rb CHANGED
@@ -15,17 +15,17 @@ PLUGIN_HELP['Notes'] = <<~HELP
15
15
  Press F5 on any selected item to view, create,
16
16
  edit, or delete its note.
17
17
 
18
- #{"How it works:".b}
18
+ #{"How it works:".bd}
19
19
  If no note exists, you're prompted to create one.
20
20
  If a note exists, it shows in the right pane
21
21
  with options to edit or delete.
22
22
 
23
- #{"Commands (when viewing a note):".b}
23
+ #{"Commands (when viewing a note):".bd}
24
24
  e Edit the note
25
25
  d Delete the note
26
26
  q Close
27
27
 
28
- #{"Difference from marks:".b}
28
+ #{"Difference from marks:".bd}
29
29
  Marks (m/') are single-letter bookmarks for
30
30
  quick directory jumping. Notes are free-text
31
31
  annotations attached to specific files or
@@ -49,13 +49,13 @@ def toggle_note
49
49
  note = File.read(npath)
50
50
  loop do
51
51
  lines = []
52
- lines << "Note for:".b.fg(254)
52
+ lines << "Note for:".bd.fg(254)
53
53
  lines << File.basename(file).fg(112)
54
54
  lines << ""
55
55
  lines << note
56
56
  lines << ""
57
- lines << "e".b.fg(112) + " edit note"
58
- lines << "d".b.fg(112) + " delete note"
57
+ lines << "e".bd.fg(112) + " edit note"
58
+ lines << "d".bd.fg(112) + " delete note"
59
59
  lines << "q/ESC: close".fg(240)
60
60
 
61
61
  @pR.update = true
data/examples/opener.rb CHANGED
@@ -13,7 +13,7 @@ PLUGIN_HELP['Opener'] = <<~HELP
13
13
  a list of custom openers before using the default
14
14
  open behavior.
15
15
 
16
- #{"Configuration:".b}
16
+ #{"Configuration:".bd}
17
17
  Edit the CUSTOM_OPENERS hash in the plugin file
18
18
  (~/.rtfm/plugins/opener.rb):
19
19
 
@@ -25,7 +25,7 @@ PLUGIN_HELP['Opener'] = <<~HELP
25
25
 
26
26
  Use %f as placeholder for the file path.
27
27
 
28
- #{"How it works:".b}
28
+ #{"How it works:".bd}
29
29
  When you press RIGHT or l on a file, the plugin
30
30
  checks if its extension matches any entry in
31
31
  CUSTOM_OPENERS. If yes, it launches that program
data/examples/settings.rb CHANGED
@@ -10,14 +10,14 @@ PLUGIN_HELP['Settings'] = <<~HELP
10
10
 
11
11
  Overrides the default 'C' (show config) key.
12
12
 
13
- #{"Navigation:".b}
13
+ #{"Navigation:".bd}
14
14
  j/k or UP/DOWN Navigate settings
15
15
  LEFT/RIGHT Toggle booleans, adjust colors +-1
16
16
  H/L Adjust colors +-10
17
17
  ENTER Edit text fields or type color number
18
18
  q/ESC Save and close
19
19
 
20
- #{"Settings included:".b}
20
+ #{"Settings included:".bd}
21
21
  Trash mode, run-mailcap, interactive programs,
22
22
  custom ls flags, OpenAI key/model, and all
23
23
  pane colors (top, bottom, search, command,
@@ -54,7 +54,7 @@ def show_settings
54
54
  loop do
55
55
  # Build display
56
56
  lines = []
57
- lines << "Settings".b.fg(254)
57
+ lines << "Settings".bd.fg(254)
58
58
  lines << ""
59
59
 
60
60
  settings.each_with_index do |(label, var, type, _opts), i|
@@ -73,7 +73,7 @@ def show_settings
73
73
 
74
74
  pad = label_w - label.length
75
75
  line = "#{label}#{' ' * pad}#{display}"
76
- line = i == sel ? line.u : line
76
+ line = i == sel ? line.ul : line
77
77
  lines << line
78
78
  end
79
79
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rtfm-filemanager
3
3
  version: !ruby/object:Gem::Version
4
- version: 8.2.4
4
+ version: 8.2.5
5
5
  platform: ruby
6
6
  authors:
7
7
  - Geir Isene
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2026-03-28 00:00:00.000000000 Z
11
+ date: 2026-04-11 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rcurses
@@ -16,14 +16,14 @@ dependencies:
16
16
  requirements:
17
17
  - - "~>"
18
18
  - !ruby/object:Gem::Version
19
- version: '6.0'
19
+ version: '7.0'
20
20
  type: :runtime
21
21
  prerelease: false
22
22
  version_requirements: !ruby/object:Gem::Requirement
23
23
  requirements:
24
24
  - - "~>"
25
25
  - !ruby/object:Gem::Version
26
- version: '6.0'
26
+ version: '7.0'
27
27
  - !ruby/object:Gem::Dependency
28
28
  name: termpix
29
29
  requirement: !ruby/object:Gem::Requirement