mdless 1.0.18 → 1.0.22
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +8 -1
- data/lib/mdless/colors.rb +9 -10
- data/lib/mdless/converter.rb +109 -95
- data/lib/mdless/theme.rb +5 -5
- data/lib/mdless/version.rb +1 -1
- metadata +3 -17
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: ea19ef57c9cdd3b8800a854cc342e518c3c5acca0a2bfd6806f30970686e37e7
|
4
|
+
data.tar.gz: aaf0111e1b7777c06ddb149032985665184f92c6a34e4d5d6e7a5abecf691289
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 11e08991457fd1c94698666be37e40e38c59753b4437e94c01a45a0215d9fbf7fea00c6bedbbb5408451f8ea8402897dcf81d6a8f757950669c2c85f1371ba48
|
7
|
+
data.tar.gz: 997cbd5836733b2740ae15d344764c6e303d41d77ec760392a9bad6ccdc08f8aaa2457601f0385449964826d423e9f26036c5d843946e50a94ecb922f5ce4e3b
|
data/README.md
CHANGED
@@ -1,4 +1,3 @@
|
|
1
|
-
|
2
1
|
# mdless
|
3
2
|
|
4
3
|
`mdless` is a utility that provides a formatted and highlighted view of Markdown files in Terminal.
|
@@ -27,6 +26,14 @@ I often use iTerm2 in visor mode, so `qlmanage -p` is annoying. I still wanted a
|
|
27
26
|
|
28
27
|
gem install mdless
|
29
28
|
|
29
|
+
### Dependencies
|
30
|
+
|
31
|
+
Some OSs are missing `tput`, which is necessary for mdless.
|
32
|
+
|
33
|
+
apt update
|
34
|
+
apt install ruby ncurses-utils
|
35
|
+
gem install mdless
|
36
|
+
|
30
37
|
## Usage
|
31
38
|
|
32
39
|
`mdless [options] path` or `cat [path] | mdless`
|
data/lib/mdless/colors.rb
CHANGED
@@ -71,7 +71,7 @@ module CLIMarkdown
|
|
71
71
|
self.uncolor.size
|
72
72
|
end
|
73
73
|
|
74
|
-
def wrap(width=78)
|
74
|
+
def wrap(width=78,foreground=:x)
|
75
75
|
|
76
76
|
if self.uncolor =~ /(^([%~] |\s*>)| +[=\-]{5,})/
|
77
77
|
return self
|
@@ -87,7 +87,7 @@ module CLIMarkdown
|
|
87
87
|
input.split(/\s+/).each do |word|
|
88
88
|
last_ansi = line.scan(/\e\[[\d;]+m/)[-1] || ''
|
89
89
|
if visible_width + word.size_clean >= width
|
90
|
-
lines << line + xc
|
90
|
+
lines << line + xc(foreground)
|
91
91
|
visible_width = word.size_clean
|
92
92
|
line = last_ansi + word
|
93
93
|
elsif line.empty?
|
@@ -98,18 +98,11 @@ module CLIMarkdown
|
|
98
98
|
line << " " << last_ansi + word
|
99
99
|
end
|
100
100
|
end
|
101
|
-
lines << line + self.match(/\s*$/)[0] + xc if line
|
101
|
+
lines << line + self.match(/\s*$/)[0] + xc(foreground) if line
|
102
102
|
return lines.join("\n") # .gsub(/\- (\S)/,'-\1')
|
103
103
|
end
|
104
104
|
|
105
|
-
def xc(count=0)
|
106
|
-
c([:x,:white])
|
107
|
-
end
|
108
|
-
|
109
105
|
def c(args)
|
110
|
-
|
111
|
-
|
112
|
-
|
113
106
|
out = []
|
114
107
|
|
115
108
|
args.each {|arg|
|
@@ -124,6 +117,12 @@ module CLIMarkdown
|
|
124
117
|
''
|
125
118
|
end
|
126
119
|
end
|
120
|
+
|
121
|
+
private
|
122
|
+
|
123
|
+
def xc(foreground=:x)
|
124
|
+
c([foreground])
|
125
|
+
end
|
127
126
|
end
|
128
127
|
end
|
129
128
|
|
data/lib/mdless/converter.rb
CHANGED
@@ -105,7 +105,12 @@ module CLIMarkdown
|
|
105
105
|
end
|
106
106
|
end
|
107
107
|
|
108
|
-
|
108
|
+
begin
|
109
|
+
optparse.parse!
|
110
|
+
rescue OptionParser::ParseError => pe
|
111
|
+
$stderr.puts "error: #{pe.message}"
|
112
|
+
exit 1
|
113
|
+
end
|
109
114
|
|
110
115
|
@theme = load_theme(@options[:theme])
|
111
116
|
@cols = @options[:width]
|
@@ -164,7 +169,7 @@ module CLIMarkdown
|
|
164
169
|
if @theme.key?(keys[0])
|
165
170
|
val = @theme[keys.shift]
|
166
171
|
else
|
167
|
-
@log.error("Invalid theme key: #{key}")
|
172
|
+
@log.error("Invalid theme key: #{key}") unless keys[0] =~ /^text/
|
168
173
|
return c([:reset])
|
169
174
|
end
|
170
175
|
keys.each {|k|
|
@@ -355,7 +360,7 @@ module CLIMarkdown
|
|
355
360
|
end
|
356
361
|
end
|
357
362
|
|
358
|
-
def find_color(line,nullable=false)
|
363
|
+
def find_color(line, nullable = false)
|
359
364
|
return line if line.nil?
|
360
365
|
colors = line.scan(/\e\[[\d;]+m/)
|
361
366
|
if colors && colors.size > 0
|
@@ -468,13 +473,14 @@ module CLIMarkdown
|
|
468
473
|
color('code_block border'),
|
469
474
|
'--[ ',
|
470
475
|
color('code_block title'),
|
471
|
-
leader,
|
476
|
+
leader.chomp,
|
472
477
|
color('code_block border'),
|
473
478
|
' ]',
|
474
|
-
'-'*(@cols-new_indent-leader.size
|
479
|
+
'-'*(@cols-new_indent-leader.size-2),
|
475
480
|
xc,
|
476
481
|
"\n",
|
477
|
-
hilite,
|
482
|
+
hilite.chomp,
|
483
|
+
"\n",
|
478
484
|
" "*(new_indent),
|
479
485
|
color('code_block border'),
|
480
486
|
'-'*(@cols-new_indent),
|
@@ -576,6 +582,44 @@ module CLIMarkdown
|
|
576
582
|
# match = Regexp.last_match
|
577
583
|
# "#" * (match[1].length - h_adjust)
|
578
584
|
# end
|
585
|
+
#
|
586
|
+
# Headlines
|
587
|
+
@headers.each {|h|
|
588
|
+
input.sub!(/^#{Regexp.escape(h[2])}/m) do |m|
|
589
|
+
pad = ''
|
590
|
+
ansi = ''
|
591
|
+
case h[0].length
|
592
|
+
when 1
|
593
|
+
ansi = color('h1 color')
|
594
|
+
pad = color('h1 pad')
|
595
|
+
char = @theme['h1']['pad_char'] || "="
|
596
|
+
pad += h[1].length + 2 > @cols ? char*h[1].length : char*(@cols - (h[1].length + 1))
|
597
|
+
when 2
|
598
|
+
ansi = color('h2 color')
|
599
|
+
pad = color('h2 pad')
|
600
|
+
char = @theme['h2']['pad_char'] || "-"
|
601
|
+
pad += h[1].length + 2 > @cols ? char*h[1].length : char*(@cols - (h[1].length + 1))
|
602
|
+
when 3
|
603
|
+
ansi = color('h3 color')
|
604
|
+
when 4
|
605
|
+
ansi = color('h4 color')
|
606
|
+
when 5
|
607
|
+
ansi = color('h5 color')
|
608
|
+
else
|
609
|
+
ansi = color('h6 color')
|
610
|
+
end
|
611
|
+
|
612
|
+
# If we're in iTerm and not paginating, add
|
613
|
+
# iTerm Marks for navigation on h1-3
|
614
|
+
if h[0].length < 4 &&
|
615
|
+
ENV['TERM_PROGRAM'] =~ /^iterm/i &&
|
616
|
+
@options[:pager] == false
|
617
|
+
ansi = "\e]1337;SetMark\a" + ansi
|
618
|
+
end
|
619
|
+
|
620
|
+
"\n#{xc}#{ansi}#{h[1]} #{pad}#{xc}\n"
|
621
|
+
end
|
622
|
+
}
|
579
623
|
|
580
624
|
# code block parsing
|
581
625
|
input.gsub!(/(?i-m)(^[ \t]*[`~]{3,})([\s\S]*?)\n([\s\S]*?)\1/m) do
|
@@ -632,11 +676,41 @@ module CLIMarkdown
|
|
632
676
|
# previous_indent = indent
|
633
677
|
# end
|
634
678
|
else
|
679
|
+
# list items
|
680
|
+
# TODO: Fix ordered list numbering, pad numbers based on total number of list items
|
681
|
+
line.gsub!(/^(\s*)([*\-+]|\d+\.) /) do |m|
|
682
|
+
match = Regexp.last_match
|
683
|
+
last = find_color(match.pre_match)
|
684
|
+
mcolor = match[2] =~ /^\d+\./ ? 'list number' : 'list bullet'
|
685
|
+
indent = match[1] || ''
|
686
|
+
[
|
687
|
+
indent,
|
688
|
+
color(mcolor),
|
689
|
+
match[2], " ",
|
690
|
+
color('list color')
|
691
|
+
].join
|
692
|
+
end
|
693
|
+
|
694
|
+
# definition lists
|
695
|
+
line.gsub!(/^(:\s*)(.*?)/) do |m|
|
696
|
+
match = Regexp.last_match
|
697
|
+
[
|
698
|
+
color('dd marker'),
|
699
|
+
match[1],
|
700
|
+
" ",
|
701
|
+
color('dd color'),
|
702
|
+
match[2],
|
703
|
+
xc
|
704
|
+
].join
|
705
|
+
end
|
706
|
+
|
635
707
|
# place footnotes under paragraphs that reference them
|
636
708
|
if line =~ /\[(?:\e\[[\d;]+m)*\^(?:\e\[[\d;]+m)*(\S+)(?:\e\[[\d;]+m)*\]/
|
637
|
-
|
709
|
+
match = Regexp.last_match
|
710
|
+
key = match[1].uncolor
|
638
711
|
if @footnotes.key? key
|
639
|
-
line
|
712
|
+
line = "#{xc}#{line}"
|
713
|
+
line += "\n\n#{color('footnote brackets')}[#{color('footnote caret')}^#{color('footnote title')}#{key}#{color('footnote brackets')}]: #{color('footnote note')}#{@footnotes[key]}#{xc}"
|
640
714
|
@footnotes.delete(key)
|
641
715
|
end
|
642
716
|
end
|
@@ -650,7 +724,7 @@ module CLIMarkdown
|
|
650
724
|
counter -= 1
|
651
725
|
find_color(lines[counter])
|
652
726
|
end
|
653
|
-
"#{
|
727
|
+
"#{color('footnote brackets')}[#{color('footnote caret')}^#{color('footnote title')}#{match[1]}#{color('footnote brackets')}]" + (last ? last : xc)
|
654
728
|
end
|
655
729
|
|
656
730
|
# blockquotes
|
@@ -666,7 +740,6 @@ module CLIMarkdown
|
|
666
740
|
end
|
667
741
|
|
668
742
|
# make reference links inline
|
669
|
-
|
670
743
|
line.gsub!(/(?<![\e*])\[(\b.*?\b)?\]\[(\b.+?\b)?\]/) do |m|
|
671
744
|
match = Regexp.last_match
|
672
745
|
title = match[2] || ''
|
@@ -690,23 +763,6 @@ module CLIMarkdown
|
|
690
763
|
color_link(match.pre_match, match[1], match[2])
|
691
764
|
end
|
692
765
|
|
693
|
-
|
694
|
-
|
695
|
-
# inline code
|
696
|
-
line.gsub!(/`(.*?)`/) do |m|
|
697
|
-
match = Regexp.last_match
|
698
|
-
last = find_color(match.pre_match, true)
|
699
|
-
[
|
700
|
-
color('code_span marker'),
|
701
|
-
'`',
|
702
|
-
color('code_span color'),
|
703
|
-
match[1],
|
704
|
-
color('code_span marker'),
|
705
|
-
'`',
|
706
|
-
last ? last : xc
|
707
|
-
].join
|
708
|
-
end
|
709
|
-
|
710
766
|
# horizontal rules
|
711
767
|
line.gsub!(/^ {,3}([\-*] ?){3,}$/) do |m|
|
712
768
|
color('hr color') + '_'*@cols + xc
|
@@ -741,7 +797,7 @@ module CLIMarkdown
|
|
741
797
|
end
|
742
798
|
|
743
799
|
# equations
|
744
|
-
line.gsub!(/((\\\\\[)(.*?)(\\\\\])|(\\\\\()(.*?)(\\\\\)))/) do |m|
|
800
|
+
line.gsub!(/((\\\\\[|\$\$)(.*?)(\\\\\]|\$\$)|(\\\\\(|\$)(.*?)(\\\\\)|\$))/) do |m|
|
745
801
|
match = Regexp.last_match
|
746
802
|
last = find_color(match.pre_match)
|
747
803
|
if match[2]
|
@@ -754,34 +810,6 @@ module CLIMarkdown
|
|
754
810
|
"#{c(%i[b black])}#{brackets[0]}#{xc}#{c(%i[b blue])}#{equat}#{c(%i[b black])}#{brackets[1]}" + (last ? last : xc)
|
755
811
|
end
|
756
812
|
|
757
|
-
# list items
|
758
|
-
# TODO: Fix ordered list numbering, pad numbers based on total number of list items
|
759
|
-
line.gsub!(/^(\s*)([*\-+]|\d+\.) /) do |m|
|
760
|
-
match = Regexp.last_match
|
761
|
-
last = find_color(match.pre_match)
|
762
|
-
mcolor = match[2] =~ /^\d+\./ ? 'list number' : 'list bullet'
|
763
|
-
indent = match[1] || ''
|
764
|
-
[
|
765
|
-
indent,
|
766
|
-
color(mcolor),
|
767
|
-
match[2], " ",
|
768
|
-
color('list color')
|
769
|
-
].join
|
770
|
-
end
|
771
|
-
|
772
|
-
# definition lists
|
773
|
-
line.gsub!(/^(:\s*)(.*?)/) do |m|
|
774
|
-
match = Regexp.last_match
|
775
|
-
[
|
776
|
-
color('dd marker'),
|
777
|
-
match[1],
|
778
|
-
" ",
|
779
|
-
color('dd color'),
|
780
|
-
match[2],
|
781
|
-
xc
|
782
|
-
].join
|
783
|
-
end
|
784
|
-
|
785
813
|
# misc html
|
786
814
|
line.gsub!(/<br\/?>/, "\n")
|
787
815
|
line.gsub!(/(?i-m)((<\/?)(\w+[\s\S]*?)(>))/) do |tag|
|
@@ -797,51 +825,33 @@ module CLIMarkdown
|
|
797
825
|
last ? last : xc
|
798
826
|
].join
|
799
827
|
end
|
828
|
+
|
829
|
+
# inline code spans
|
830
|
+
line.gsub!(/`(.*?)`/) do |m|
|
831
|
+
match = Regexp.last_match
|
832
|
+
last = find_color(match.pre_match, true)
|
833
|
+
[
|
834
|
+
color('code_span marker'),
|
835
|
+
'`',
|
836
|
+
color('code_span color'),
|
837
|
+
match[1],
|
838
|
+
color('code_span marker'),
|
839
|
+
'`',
|
840
|
+
last ? last : xc
|
841
|
+
].join
|
842
|
+
end
|
800
843
|
end
|
801
844
|
|
845
|
+
## Should force a foreground color but doesn't...
|
846
|
+
# unless line =~ /^\s*\e\[[\d;]+m/
|
847
|
+
# line.sub!(/^(\s*)/, "\\1#{color('text')}")
|
848
|
+
# end
|
849
|
+
|
802
850
|
line
|
803
851
|
end
|
804
852
|
|
805
853
|
input = lines.join("\n")
|
806
854
|
|
807
|
-
# Headlines
|
808
|
-
@headers.each {|h|
|
809
|
-
input.sub!(/^#{Regexp.escape(h[2])}/m) do |m|
|
810
|
-
pad = ''
|
811
|
-
ansi = ''
|
812
|
-
case h[0].length
|
813
|
-
when 1
|
814
|
-
ansi = color('h1 color')
|
815
|
-
pad = color('h1 pad')
|
816
|
-
char = @theme['h1']['pad_char'] || "="
|
817
|
-
pad += h[1].length + 2 > @cols ? char*h[1].length : char*(@cols - (h[1].length + 1))
|
818
|
-
when 2
|
819
|
-
ansi = color('h2 color')
|
820
|
-
pad = color('h2 pad')
|
821
|
-
char = @theme['h2']['pad_char'] || "-"
|
822
|
-
pad += h[1].length + 2 > @cols ? char*h[1].length : char*(@cols - (h[1].length + 1))
|
823
|
-
when 3
|
824
|
-
ansi = color('h3 color')
|
825
|
-
when 4
|
826
|
-
ansi = color('h4 color')
|
827
|
-
when 5
|
828
|
-
ansi = color('h5 color')
|
829
|
-
else
|
830
|
-
ansi = color('h6 color')
|
831
|
-
end
|
832
|
-
|
833
|
-
# If we're in iTerm and not paginating, add
|
834
|
-
# iTerm Marks for navigation on h1-3
|
835
|
-
if h[0].length < 4 &&
|
836
|
-
ENV['TERM_PROGRAM'] =~ /^iterm/i &&
|
837
|
-
@options[:pager] == false
|
838
|
-
ansi = "\e]1337;SetMark\a" + ansi
|
839
|
-
end
|
840
|
-
|
841
|
-
"\n#{xc}#{ansi}#{h[1]} #{pad}#{xc}\n"
|
842
|
-
end
|
843
|
-
}
|
844
|
-
|
845
855
|
# images
|
846
856
|
input.gsub!(/^(.*?)!\[(.*)?\]\((.*?\.(?:png|gif|jpg))( +.*)?\)/) do |m|
|
847
857
|
match = Regexp.last_match
|
@@ -980,7 +990,7 @@ module CLIMarkdown
|
|
980
990
|
|
981
991
|
def printout
|
982
992
|
out = @output.rstrip.split(/\n/).map {|p|
|
983
|
-
p.wrap(@cols)
|
993
|
+
p.wrap(@cols, color('text'))
|
984
994
|
}.join("\n")
|
985
995
|
|
986
996
|
|
@@ -1043,5 +1053,9 @@ module CLIMarkdown
|
|
1043
1053
|
|
1044
1054
|
[pg, args]
|
1045
1055
|
end
|
1056
|
+
|
1057
|
+
def xc
|
1058
|
+
color('text')
|
1059
|
+
end
|
1046
1060
|
end
|
1047
1061
|
end
|
data/lib/mdless/theme.rb
CHANGED
@@ -93,11 +93,11 @@ module CLIMarkdown
|
|
93
93
|
new_theme = YAML.load(IO.read(theme_file))
|
94
94
|
begin
|
95
95
|
theme = THEME_DEFAULTS.deep_merge(new_theme)
|
96
|
-
# write merged theme back in case there are new keys since
|
97
|
-
# last updated
|
98
|
-
File.open(theme_file,'w') {|f|
|
99
|
-
|
100
|
-
}
|
96
|
+
# # write merged theme back in case there are new keys since
|
97
|
+
# # last updated
|
98
|
+
# File.open(theme_file,'w') {|f|
|
99
|
+
# f.puts theme.to_yaml
|
100
|
+
# }
|
101
101
|
rescue
|
102
102
|
@log.warn('Error merging user theme')
|
103
103
|
theme = THEME_DEFAULTS
|
data/lib/mdless/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: mdless
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.0.
|
4
|
+
version: 1.0.22
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Brett Terpstra
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2021-
|
11
|
+
date: 2021-09-15 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rake
|
@@ -44,20 +44,6 @@ dependencies:
|
|
44
44
|
- - ">="
|
45
45
|
- !ruby/object:Gem::Version
|
46
46
|
version: 4.1.1
|
47
|
-
- !ruby/object:Gem::Dependency
|
48
|
-
name: aruba
|
49
|
-
requirement: !ruby/object:Gem::Requirement
|
50
|
-
requirements:
|
51
|
-
- - "~>"
|
52
|
-
- !ruby/object:Gem::Version
|
53
|
-
version: '0'
|
54
|
-
type: :development
|
55
|
-
prerelease: false
|
56
|
-
version_requirements: !ruby/object:Gem::Requirement
|
57
|
-
requirements:
|
58
|
-
- - "~>"
|
59
|
-
- !ruby/object:Gem::Version
|
60
|
-
version: '0'
|
61
47
|
description: A CLI that provides a formatted and highlighted view of Markdown files
|
62
48
|
in a terminal
|
63
49
|
email: me@brettterpstra.com
|
@@ -103,7 +89,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
103
89
|
- !ruby/object:Gem::Version
|
104
90
|
version: '0'
|
105
91
|
requirements: []
|
106
|
-
rubygems_version: 3.
|
92
|
+
rubygems_version: 3.2.16
|
107
93
|
signing_key:
|
108
94
|
specification_version: 4
|
109
95
|
summary: A pager like less, but for Markdown files
|