rfd 0.2.0 → 0.3.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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 433838cecd4fd367a1820347e5e6914cf4baf3a9
4
- data.tar.gz: d92980f79fc3a0bd3a553f10360d061d054dfc0f
3
+ metadata.gz: bfede93c56a43d3df90257d60df31b8934b6891f
4
+ data.tar.gz: d5187481f8cb6076394a4337ae85a1799120f2a6
5
5
  SHA512:
6
- metadata.gz: ac5d0d885e4d5c26c431711072be5bd878a876c2be73999a3e0cc9638f3cfb7d109c5cd091d8032c5fb803f7f3b064c2ed15642e3df813fc0e32fc8055714738
7
- data.tar.gz: cd1051af5fa5fdc53978193962f2ca25d95163cbc870b6fea55c0cadb3905c47407af90f075e5ac9370891ef648a6c18ff95a31bfcc6fc423a54faa00d93e763
6
+ metadata.gz: 427efc2d0a2a5e6fba9e4ad7de07dc791b335e6b59ca0f21c62dd3760999816d338f58cd233eddcc80c8849232302808911d447878b3cd1824765e872cba5044
7
+ data.tar.gz: 4f41128bcd148e16149a4ce40ea1485be8e11b989bcb280a69e31074088e50865488097434ecfaa0daf623218df09723454ee5789f9132c56a4740d69f632105
data/README.md CHANGED
@@ -16,15 +16,140 @@ rfd is a terminal based File explorer, inpsired by the legendary freesoft MS-DOS
16
16
 
17
17
  Mac OS X Mountain Lion, Mac OS X Lion
18
18
 
19
- ## Usage
19
+ ## Screenshot
20
+
21
+ ![screenshot](https://www.evernote.com/shard/s20/sh/0bec8345-46c6-45f9-989b-c979b060f5a6/1cffd4c54b30204426251d8561c084a2/res/659f4073-10cc-48f5-a3d2-eb5fe54fba45/skitch.png?resizeSmall&width=768)
22
+
23
+ ## Start Me Up
20
24
 
21
25
  Open up your terminal and type in:
22
26
 
23
27
  % rfd
24
28
 
25
- You can command rfd by pressing some chars on your keyboard, just like Vim.
29
+ You can also pass in a starting directory name, which is defaulted to `.`.
30
+
31
+ % rfd ~/src/rails
32
+
33
+ ## Commands
34
+
35
+ You can command rfd by pressing some chars on your keyboard, just like Vim. If you're totally unfamiliar with this sort of command system, I recommend you to play with `vimtutor` before you go any further.
36
+
37
+ All available commands in rfd are defined as Ruby methods here. https://github.com/amatsuda/rfd/tree/master/lib/rfd/commands.rb
38
+
39
+ ### Changing the current directory
40
+
41
+ * **\<Enter\>**: cd into the directory where the cursor is on.
42
+ * **\<Delete\>** (or \<Backspace\> on you keyboard, probably?): Go up to the upper directory (cd ..).
43
+ * **-**: Get back to where you once belonged (popd).
44
+
45
+ ### Moving the cursor
46
+
47
+ * **j**: Move downward.
48
+ * **k**: Move upward.
49
+ * **h**: Move to the left column. At the left end column, move to the right end column at the previous page.
50
+ * **l**: Move to the right column. At the right end column, move to the left end column at the next page.
51
+
52
+ ### The {count} parameter
53
+
54
+ Some commands such as `j` or `k` take a number parameter called {count}. For passing a {count} parameter, just type in a number prior to the command.
55
+ For example, `3j` moves the cursor to 3 lines below, and `999k` will take your cursor to 999 lines above.
56
+
57
+ ### Jumping the cursor
58
+
59
+ * **H**: Move to the top of the current page.
60
+ * **M**: Move to the middle of the current page.
61
+ * **L**: Move to the bottom of the current page.
62
+
63
+ ### Switching the page
64
+
65
+ * **ctrl-n, ctrl-f**: Move to the top of the next page.
66
+ * **ctrl-p, ctrl-b**: Move to the top of the previous page.
67
+ * **g**: Move to the top of the first page.
68
+ * **G**: Move to the bottom of the last page.
69
+
70
+ ### Finding a file / directory
71
+
72
+ You can find a file by typing the first letter of it immediately after the find commands.
73
+
74
+ * **f{char}**: Move to the next file / directory of which name starts with the given char.
75
+ * **F{char}**: Move to the previous file / directory of which name starts with the given char.
76
+ * **n**: Repeat the last `f` or `F`.
77
+
78
+ ### Searching, sorting
79
+
80
+ For commands like these that require a parameter string, type the parameter in the command line at the bottom of the screen, and press \<Enter\>.
81
+
82
+ * **/**: Grep the current directory with the given parameter. The parameter will be interpreted as Ruby Regexp (e.g. `.*\.rb$`).
83
+ * **s**: Sort files / directories in the current directory in the given order.
84
+ * (none): by name
85
+ * r : reverse order by name
86
+ * s, S : order by file size
87
+ * sr, Sr: reverse order by file size
88
+ * t : order by mtime
89
+ * tr : reverse order by mtime
90
+ * c : order by ctime
91
+ * cr : reverse order by ctime
92
+ * u : order by atime
93
+ * ur : reverse order by atime
94
+ * e : order by extname
95
+ * er : reverse order by extname
96
+
97
+ ### Marking files / directories
98
+
99
+ You can send a command to the file / directory on which the cursor is on. Or, you can send a command to multiple files / directories at once by marking them first.
100
+ The mark is drawn as a `*` char on the left of each file / directory name.
101
+
102
+ * **\<Space\>**: Mark / unmark current file / directory.
103
+ * **ctrl-a**: Mark / unmark all file / directories in the current directory.
104
+
105
+ ### Manipulating files / directories
106
+
107
+ As stated above, you can send a command to one or more files / directories. In this document, the term "selected items" means "(the marked files / directories) || (the file / directory on which the cursor is on)".
108
+
109
+ * **c**: Copy selected items (cp).
110
+ * **m**: Move selected items (mv).
111
+ * **d**: Move selected items into the Trash.
112
+ * **D**: Delete selected items.
113
+ * **r**: Rename selected items.
114
+
115
+ ### Creating files / directories
116
+
117
+ * **t**: Create a new file (touch).
118
+ * **K**: Creat a new directory (mkdir).
119
+ * **S**: Create new symlink to the current file / directory (ln -s).
120
+
121
+ ### Attributes
122
+
123
+ * **a**: Change permission of selected items (chmod).
124
+ * **w**: Change the owner of of selected items (chown).
125
+
126
+ ### Viewing, Editing, Opening
127
+
128
+ * **\<Enter\>**: View current file with the system $VIEWER such as `less`.
129
+ * **v**: View current file with the system $VIEWER such as `less`.
130
+ * **e**: Edit current file with the system $EDITOR such as `vim`.
131
+ * **o**: Send the `open` command.
132
+
133
+ ### Manipulating archives
134
+
135
+ * **u**: Unarchive .zip, .gz, or .tar.gz file into the current directory.
136
+ * **z**: Archive selected items into a .zip file with the given name.
137
+
138
+ ### Handling .zip files
139
+
140
+ You can `cd` into a .zip file as if it's just a directory, then unarchive selected items, view files in it, and even create new files or edit files in the archive.
141
+
142
+ ### Splitting columns
143
+
144
+ * **ctrl-w**: Change the window split size to the {count} value (e.g. `4<C-w>` to split the window into 4 columns). The default number of columns is 2.
145
+
146
+ ### Misc
26
147
 
27
- All available commands are defined here. https://github.com/amatsuda/rfd/tree/master/lib/rfd/commands.rb
148
+ * **ctrl-l**: Refresh the whole screen.
149
+ * **C**: Copy selected items' paths to the clipboard.
150
+ * **O**: Open a new terminal window at the current directory.
151
+ * **!**: Execute a shell command.
152
+ * **q**: Quit the app.
28
153
 
29
154
  ## Contributing
30
155
 
data/lib/rfd.rb CHANGED
@@ -171,23 +171,15 @@ module Rfd
171
171
 
172
172
  # Change the current directory.
173
173
  def cd(dir, pushd: true)
174
- if dir.is_a?(Item) && dir.zip?
175
- cd_into_zip dir
174
+ dir = load_item expand_path(dir) unless dir.is_a? Item
175
+ unless dir.zip?
176
+ Dir.chdir dir
177
+ @current_zip = nil
176
178
  else
177
- target = expand_path dir
178
- if File.readable? target
179
- Dir.chdir target
180
- @dir_history << current_dir if current_dir && pushd
181
- @current_dir, @current_page, @current_row, @current_zip = target, 0, nil, nil
182
- main.activate_pane 0
183
- end
179
+ @current_zip = dir
184
180
  end
185
- end
186
-
187
- def cd_into_zip(zipfile)
188
- @current_zip = zipfile
189
- @dir_history << current_dir if current_dir
190
- @current_dir, @current_page, @current_row = zipfile.path, 0, nil
181
+ @dir_history << current_dir if current_dir && pushd
182
+ @current_dir, @current_page, @current_row = dir, 0, nil
191
183
  main.activate_pane 0
192
184
  end
193
185
 
@@ -266,7 +258,7 @@ module Rfd
266
258
  def fetch_items_from_filesystem_or_zip
267
259
  unless in_zip?
268
260
  @items = Dir.foreach(current_dir).map {|fn|
269
- stat = File.lstat File.join(current_dir, fn)
261
+ stat = File.lstat current_dir.join(fn)
270
262
  Item.new dir: current_dir, name: fn, stat: stat, window_width: maxx
271
263
  }.to_a
272
264
  else
@@ -311,7 +303,7 @@ module Rfd
311
303
  # Update the main window with the loaded files and directories. Also update the header.
312
304
  def draw_items
313
305
  main.draw_items_to_each_pane (@displayed_items = items[current_page * max_items, max_items])
314
- header_l.draw_path_and_page_number path: current_dir, current: current_page + 1, total: total_pages
306
+ header_l.draw_path_and_page_number path: current_dir.path, current: current_page + 1, total: total_pages
315
307
  end
316
308
 
317
309
  # Sort the loaded files and directories in already given sort order.
@@ -367,11 +359,11 @@ module Rfd
367
359
  # Copy selected files and directories to the destination.
368
360
  def cp(dest)
369
361
  unless in_zip?
370
- src = (m = marked_items).any? ? m.map(&:path) : current_item.path
362
+ src = (m = marked_items).any? ? m.map(&:path) : current_item
371
363
  FileUtils.cp_r src, expand_path(dest)
372
364
  else
373
365
  raise 'cping multiple items in .zip is not supported.' if selected_items.size > 1
374
- Zip::File.open(current_zip.path) do |zip|
366
+ Zip::File.open(current_zip) do |zip|
375
367
  entry = zip.find_entry(selected_items.first.name).dup
376
368
  entry.name, entry.name_length = dest, dest.size
377
369
  zip.instance_variable_get(:@entry_set) << entry
@@ -383,7 +375,7 @@ module Rfd
383
375
  # Move selected files and directories to the destination.
384
376
  def mv(dest)
385
377
  unless in_zip?
386
- src = (m = marked_items).any? ? m.map(&:path) : current_item.path
378
+ src = (m = marked_items).any? ? m.map(&:path) : current_item
387
379
  FileUtils.mv src, expand_path(dest)
388
380
  else
389
381
  raise 'mving multiple items in .zip is not supported.' if selected_items.size > 1
@@ -402,10 +394,10 @@ module Rfd
402
394
  unless in_zip?
403
395
  selected_items.each do |item|
404
396
  name = item.name.gsub from, to
405
- FileUtils.mv item.path, File.join(current_dir, name)
397
+ FileUtils.mv item, current_dir.join(name) if item.name != name
406
398
  end
407
399
  else
408
- Zip::File.open(current_zip.path) do |zip|
400
+ Zip::File.open(current_zip) do |zip|
409
401
  selected_items.each do |item|
410
402
  name = item.name.gsub from, to
411
403
  zip.rename item.name, name
@@ -439,7 +431,7 @@ module Rfd
439
431
  unless in_zip?
440
432
  FileUtils.rm_rf selected_items.map(&:path)
441
433
  else
442
- Zip::File.open(current_zip.path) do |zip|
434
+ Zip::File.open(current_zip) do |zip|
443
435
  zip.select {|e| selected_items.map(&:name).include? e.to_s}.each do |entry|
444
436
  if entry.name_is_directory?
445
437
  zip.dir.delete entry.to_s
@@ -456,9 +448,9 @@ module Rfd
456
448
  # Create a new directory.
457
449
  def mkdir(dir)
458
450
  unless in_zip?
459
- FileUtils.mkdir_p File.join(current_dir, dir)
451
+ FileUtils.mkdir_p current_dir.join(dir)
460
452
  else
461
- Zip::File.open(current_zip.path) do |zip|
453
+ Zip::File.open(current_zip) do |zip|
462
454
  zip.dir.mkdir dir
463
455
  end
464
456
  end
@@ -468,11 +460,11 @@ module Rfd
468
460
  # Create a new empty file.
469
461
  def touch(filename)
470
462
  unless in_zip?
471
- FileUtils.touch File.join(current_dir, filename)
463
+ FileUtils.touch current_dir.join(filename)
472
464
  else
473
- Zip::File.open(current_zip.path) do |zip|
465
+ Zip::File.open(current_zip) do |zip|
474
466
  # zip.file.open(filename, 'w') {|_f| } #HAXX this code creates an unneeded temporary file
475
- zip.instance_variable_get(:@entry_set) << Zip::Entry.new(current_zip.path, filename)
467
+ zip.instance_variable_get(:@entry_set) << Zip::Entry.new(current_zip, filename)
476
468
  end
477
469
  end
478
470
  ls
@@ -480,7 +472,7 @@ module Rfd
480
472
 
481
473
  # Create a symlink to the current file or directory.
482
474
  def symlink(name)
483
- FileUtils.ln_s current_item.path, name
475
+ FileUtils.ln_s current_item, name
484
476
  ls
485
477
  end
486
478
 
@@ -498,11 +490,11 @@ module Rfd
498
490
  selected_items.each do |item|
499
491
  next if item.symlink?
500
492
  if item.directory?
501
- Dir[File.join(item.path, '**/**')].each do |file|
493
+ Dir[item.join('**/**')].each do |file|
502
494
  zipfile.add file.sub("#{current_dir}/", ''), file
503
495
  end
504
496
  else
505
- zipfile.add item.name, item.path
497
+ zipfile.add item.name, item
506
498
  end
507
499
  end
508
500
  end
@@ -514,18 +506,18 @@ module Rfd
514
506
  unless in_zip?
515
507
  zips, gzs = selected_items.partition(&:zip?).tap {|z, others| break [z, *others.partition(&:gz?)]}
516
508
  zips.each do |item|
517
- FileUtils.mkdir_p File.join(current_dir, item.basename)
518
- Zip::File.open(item.path) do |zip|
509
+ FileUtils.mkdir_p current_dir.join(item.basename)
510
+ Zip::File.open(item) do |zip|
519
511
  zip.each do |entry|
520
- FileUtils.mkdir_p File.join(File.join(item.basename, File.dirname(entry.to_s)))
512
+ FileUtils.mkdir_p File.join(item.basename, File.dirname(entry.to_s))
521
513
  zip.extract(entry, File.join(item.basename, entry.to_s)) { true }
522
514
  end
523
515
  end
524
516
  end
525
517
  gzs.each do |item|
526
- Zlib::GzipReader.open(item.path) do |gz|
518
+ Zlib::GzipReader.open(item) do |gz|
527
519
  Gem::Package::TarReader.new(gz) do |tar|
528
- dest_dir = File.join current_dir, (gz.orig_name || item.basename).sub(/\.tar$/, '')
520
+ dest_dir = current_dir.join (gz.orig_name || item.basename).sub(/\.tar$/, '')
529
521
  tar.each do |entry|
530
522
  dest = nil
531
523
  if entry.full_name == '././@LongLink'
@@ -551,7 +543,7 @@ module Rfd
551
543
  end
552
544
  end
553
545
  else
554
- Zip::File.open(current_zip.path) do |zip|
546
+ Zip::File.open(current_zip) do |zip|
555
547
  zip.select {|e| selected_items.map(&:name).include? e.to_s}.each do |entry|
556
548
  FileUtils.mkdir_p File.join(current_zip.dir, current_zip.basename, File.dirname(entry.to_s))
557
549
  zip.extract(entry, File.join(current_zip.dir, current_zip.basename, entry.to_s)) { true }
@@ -662,7 +654,7 @@ module Rfd
662
654
  else
663
655
  begin
664
656
  tmpdir, tmpfile_name = nil
665
- Zip::File.open(current_zip.path) do |zip|
657
+ Zip::File.open(current_zip) do |zip|
666
658
  tmpdir = Dir.mktmpdir
667
659
  FileUtils.mkdir_p File.join(tmpdir, File.dirname(current_item.name))
668
660
  tmpfile_name = File.join(tmpdir, current_item.name)
@@ -687,7 +679,7 @@ module Rfd
687
679
  else
688
680
  begin
689
681
  tmpdir, tmpfile_name = nil
690
- Zip::File.open(current_zip.path) do |zip|
682
+ Zip::File.open(current_zip) do |zip|
691
683
  tmpdir = Dir.mktmpdir
692
684
  FileUtils.mkdir_p File.join(tmpdir, File.dirname(current_item.name))
693
685
  tmpfile_name = File.join(tmpdir, current_item.name)
@@ -720,7 +712,12 @@ module Rfd
720
712
  end
721
713
 
722
714
  def expand_path(path)
723
- File.expand_path path.is_a?(Rfd::Item) ? path.path : path.start_with?('/') || path.start_with?('~') ? path : current_dir ? File.join(current_dir, path) : path
715
+ File.expand_path path.start_with?('/') || path.start_with?('~') ? path : current_dir ? current_dir.join(path) : path
716
+ end
717
+
718
+ def load_item(path)
719
+ stat = File.lstat path
720
+ Item.new dir: File.dirname(path), name: File.basename(path), stat: stat, window_width: maxx
724
721
  end
725
722
 
726
723
  def osx?
data/lib/rfd/commands.rb CHANGED
@@ -266,8 +266,8 @@ module Rfd
266
266
 
267
267
  # cd to the upper hierarchy.
268
268
  def del
269
- if current_dir != '/'
270
- cd File.expand_path(File.join(current_dir, ['..'] * times))
269
+ if current_dir.path != '/'
270
+ cd File.expand_path(current_dir.join(['..'] * times))
271
271
  ls
272
272
  end
273
273
  end
data/lib/rfd/item.rb CHANGED
@@ -20,6 +20,10 @@ module Rfd
20
20
  @extname ||= File.extname name
21
21
  end
22
22
 
23
+ def join(*ary)
24
+ File.join path, ary
25
+ end
26
+
23
27
  def full_display_name
24
28
  n = @name.dup
25
29
  n << " -> #{target}" if symlink?
@@ -187,6 +191,10 @@ module Rfd
187
191
  "#{current_mark}#{mb_ljust(display_name, @window_width - 15)}#{size_or_dir.rjust(13)}"
188
192
  end
189
193
 
194
+ def to_str
195
+ path
196
+ end
197
+
190
198
  def <=>(o)
191
199
  if directory? && !o.directory?
192
200
  1
data/lib/rfd/windows.rb CHANGED
@@ -138,7 +138,10 @@ module Rfd
138
138
  end
139
139
 
140
140
  def close_all
141
- @panes.each {|p| Curses.delwin p}
141
+ @panes.each do |p|
142
+ Curses.wclear p
143
+ Curses.delwin p
144
+ end
142
145
  end
143
146
 
144
147
  def include_point?(pane: pane, y: nil, x: nil)
data/rfd.gemspec CHANGED
@@ -4,7 +4,7 @@ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
4
 
5
5
  Gem::Specification.new do |spec|
6
6
  spec.name = "rfd"
7
- spec.version = '0.2.0'
7
+ spec.version = '0.3.0'
8
8
  spec.authors = ["Akira Matsuda"]
9
9
  spec.email = ["ronnie@dio.jp"]
10
10
  spec.description = 'Ruby on Files & Directories'
@@ -106,13 +106,13 @@ describe Rfd::Controller do
106
106
  before do
107
107
  controller.cd 'dir1'
108
108
  end
109
- its(:current_dir) { should == File.join(tmpdir, 'dir1') }
109
+ its('current_dir.path') { should == File.join(tmpdir, 'dir1') }
110
110
 
111
111
  describe '#popd' do
112
112
  before do
113
113
  controller.popd
114
114
  end
115
- its(:current_dir) { should == tmpdir }
115
+ its('current_dir.path') { should == tmpdir }
116
116
  end
117
117
  end
118
118
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rfd
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.0
4
+ version: 0.3.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Akira Matsuda
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2013-10-12 00:00:00.000000000 Z
11
+ date: 2013-10-13 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: ffi-ncurses