Skip to content
GitLab
Explore
Sign in
Register
Primary navigation
Search or go to…
Project
F
fzf
Manage
Activity
Members
Labels
Plan
Issues
Issue boards
Milestones
Wiki
Requirements
Code
Merge requests
Repository
Branches
Commits
Tags
Repository graph
Compare revisions
Snippets
Locked files
Build
Pipelines
Jobs
Pipeline schedules
Test cases
Artifacts
Deploy
Releases
Package Registry
Container Registry
Model registry
Operate
Environments
Terraform modules
Monitor
Incidents
Service Desk
Analyze
Value stream analytics
Contributor analytics
CI/CD analytics
Repository analytics
Code review analytics
Issue analytics
Insights
Model experiments
Help
Help
Support
GitLab documentation
Compare GitLab plans
Community forum
Contribute to JiHu GitLab
Provide feedback
Keyboard shortcuts
?
Snippets
Groups
Projects
Show more breadcrumbs
KMSCAKKSCFKA AKFACAMADCAS
fzf
Commits
1fc56598
Unverified
Commit
1fc56598
authored
8 years ago
by
Junegunn Choi
Browse files
Options
Downloads
Patches
Plain Diff
Add support for more ANSI color attributes (#674)
Dim, underline, blink, reverse
parent
1acd2adc
No related branches found
Branches containing commit
No related tags found
Tags containing commit
No related merge requests found
Changes
4
Hide whitespace changes
Inline
Side-by-side
Showing
4 changed files
src/ansi.go
+17
-7
17 additions, 7 deletions
src/ansi.go
src/curses/curses.go
+21
-14
21 additions, 14 deletions
src/curses/curses.go
src/result.go
+5
-5
5 additions, 5 deletions
src/result.go
src/terminal.go
+19
-19
19 additions, 19 deletions
src/terminal.go
with
62 additions
and
45 deletions
src/ansi.go
+
17
−
7
View file @
1fc56598
...
...
@@ -6,6 +6,8 @@ import (
"strconv"
"strings"
"unicode/utf8"
"github.com/junegunn/fzf/src/curses"
)
type
ansiOffset
struct
{
...
...
@@ -16,18 +18,18 @@ type ansiOffset struct {
type
ansiState
struct
{
fg
int
bg
int
bold
bool
attr
curses
.
Attr
}
func
(
s
*
ansiState
)
colored
()
bool
{
return
s
.
fg
!=
-
1
||
s
.
bg
!=
-
1
||
s
.
bold
return
s
.
fg
!=
-
1
||
s
.
bg
!=
-
1
||
s
.
attr
>
0
}
func
(
s
*
ansiState
)
equals
(
t
*
ansiState
)
bool
{
if
t
==
nil
{
return
!
s
.
colored
()
}
return
s
.
fg
==
t
.
fg
&&
s
.
bg
==
t
.
bg
&&
s
.
bold
==
t
.
bold
return
s
.
fg
==
t
.
fg
&&
s
.
bg
==
t
.
bg
&&
s
.
attr
==
t
.
attr
}
var
ansiRegex
*
regexp
.
Regexp
...
...
@@ -94,9 +96,9 @@ func interpretCode(ansiCode string, prevState *ansiState) *ansiState {
// State
var
state
*
ansiState
if
prevState
==
nil
{
state
=
&
ansiState
{
-
1
,
-
1
,
false
}
state
=
&
ansiState
{
-
1
,
-
1
,
0
}
}
else
{
state
=
&
ansiState
{
prevState
.
fg
,
prevState
.
bg
,
prevState
.
bold
}
state
=
&
ansiState
{
prevState
.
fg
,
prevState
.
bg
,
prevState
.
attr
}
}
if
ansiCode
[
1
]
!=
'['
||
ansiCode
[
len
(
ansiCode
)
-
1
]
!=
'm'
{
return
state
...
...
@@ -108,7 +110,7 @@ func interpretCode(ansiCode string, prevState *ansiState) *ansiState {
init
:=
func
()
{
state
.
fg
=
-
1
state
.
bg
=
-
1
state
.
bold
=
false
state
.
attr
=
0
state256
=
0
}
...
...
@@ -132,7 +134,15 @@ func interpretCode(ansiCode string, prevState *ansiState) *ansiState {
case
49
:
state
.
bg
=
-
1
case
1
:
state
.
bold
=
true
state
.
attr
=
curses
.
Bold
case
2
:
state
.
attr
=
curses
.
Dim
case
4
:
state
.
attr
=
curses
.
Underline
case
5
:
state
.
attr
=
curses
.
Blink
case
7
:
state
.
attr
=
curses
.
Reverse
case
0
:
init
()
default
:
...
...
This diff is collapsed.
Click to expand it.
src/curses/curses.go
+
21
−
14
View file @
1fc56598
...
...
@@ -23,6 +23,16 @@ import (
"unicode/utf8"
)
const
(
Bold
=
C
.
A_BOLD
Dim
=
C
.
A_DIM
Blink
=
C
.
A_BLINK
Reverse
=
C
.
A_REVERSE
Underline
=
C
.
A_UNDERLINE
)
type
Attr
C
.
int
// Types of user action
const
(
Rune
=
iota
...
...
@@ -158,7 +168,7 @@ type MouseEvent struct {
var
(
_buf
[]
byte
_in
*
os
.
File
_color
func
(
int
,
bool
)
C
.
int
_color
func
(
int
,
Attr
)
C
.
int
_colorMap
map
[
int
]
int
_prevDownTime
time
.
Time
_clickY
[]
int
...
...
@@ -183,7 +193,7 @@ type Window struct {
func
NewWindow
(
top
int
,
left
int
,
width
int
,
height
int
,
border
bool
)
*
Window
{
win
:=
C
.
newwin
(
C
.
int
(
height
),
C
.
int
(
width
),
C
.
int
(
top
),
C
.
int
(
left
))
if
border
{
attr
:=
_color
(
ColBorder
,
false
)
attr
:=
_color
(
ColBorder
,
0
)
C
.
wattron
(
win
,
attr
)
C
.
box
(
win
,
0
,
0
)
C
.
wattroff
(
win
,
attr
)
...
...
@@ -266,22 +276,19 @@ func init() {
Border
:
145
}
}
func
attrColored
(
pair
int
,
bold
bool
)
C
.
int
{
func
attrColored
(
pair
int
,
a
Attr
)
C
.
int
{
var
attr
C
.
int
if
pair
>
ColNormal
{
attr
=
C
.
COLOR_PAIR
(
C
.
int
(
pair
))
}
if
bold
{
attr
=
attr
|
C
.
A_BOLD
}
return
attr
return
attr
|
C
.
int
(
a
)
}
func
attrMono
(
pair
int
,
bold
bool
)
C
.
int
{
func
attrMono
(
pair
int
,
a
Attr
)
C
.
int
{
var
attr
C
.
int
switch
pair
{
case
ColCurrent
:
if
bold
{
if
a
&
C
.
A_BOLD
==
C
.
A_BOLD
{
attr
=
C
.
A_REVERSE
}
case
ColMatch
:
...
...
@@ -289,7 +296,7 @@ func attrMono(pair int, bold bool) C.int {
case
ColCurrentMatch
:
attr
=
C
.
A_UNDERLINE
|
C
.
A_REVERSE
}
if
bold
{
if
a
&
C
.
A_BOLD
==
C
.
A_BOLD
{
attr
=
attr
|
C
.
A_BOLD
}
return
attr
...
...
@@ -648,8 +655,8 @@ func (w *Window) Print(text string) {
},
text
)))
}
func
(
w
*
Window
)
CPrint
(
pair
int
,
bold
bool
,
text
string
)
{
attr
:=
_color
(
pair
,
bold
)
func
(
w
*
Window
)
CPrint
(
pair
int
,
a
Attr
,
text
string
)
{
attr
:=
_color
(
pair
,
a
)
C
.
wattron
(
w
.
win
,
attr
)
w
.
Print
(
text
)
C
.
wattroff
(
w
.
win
,
attr
)
...
...
@@ -675,8 +682,8 @@ func (w *Window) Fill(str string) bool {
return
C
.
waddstr
(
w
.
win
,
C
.
CString
(
str
))
==
C
.
OK
}
func
(
w
*
Window
)
CFill
(
str
string
,
fg
int
,
bg
int
,
bold
bool
)
bool
{
attr
:=
_color
(
PairFor
(
fg
,
bg
),
bold
)
func
(
w
*
Window
)
CFill
(
str
string
,
fg
int
,
bg
int
,
a
Attr
)
bool
{
attr
:=
_color
(
PairFor
(
fg
,
bg
),
a
)
C
.
wattron
(
w
.
win
,
attr
)
ret
:=
w
.
Fill
(
str
)
C
.
wattroff
(
w
.
win
,
attr
)
...
...
This diff is collapsed.
Click to expand it.
src/result.go
+
5
−
5
View file @
1fc56598
...
...
@@ -14,7 +14,7 @@ type Offset [2]int32
type
colorOffset
struct
{
offset
[
2
]
int32
color
int
bold
bool
attr
curses
.
Attr
index
int32
}
...
...
@@ -91,14 +91,14 @@ func minRank() rank {
return
rank
{
index
:
0
,
points
:
[
4
]
uint16
{
math
.
MaxUint16
,
0
,
0
,
0
}}
}
func
(
result
*
Result
)
colorOffsets
(
matchOffsets
[]
Offset
,
color
int
,
bold
bool
,
current
bool
)
[]
colorOffset
{
func
(
result
*
Result
)
colorOffsets
(
matchOffsets
[]
Offset
,
color
int
,
attr
curses
.
Attr
,
current
bool
)
[]
colorOffset
{
itemColors
:=
result
.
item
.
Colors
()
if
len
(
itemColors
)
==
0
{
var
offsets
[]
colorOffset
for
_
,
off
:=
range
matchOffsets
{
offsets
=
append
(
offsets
,
colorOffset
{
offset
:
[
2
]
int32
{
off
[
0
],
off
[
1
]},
color
:
color
,
bold
:
bold
})
offsets
=
append
(
offsets
,
colorOffset
{
offset
:
[
2
]
int32
{
off
[
0
],
off
[
1
]},
color
:
color
,
attr
:
attr
})
}
return
offsets
}
...
...
@@ -142,7 +142,7 @@ func (result *Result) colorOffsets(matchOffsets []Offset, color int, bold bool,
if
curr
!=
0
&&
idx
>
start
{
if
curr
==
-
1
{
colors
=
append
(
colors
,
colorOffset
{
offset
:
[
2
]
int32
{
int32
(
start
),
int32
(
idx
)},
color
:
color
,
bold
:
bold
})
offset
:
[
2
]
int32
{
int32
(
start
),
int32
(
idx
)},
color
:
color
,
attr
:
attr
})
}
else
{
ansi
:=
itemColors
[
curr
-
1
]
fg
:=
ansi
.
color
.
fg
...
...
@@ -164,7 +164,7 @@ func (result *Result) colorOffsets(matchOffsets []Offset, color int, bold bool,
colors
=
append
(
colors
,
colorOffset
{
offset
:
[
2
]
int32
{
int32
(
start
),
int32
(
idx
)},
color
:
curses
.
PairFor
(
fg
,
bg
),
bold
:
ansi
.
color
.
bold
||
bold
})
attr
:
ansi
.
color
.
attr
|
attr
})
}
}
}
...
...
This diff is collapsed.
Click to expand it.
src/terminal.go
+
19
−
19
View file @
1fc56598
...
...
@@ -526,24 +526,24 @@ func (t *Terminal) placeCursor() {
func
(
t
*
Terminal
)
printPrompt
()
{
t
.
move
(
0
,
0
,
true
)
t
.
window
.
CPrint
(
C
.
ColPrompt
,
true
,
t
.
prompt
)
t
.
window
.
CPrint
(
C
.
ColNormal
,
true
,
string
(
t
.
input
))
t
.
window
.
CPrint
(
C
.
ColPrompt
,
C
.
Bold
,
t
.
prompt
)
t
.
window
.
CPrint
(
C
.
ColNormal
,
C
.
Bold
,
string
(
t
.
input
))
}
func
(
t
*
Terminal
)
printInfo
()
{
if
t
.
inlineInfo
{
t
.
move
(
0
,
displayWidth
([]
rune
(
t
.
prompt
))
+
displayWidth
(
t
.
input
)
+
1
,
true
)
if
t
.
reading
{
t
.
window
.
CPrint
(
C
.
ColSpinner
,
true
,
" < "
)
t
.
window
.
CPrint
(
C
.
ColSpinner
,
C
.
Bold
,
" < "
)
}
else
{
t
.
window
.
CPrint
(
C
.
ColPrompt
,
true
,
" < "
)
t
.
window
.
CPrint
(
C
.
ColPrompt
,
C
.
Bold
,
" < "
)
}
}
else
{
t
.
move
(
1
,
0
,
true
)
if
t
.
reading
{
duration
:=
int64
(
spinnerDuration
)
idx
:=
(
time
.
Now
()
.
UnixNano
()
%
(
duration
*
int64
(
len
(
_spinner
))))
/
duration
t
.
window
.
CPrint
(
C
.
ColSpinner
,
true
,
_spinner
[
idx
])
t
.
window
.
CPrint
(
C
.
ColSpinner
,
C
.
Bold
,
_spinner
[
idx
])
}
t
.
move
(
1
,
2
,
false
)
}
...
...
@@ -562,7 +562,7 @@ func (t *Terminal) printInfo() {
if
t
.
progress
>
0
&&
t
.
progress
<
100
{
output
+=
fmt
.
Sprintf
(
" (%d%%)"
,
t
.
progress
)
}
t
.
window
.
CPrint
(
C
.
ColInfo
,
false
,
output
)
t
.
window
.
CPrint
(
C
.
ColInfo
,
0
,
output
)
}
func
(
t
*
Terminal
)
printHeader
()
{
...
...
@@ -586,7 +586,7 @@ func (t *Terminal) printHeader() {
colors
:
colors
}
t
.
move
(
line
,
2
,
true
)
t
.
printHighlighted
(
&
Result
{
item
:
item
},
false
,
C
.
ColHeader
,
0
,
false
)
t
.
printHighlighted
(
&
Result
{
item
:
item
},
0
,
C
.
ColHeader
,
0
,
false
)
}
}
...
...
@@ -620,21 +620,21 @@ func (t *Terminal) printItem(result *Result, i int, current bool) {
}
else
if
current
{
label
=
">"
}
t
.
window
.
CPrint
(
C
.
ColCursor
,
true
,
label
)
t
.
window
.
CPrint
(
C
.
ColCursor
,
C
.
Bold
,
label
)
if
current
{
if
selected
{
t
.
window
.
CPrint
(
C
.
ColSelected
,
true
,
">"
)
t
.
window
.
CPrint
(
C
.
ColSelected
,
C
.
Bold
,
">"
)
}
else
{
t
.
window
.
CPrint
(
C
.
ColCurrent
,
true
,
" "
)
t
.
window
.
CPrint
(
C
.
ColCurrent
,
C
.
Bold
,
" "
)
}
t
.
printHighlighted
(
result
,
true
,
C
.
ColCurrent
,
C
.
ColCurrentMatch
,
true
)
t
.
printHighlighted
(
result
,
C
.
Bold
,
C
.
ColCurrent
,
C
.
ColCurrentMatch
,
true
)
}
else
{
if
selected
{
t
.
window
.
CPrint
(
C
.
ColSelected
,
true
,
">"
)
t
.
window
.
CPrint
(
C
.
ColSelected
,
C
.
Bold
,
">"
)
}
else
{
t
.
window
.
Print
(
" "
)
}
t
.
printHighlighted
(
result
,
false
,
0
,
C
.
ColMatch
,
false
)
t
.
printHighlighted
(
result
,
0
,
0
,
C
.
ColMatch
,
false
)
}
}
...
...
@@ -690,7 +690,7 @@ func overflow(runes []rune, max int) bool {
return
false
}
func
(
t
*
Terminal
)
printHighlighted
(
result
*
Result
,
bold
bool
,
col1
int
,
col2
int
,
current
bool
)
{
func
(
t
*
Terminal
)
printHighlighted
(
result
*
Result
,
attr
C
.
Attr
,
col1
int
,
col2
int
,
current
bool
)
{
item
:=
result
.
item
// Overflow
...
...
@@ -715,7 +715,7 @@ func (t *Terminal) printHighlighted(result *Result, bold bool, col1 int, col2 in
maxe
=
util
.
Max
(
maxe
,
int
(
offset
[
1
]))
}
offsets
:=
result
.
colorOffsets
(
charOffsets
,
col2
,
bold
,
current
)
offsets
:=
result
.
colorOffsets
(
charOffsets
,
col2
,
attr
,
current
)
maxWidth
:=
t
.
window
.
Width
-
3
maxe
=
util
.
Constrain
(
maxe
+
util
.
Min
(
maxWidth
/
2
-
2
,
t
.
hscrollOff
),
0
,
len
(
text
))
if
overflow
(
text
,
maxWidth
)
{
...
...
@@ -764,11 +764,11 @@ func (t *Terminal) printHighlighted(result *Result, bold bool, col1 int, col2 in
e
:=
util
.
Constrain32
(
offset
.
offset
[
1
],
index
,
maxOffset
)
substr
,
prefixWidth
=
processTabs
(
text
[
index
:
b
],
prefixWidth
)
t
.
window
.
CPrint
(
col1
,
bold
,
substr
)
t
.
window
.
CPrint
(
col1
,
attr
,
substr
)
if
b
<
e
{
substr
,
prefixWidth
=
processTabs
(
text
[
b
:
e
],
prefixWidth
)
t
.
window
.
CPrint
(
offset
.
color
,
offset
.
bold
,
substr
)
t
.
window
.
CPrint
(
offset
.
color
,
offset
.
attr
,
substr
)
}
index
=
e
...
...
@@ -778,7 +778,7 @@ func (t *Terminal) printHighlighted(result *Result, bold bool, col1 int, col2 in
}
if
index
<
maxOffset
{
substr
,
_
=
processTabs
(
text
[
index
:
],
prefixWidth
)
t
.
window
.
CPrint
(
col1
,
bold
,
substr
)
t
.
window
.
CPrint
(
col1
,
attr
,
substr
)
}
}
...
...
@@ -812,7 +812,7 @@ func (t *Terminal) printPreview() {
}
}
if
ansi
!=
nil
&&
ansi
.
colored
()
{
return
t
.
pwindow
.
CFill
(
str
,
ansi
.
fg
,
ansi
.
bg
,
ansi
.
bold
)
return
t
.
pwindow
.
CFill
(
str
,
ansi
.
fg
,
ansi
.
bg
,
ansi
.
attr
)
}
return
t
.
pwindow
.
Fill
(
str
)
})
...
...
This diff is collapsed.
Click to expand it.
Preview
0%
Loading
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Save comment
Cancel
Please
register
or
sign in
to comment