使用 Go GUI 库 fyne 编写一个计算器程序

控件布局

display := widget.NewEntry()
display.MultiLine = true


digits := []string{
"7", "8", "9", "×",
"4", "5", "6", "-",
"1", "2", "3", "+",
}
var digitBtns []fyne.CanvasObject
for _, val := range digits {
digitBtns = append(digitBtns, widget.NewButton(val, input(display, val)))
}
digitContainer := fyne.NewContainerWithLayout(
layout.NewGridLayout(4),
digitBtns...)


input 回调后面介绍。

• AC ：清空显示框；
• +/- ：切换正负号；
• % 将数字变为百分数，即除以 100。

clearBtn := widget.NewButton("AC", clear(display))
signBtn := widget.NewButton("+/-", sign(display))
percentBtn := widget.NewButton("%", percent(display, "%"))
divideBtn := widget.NewButton("÷", input(display, "÷"))
clearContainer := fyne.NewContainerWithLayout(
layout.NewGridLayout(4),
clearBtn,
signBtn,
percentBtn,
divideBtn,
)


zeroBtn := widget.NewButton("0", input(display, "0"))
dotBtn := widget.NewButton(".", input(display, "."))
equalBtn := widget.NewButton("=", equals(display))
zeroContainer := fyne.NewContainerWithLayout(
layout.NewGridLayout(2),
zeroBtn,
fyne.NewContainerWithLayout(
layout.NewGridLayout(2),
dotBtn,
equalBtn,
),
)


container := fyne.NewContainerWithLayout(
layout.NewVBoxLayout(),
display,
clearContainer,
digitContainer,
zeroContainer,
)


按钮响应

func clear(display *widget.Entry) func() {
return func() {
display.Text = ""
display.Refresh()
}
}


func sign(display *widget.Entry) func() {
return func() {
lines := strings.Split(display.Text, "\n")
if len(lines) == 0 {
return
}

line := lines[len(lines)-1]
value, err := strconv.ParseInt(line, 10, 64)
if err != nil {
return
}
lines[len(lines)-1] = strconv.FormatInt(-value, 10)
display.Text = strings.Join(lines, "\n")
}
}


func input(display *widget.Entry, value string) func() {
return func() {
display.Text += value
display.Refresh()
}
}


func equals(display *widget.Entry) func() {
return func() {
lines := strings.Split(display.Text, "\n")
if len(lines) == 0 {
return
}

line := lines[len(lines)-1]
line = strings.Trim(line, "+÷×")
exprLine := strings.Replace(line, "÷", "/", -1)
exprLine = strings.Replace(exprLine, "×", "*", -1)
expr, _ := govaluate.NewEvaluableExpression(exprLine)
result, _ := expr.Evaluate(nil)
line += "=\n"
line += fmt.Sprint(result)
display.Text = line
display.Refresh()
}
}


打包

\$ fyne package -os windows -icon icon.jpg


参考

1. fyne GitHub：https://github.com/fyne-io/fyne

2. fyne 官网：https://fyne.io/

3. fyne 官方入门教程：https://developer.fyne.io/tour/introduction/hello.html

4. Go 每日一库 GitHub：https://github.com/darjun/go-daily-lib

Go 语言中 文网启用 信学习交流群，欢迎加微信 274768166 ，投稿亦欢迎