diff --git a/oviewer/convert_align.go b/oviewer/convert_align.go index 09794d00..86822bab 100644 --- a/oviewer/convert_align.go +++ b/oviewer/convert_align.go @@ -100,7 +100,7 @@ func (a *align) convertWidth(st *parseState) bool { } lc = append(lc, st.lc[s:e]...) // Add space to align columns. - for ; width <= a.maxWidths[i]+1; width++ { + for ; width <= a.maxWidths[i]; width++ { lc = append(lc, SpaceContent) } s = e diff --git a/oviewer/convert_align_test.go b/oviewer/convert_align_test.go new file mode 100644 index 00000000..f0bc78b2 --- /dev/null +++ b/oviewer/convert_align_test.go @@ -0,0 +1,85 @@ +package oviewer + +import ( + "regexp" + "testing" +) + +func Test_align_convert(t *testing.T) { + type fields struct { + es *escapeSequence + maxWidths []int + orgWidths []int + WidthF bool + delimiter string + delimiterReg *regexp.Regexp + count int + } + type args struct { + st *parseState + } + tests := []struct { + name string + fields fields + args args + want bool + wantStr string + }{ + { + name: "convertAlignDelm", + fields: fields{ + es: newESConverter(), + maxWidths: []int{1, 2}, + WidthF: false, + delimiter: ",", + count: 0, + }, + args: args{ + st: &parseState{ + lc: StrToContents("a,b,c\n", 8), + mainc: '\n', + }, + }, + want: false, + wantStr: "a ,b ,c\n", + }, + { + name: "convertAlignWidth", + fields: fields{ + es: newESConverter(), + maxWidths: []int{3, 3}, + orgWidths: []int{2, 5}, + WidthF: true, + count: 0, + }, + args: args{ + st: &parseState{ + lc: StrToContents("a b c\n", 8), + mainc: '\n', + }, + }, + want: false, + wantStr: "a b c\n", + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + a := &align{ + es: tt.fields.es, + maxWidths: tt.fields.maxWidths, + orgWidths: tt.fields.orgWidths, + WidthF: tt.fields.WidthF, + delimiter: tt.fields.delimiter, + delimiterReg: tt.fields.delimiterReg, + count: tt.fields.count, + } + if got := a.convert(tt.args.st); got != tt.want { + t.Errorf("align.convert() = %v, want %v", got, tt.want) + } + goStr, _ := ContentsToStr(tt.args.st.lc) + if goStr != tt.wantStr { + t.Errorf("align.convert() = %v, want %v", goStr, tt.wantStr) + } + }) + } +} diff --git a/oviewer/convert_raw_test.go b/oviewer/convert_raw_test.go new file mode 100644 index 00000000..2d4b8f1c --- /dev/null +++ b/oviewer/convert_raw_test.go @@ -0,0 +1,50 @@ +package oviewer + +import ( + "reflect" + "testing" +) + +func Test_rawConverter_convert(t *testing.T) { + tests := []struct { + name string + r rawConverter + st *parseState + str string + want bool + wantStr string + }{ + { + name: "convertABC", + r: *newRawConverter(), + str: "abc", + st: &parseState{ + mainc: '\n', + }, + want: false, + wantStr: "abc", + }, + { + name: "convertEscape", + r: *newRawConverter(), + str: "abc", + st: &parseState{ + mainc: 0x1b, + }, + want: true, + wantStr: "abc^[", + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + tt.st.lc = StrToContents(tt.str, tt.st.tabWidth) + if got := tt.r.convert(tt.st); got != tt.want { + t.Errorf("rawConverter.convert() = %v, want %v", got, tt.want) + } + gotStr, _ := ContentsToStr(tt.st.lc) + if !reflect.DeepEqual(gotStr, tt.wantStr) { + t.Errorf("rawConverter.convert() = %v, want %v", gotStr, tt.wantStr) + } + }) + } +} diff --git a/oviewer/prepare_draw.go b/oviewer/prepare_draw.go index 94f6b2b6..46183dca 100644 --- a/oviewer/prepare_draw.go +++ b/oviewer/prepare_draw.go @@ -123,9 +123,6 @@ func (root *Root) setAlignConverter() { m.alignConv.orgWidths = m.columnWidths m.alignConv.maxWidths = maxWidths m.ClearCache() - log.Println("Change in column width") - } else { - log.Println("No change in column width") } } @@ -152,16 +149,18 @@ func maxWidthsDelm(lc contents, maxWidths []int, delimiter string, delimiterReg if len(indexes) == 0 { return maxWidths } - s := 0 + s := 1 for i := 0; i < len(indexes); i++ { - e := pos.x(indexes[i][1]) + e := pos.x(indexes[i][0]) + e1 := pos.x(indexes[i][1]) + delWidth := e1 - e width := e - s if len(maxWidths) <= i { maxWidths = append(maxWidths, width) } else { maxWidths[i] = max(width, maxWidths[i]) } - s = e + 1 + s = e + delWidth } return maxWidths } @@ -460,9 +459,9 @@ func (root *Root) columnWidthHighlight(line LineC) { numC := len(root.StyleColumnRainbow) - start, end := -1, -1 + start := 0 for c := 0; c < len(indexes)+1; c++ { - start = end + 1 + end := 0 if m.Converter == alignConv { end = alignColumnEnd(line.lc, m.alignConv.maxWidths, c, start) } else { @@ -475,6 +474,7 @@ func (root *Root) columnWidthHighlight(line LineC) { if c == m.columnCursor { RangeStyle(line.lc, start, end, root.StyleColumnHighlight) } + start = end + 1 } } @@ -521,7 +521,7 @@ func alignColumnEnd(lc contents, widths []int, n int, start int) int { if len(widths) <= n { return len(lc) } - end := start + widths[n] + 1 + end := start + widths[n] return min(end, len(lc)) } diff --git a/oviewer/prepare_draw_test.go b/oviewer/prepare_draw_test.go index 8fd7270a..9bfcea0e 100644 --- a/oviewer/prepare_draw_test.go +++ b/oviewer/prepare_draw_test.go @@ -1071,6 +1071,89 @@ func TestRoot_sectionHeader(t *testing.T) { } } +func TestRoot_setAlignConverter(t *testing.T) { + tcellNewScreen = fakeScreen + defer func() { + tcellNewScreen = tcell.NewScreen + }() + type fields struct { + fileName string + header int + columnWidth bool + columnDelimiter string + } + tests := []struct { + name string + fields fields + want []int + }{ + { + name: "Test setAlignConverter1", + fields: fields{ + fileName: "width-column.txt", + header: 1, + columnWidth: true, + }, + want: []int{4, 9}, + }, + { + name: "Test setAlignConverterDelimiter", + fields: fields{ + fileName: "column.txt", + header: 1, + columnWidth: false, + columnDelimiter: "|", + }, + want: []int{-1, 7, 7, 7}, + }, + { + name: "Test setAlignConverterDelimiter2", + fields: fields{ + fileName: "test.csv", + header: 1, + columnWidth: false, + columnDelimiter: ",", + }, + want: []int{0, 5, 1}, + }, + { + name: "Test setAlignNoColumn", + fields: fields{ + fileName: "test.txt", + header: 1, + columnWidth: true, + }, + want: []int{}, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + root := rootFileReadHelper(t, filepath.Join(testdata, tt.fields.fileName)) + m := root.Doc + m.width = 80 + root.scr.vHeight = 24 + m.topLX = 0 + m.Header = tt.fields.header + m.ColumnMode = true + m.ColumnWidth = tt.fields.columnWidth + m.ColumnDelimiter = tt.fields.columnDelimiter + if m.ColumnDelimiter != "" { + m.ColumnDelimiterReg = condRegexpCompile(m.ColumnDelimiter) + } + root.scr.lines = make(map[int]LineC) + root.prepareScreen() + ctx := context.Background() + root.Doc.ColumnRainbow = true + root.Doc.Converter = alignConv + root.Doc.alignConv = newAlignConverter(true) + root.prepareDraw(ctx) + if got := root.Doc.alignConv.maxWidths; !reflect.DeepEqual(got, tt.want) { + t.Errorf("Root.setAlignConverter() = %v, want %v", got, tt.want) + } + }) + } +} + func Test_maxWidthsDelm(t *testing.T) { type args struct { maxWidths []int @@ -1091,7 +1174,7 @@ func Test_maxWidthsDelm(t *testing.T) { delimiter: ",", delimiterReg: regexpCompile(",", false), }, - want: []int{2, 2, 2, 2, 2, 2}, + want: []int{0, 2, 2, 2, 2, 2}, }, { name: "Test maxWidthsDelm2", diff --git a/testdata/test.csv b/testdata/test.csv new file mode 100644 index 00000000..a1458f94 --- /dev/null +++ b/testdata/test.csv @@ -0,0 +1,6 @@ +a,1234,c,d + +d,e,f,g +g,h,i,j +a,"b,c",d,k +a,b"c,d,l \ No newline at end of file diff --git a/testdata/width-column.txt b/testdata/width-column.txt new file mode 100644 index 00000000..98f693c2 --- /dev/null +++ b/testdata/width-column.txt @@ -0,0 +1,4 @@ +id name age + 1 tsst 21 + 2 test2 20 +123 test3 123 \ No newline at end of file