-
Notifications
You must be signed in to change notification settings - Fork 1
/
helper.go
155 lines (142 loc) · 2.88 KB
/
helper.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
package main
import (
"io"
"log"
"path"
"strings"
"github.com/mjl-/duit"
)
func unscale(v int) int {
return v * 1000 / dui.Scale(1000)
}
func buttonText(edit *duit.Edit) string {
t, err := edit.Selection()
topUI.error("", err, "button selection")
if len(t) == 0 {
t, err = edit.ExpandedText()
topUI.error("", err, "button expanded text")
}
return string(t)
}
func readAtFull(src io.ReaderAt, buf []byte, offset int64) (read int, err error) {
want := len(buf)
for want > 0 {
var n int
n, err = src.ReadAt(buf, offset)
if n > 0 {
read += n
offset += int64(n)
want -= n
buf = buf[n:]
}
if err == io.EOF {
return
}
}
return
}
func expandText(edit *duit.Edit, offset int64) string {
c := edit.Cursor()
c0, c1 := c.Ordered()
if c0 != c1 && offset >= c0 && offset <= c1 {
buf, err := edit.Selection()
topUI.error("", err, "expanded text")
return string(buf)
}
br := edit.ReverseEditReader(offset)
fr := edit.EditReader(offset)
br.Nonwhitespace()
fr.Nonwhitespace()
buf := make([]byte, int(fr.Offset()-br.Offset()))
n, err := readAtFull(edit.Reader(), buf, br.Offset())
if err != nil {
log.Printf("read: %s\n", err)
return ""
}
return string(buf[:n])
}
func errorDest(s string) string {
if !strings.HasSuffix(s, "/+Errors") {
if !strings.HasSuffix(s, "/") {
s = path.Dir(s) + "/"
}
s += "+Errors"
}
return s
}
func minimum(a, b int) int {
if a < b {
return a
}
return b
}
func maximum(a, b int) int {
if a > b {
return a
}
return b
}
func maximum64(a, b int64) int64 {
if a > b {
return a
}
return b
}
func grow(ogrow int, index int, dims []int, minDim int) (taken int) {
take := func(want int, dims []int, i, delta int) int {
avail := 0
for j := i + delta; j >= 0 && j < len(dims); j += delta {
avail += maximum(0, dims[j]-minDim)
}
if want >= avail {
for j := i + delta; j >= 0 && j < len(dims); j += delta {
dims[j] = minDim
}
want -= avail
} else if avail > 0 {
stillNeed := want
for j := i + delta; j >= 0 && j < len(dims); j += delta {
if j == 0 || j == len(dims)-1 {
dims[j] = maximum(minDim, dims[j]-stillNeed)
} else {
d := dims[j] - (maximum(0, dims[j]-minDim))*want/avail
stillNeed -= dims[j] - d
dims[j] = d
}
}
want = 0
}
return want
}
grow := take(ogrow, dims, index, 1)
grow = take(grow, dims, index, -1)
taken = ogrow - grow
dims[index] += taken
return taken
}
func tagHeight() int {
return 1 + unscale(dui.Display.DefaultFont.Height)
}
func setMinDims(dim []int, min int) {
need := 0
found := 0
for _, d := range dim {
if d > min {
found += d - min
} else {
need += min - d
}
}
found = minimum(found, need)
for i, d := range dim {
if d > min && need > 0 {
take := minimum(need, d-min)
need -= take
dim[i] -= take
} else if d < min && found > 0 {
take := minimum(found, min-d)
dim[i] += take
found -= take
}
}
}