简介
fynefynefynefynefyne
快速使用
本文代码使用 Go Modules。
先初始化:
$ mkdir fyne && cd fyne
$ go mod init github.com/darjun/go-daily-lib/fyne
复制代码fynegccgccgcc
TDM-GCCPATHgcc -v
fyne
$ go get -u fyne.io/fyne
复制代码到此准备工作已经完成,我们开始编码。按照惯例,先以Hello, World程序开始:
package main
import (
"fyne.io/fyne"
"fyne.io/fyne/app"
"fyne.io/fyne/widget"
)
func main() {
myApp := app.New()
myWin := myApp.NewWindow("Hello")
myWin.SetContent(widget.NewLabel("Hello Fyne!"))
myWin.Resize(fyne.NewSize(200, 200))
myWin.ShowAndRun()
}
复制代码运行结果如下:
fynefynemyAppapp.New()myAppmyApp.NewWindow("Hello")myApp.NewWindow()
fynewidget.NewXXX()XXXLabelmyWin.ShowAndRun()myWin.ShowAndRun()
myWin.Show()
myApp.Run()
复制代码myWin.Show()myApp.Run()
fynemyWin.Resize()Hello Fyne!
fyne
fyne
fyne.io/fynefynefyne.io/fyne/appfyne.io/fyne/canvasFynefyne.io/fyne/dialogfyne.io/fyne/layoutfyne.io/fyne/widgetfyne
Canvas
fyneCanvasCanvasObjectCanvas.SetContent()CanvasLayoutContainercanvas
package main
import (
"image/color"
"math/rand"
"fyne.io/fyne"
"fyne.io/fyne/app"
"fyne.io/fyne/canvas"
"fyne.io/fyne/layout"
"fyne.io/fyne/theme"
)
func main() {
a := app.New()
w := a.NewWindow("Canvas")
rect := canvas.NewRectangle(color.White)
text := canvas.NewText("Hello Text", color.White)
text.Alignment = fyne.TextAlignTrailing
text.TextStyle = fyne.TextStyle{Italic: true}
line := canvas.NewLine(color.White)
line.StrokeWidth = 5
circle := canvas.NewCircle(color.White)
circle.StrokeColor = color.Gray{0x99}
circle.StrokeWidth = 5
image := canvas.NewImageFromResource(theme.FyneLogo())
image.FillMode = canvas.ImageFillOriginal
raster := canvas.NewRasterWithPixels(
func(_, _, w, h int) color.Color {
return color.RGBA{uint8(rand.Intn(255)),
uint8(rand.Intn(255)),
uint8(rand.Intn(255)), 0xff}
},
)
gradient := canvas.NewHorizontalGradient(color.White, color.Transparent)
container := fyne.NewContainerWithLayout(
layout.NewGridWrapLayout(fyne.NewSize(150, 150)),
rect, text, line, circle, image, raster, gradient))
w.SetContent(container)
w.ShowAndRun()
}
复制代码程序运行结果如下:
canvas.Rectanglecanvas.NewRectangle()
canvas.Textcanvas.NewText()TextAlignment
TextAlignLeadingTextAlignCenterTextAlignTrailing
TextTextStyleTextStyle
type TextStyle struct {
Bold bool
Italic bool
Monospace bool
}
复制代码true
BoldItalicMonospace
FYNE_FONT.ttf
canvas.Linecanvas.NewLine()line.StrokeWidthline.Move()line.Resize()
canvas.Circlecanvas.NewCircle()StrokeColorStrokeWidth
canvas.Imagecanvas.NewImageFromResource()canvas.NewImageFromFile()image.Imagecanvas.NewImageFromImage()FillMode
ImageFillStretchImageFillContainImageFillOriginal
下面程序演示了这 3 种创建图像的方式:
package main
import (
"image"
"image/color"
"fyne.io/fyne"
"fyne.io/fyne/app"
"fyne.io/fyne/canvas"
"fyne.io/fyne/layout"
"fyne.io/fyne/theme"
)
func main() {
a := app.New()
w := a.NewWindow("Hello")
img1 := canvas.NewImageFromResource(theme.FyneLogo())
img1.FillMode = canvas.ImageFillOriginal
img2 := canvas.NewImageFromFile("./luffy.jpg")
img2.FillMode = canvas.ImageFillOriginal
image := image.NewAlpha(image.Rectangle{image.Point{0, 0}, image.Point{100, 100}})
for i := 0; i < 100; i++ {
for j := 0; j < 100; j++ {
image.Set(i, j, color.Alpha{uint8(i % 256)})
}
}
img3 := canvas.NewImageFromImage(image)
img3.FillMode = canvas.ImageFillOriginal
container := fyne.NewContainerWithLayout(
layout.NewGridWrapLayout(fyne.NewSize(150, 150)),
img1, img2, img3)
w.SetContent(container)
w.ShowAndRun()
}
复制代码theme.FyneLogo()luffy.jpgimage.Imagecanvas.Image
canvas.LinearGradientcanvas.RadialGradientcanvas.NewHorizontalGradient()canvas.NewVerticalGradient()canvas.NewRadialGradient()
func main() {
a := app.New()
w := a.NewWindow("Canvas")
gradient := canvas.NewRadialGradient(color.White, color.Transparent)
w.SetContent(gradient)
w.Resize(fyne.NewSize(200, 200))
w.ShowAndRun()
}
复制代码运行效果如下:
放射效果就是从中心向周围渐变。
Widget
Fyne
Label
Labelcanvas.TextLabel\n
func main() {
myApp := app.New()
myWin := myApp.NewWindow("Label")
l1 := widget.NewLabel("Name")
l2 := widget.NewLabel("da\njun")
container := fyne.NewContainerWithLayout(layout.NewVBoxLayout(), l1, l2)
myWin.SetContent(container)
myWin.Resize(fyne.NewSize(150, 150))
myWin.ShowAndRun()
}
复制代码widget.Label\n
Button
ButtonButtonwidget.NewButton()widget.NewButtonWithIcon()fyne.Resource
func main() {
myApp := app.New()
myWin := myApp.NewWindow("Button")
btn1 := widget.NewButton("text button", func() {
fmt.Println("text button clicked")
})
btn2 := widget.NewButtonWithIcon("icon", theme.HomeIcon(), func() {
fmt.Println("icon button clicked")
})
container := fyne.NewContainerWithLayout(layout.NewVBoxLayout(), btn1, btn2)
myWin.SetContent(container)
myWin.Resize(fyne.NewSize(150, 50))
myWin.ShowAndRun()
}
复制代码theme
点击按钮,对应的回调就会被调用,试试看!
Box
BoxBoxBox Layoutwidget.NewHBox()widget.NewVBox()widget.BoxAppend()Prepend()
func main() {
myApp := app.New()
myWin := myApp.NewWindow("Box")
content := widget.NewVBox(
widget.NewLabel("The top row of VBox"),
widget.NewHBox(
widget.NewLabel("Label 1"),
widget.NewLabel("Label 2"),
),
)
content.Append(widget.NewButton("Append", func() {
content.Append(widget.NewLabel("Appended"))
}))
content.Append(widget.NewButton("Prepend", func() {
content.Prepend(widget.NewLabel("Prepended"))
}))
myWin.SetContent(content)
myWin.Resize(fyne.NewSize(150, 150))
myWin.ShowAndRun()
}
复制代码widget.BoxLabel
Entry
Entrywidget.NewEntry()TextOnChangedOnChangedSetReadOnly(true)SetPlaceHolder()MultilineNewPasswordEntry()
func main() {
myApp := app.New()
myWin := myApp.NewWindow("Entry")
nameEntry := widget.NewEntry()
nameEntry.SetPlaceHolder("input name")
nameEntry.OnChanged = func(content string) {
fmt.Println("name:", nameEntry.Text, "entered")
}
passEntry := widget.NewPasswordEntry()
passEntry.SetPlaceHolder("input password")
nameBox := widget.NewHBox(widget.NewLabel("Name"), layout.NewSpacer(), nameEntry)
passwordBox := widget.NewHBox(widget.NewLabel("Password"), layout.NewSpacer(), passEntry)
loginBtn := widget.NewButton("Login", func() {
fmt.Println("name:", nameEntry.Text, "password:", passEntry.Text, "login in")
})
multiEntry := widget.NewEntry()
multiEntry.SetPlaceHolder("please enter\nyour description")
multiEntry.MultiLine = true
content := widget.NewVBox(nameBox, passwordBox, loginBtn, multiEntry)
myWin.SetContent(content)
myWin.ShowAndRun()
}
复制代码这里我们实现了一个简单的登录界面:
Checkbox/Radio/Select
CheckBoxwidget.NewCheck()bool
Radiowidget.NewRadio()Selected
SelectSelectwidget.NewSelect()NewRadio()
func main() {
myApp := app.New()
myWin := myApp.NewWindow("Choices")
nameEntry := widget.NewEntry()
nameEntry.SetPlaceHolder("input name")
passEntry := widget.NewPasswordEntry()
passEntry.SetPlaceHolder("input password")
repeatPassEntry := widget.NewPasswordEntry()
repeatPassEntry.SetPlaceHolder("repeat password")
nameBox := widget.NewHBox(widget.NewLabel("Name"), layout.NewSpacer(), nameEntry)
passwordBox := widget.NewHBox(widget.NewLabel("Password"), layout.NewSpacer(), passEntry)
repeatPasswordBox := widget.NewHBox(widget.NewLabel("Repeat Password"), layout.NewSpacer(), repeatPassEntry)
sexRadio := widget.NewRadio([]string{"male", "female", "unknown"}, func(value string) {
fmt.Println("sex:", value)
})
sexBox := widget.NewHBox(widget.NewLabel("Sex"), sexRadio)
football := widget.NewCheck("football", func(value bool) {
fmt.Println("football:", value)
})
basketball := widget.NewCheck("basketball", func(value bool) {
fmt.Println("basketball:", value)
})
pingpong := widget.NewCheck("pingpong", func(value bool) {
fmt.Println("pingpong:", value)
})
hobbyBox := widget.NewHBox(widget.NewLabel("Hobby"), football, basketball, pingpong)
provinceSelect := widget.NewSelect([]string{"anhui", "zhejiang", "shanghai"}, func(value string) {
fmt.Println("province:", value)
})
provinceBox := widget.NewHBox(widget.NewLabel("Province"), layout.NewSpacer(), provinceSelect)
registerBtn := widget.NewButton("Register", func() {
fmt.Println("name:", nameEntry.Text, "password:", passEntry.Text, "register")
})
content := widget.NewVBox(nameBox, passwordBox, repeatPasswordBox,
sexBox, hobbyBox, provinceBox, registerBtn)
myWin.SetContent(content)
myWin.ShowAndRun()
}
复制代码这里我们实现了一个简单的注册界面:
Form
FormLabelOnSubmitOnCancelButtonwidget.NewForm()widget.FormItemFormLabelFormAppend(label, widget)
func main() {
myApp := app.New()
myWindow := myApp.NewWindow("Form")
nameEntry := widget.NewEntry()
passEntry := widget.NewPasswordEntry()
form := widget.NewForm(
&widget.FormItem{"Name", nameEntry},
&widget.FormItem{"Pass", passEntry},
)
form.OnSubmit = func() {
fmt.Println("name:", nameEntry.Text, "pass:", passEntry.Text, "login in")
}
form.OnCancel = func() {
fmt.Println("login canceled")
}
myWindow.SetContent(form)
myWindow.Resize(fyne.NewSize(150, 150))
myWindow.ShowAndRun()
}
复制代码FormForm
SubmitCancel
ProgressBar
ProgressBarwidget.NewProgressBar()0.01.1Min/MaxSetValue()
func main() {
myApp := app.New()
myWindow := myApp.NewWindow("ProgressBar")
bar1 := widget.NewProgressBar()
bar1.Min = 0
bar1.Max = 100
bar2 := widget.NewProgressBarInfinite()
go func() {
for i := 0; i <= 100; i ++ {
time.Sleep(time.Millisecond * 500)
bar1.SetValue(float64(i))
}
}()
content := widget.NewVBox(bar1, bar2)
myWindow.SetContent(content)
myWindow.Resize(fyne.NewSize(150, 150))
myWindow.ShowAndRun()
}
复制代码在另一个 goroutine 中更新进度。效果如下:
TabContainer
TabContainerwidget.NewTabContainer()widget.TabItemwidget.TabItemwidget.NewTabItem(label, widget)
TabLocationBottomTabLocationLeadingTabLocationTrailing
看示例:
func main() {
myApp := app.New()
myWindow := myApp.NewWindow("TabContainer")
nameLabel := widget.NewLabel("Name: dajun")
sexLabel := widget.NewLabel("Sex: male")
ageLabel := widget.NewLabel("Age: 18")
addressLabel := widget.NewLabel("Province: shanghai")
addressLabel.Hide()
profile := widget.NewVBox(nameLabel, sexLabel, ageLabel, addressLabel)
musicRadio := widget.NewRadio([]string{"on", "off"}, func(string) {})
showAddressCheck := widget.NewCheck("show address?", func(value bool) {
if !value {
addressLabel.Hide()
} else {
addressLabel.Show()
}
})
memberTypeSelect := widget.NewSelect([]string{"junior", "senior", "admin"}, func(string) {})
setting := widget.NewForm(
&widget.FormItem{"music", musicRadio},
&widget.FormItem{"check", showAddressCheck},
&widget.FormItem{"member type", memberTypeSelect},
)
tabs := widget.NewTabContainer(
widget.NewTabItem("Profile", profile),
widget.NewTabItem("Setting", setting),
)
myWindow.SetContent(tabs)
myWindow.Resize(fyne.NewSize(200, 200))
myWindow.ShowAndRun()
}
复制代码show address?
Toolbar
Toolbarwidget.NewToolbar()widget.ToolbarItemToolbarItemActionSeparatorSpacerwidget.NewToolbarItemAction(resource, callback)widget.NewToolbarSeparator()widget.NewToolbarSpacer()
func main() {
myApp := app.New()
myWindow := myApp.NewWindow("Toolbar")
toolbar := widget.NewToolbar(
widget.NewToolbarAction(theme.DocumentCreateIcon(), func() {
fmt.Println("New document")
}),
widget.NewToolbarSeparator(),
widget.NewToolbarAction(theme.ContentCutIcon(), func() {
fmt.Println("Cut")
}),
widget.NewToolbarAction(theme.ContentCopyIcon(), func() {
fmt.Println("Copy")
}),
widget.NewToolbarAction(theme.ContentPasteIcon(), func() {
fmt.Println("Paste")
}),
widget.NewToolbarSpacer(),
widget.NewToolbarAction(theme.HelpIcon(), func() {
log.Println("Display help")
}),
)
content := fyne.NewContainerWithLayout(
layout.NewBorderLayout(toolbar, nil, nil, nil),
toolbar, widget.NewLabel(`Lorem ipsum dolor,
sit amet consectetur adipisicing elit.
Quidem consectetur ipsam nesciunt,
quasi sint expedita minus aut,
porro iusto magnam ducimus voluptates cum vitae.
Vero adipisci earum iure consequatur quidem.`),
)
myWindow.SetContent(content)
myWindow.ShowAndRun()
}
复制代码BorderLayout
扩展控件
widget.IconExtendBaseWidget()
type tappableIcon struct {
widget.Icon
}
func newTappableIcon(res fyne.Resource) *tappableIcon {
icon := &tappableIcon{}
icon.ExtendBaseWidget(icon)
icon.SetResource(res)
return icon
}
复制代码然后实现相关的接口:
// src/fyne.io/fyne/canvasobject.go
// 鼠标左键
type Tappable interface {
Tapped(*PointEvent)
}
// 鼠标右键或长按
type SecondaryTappable interface {
TappedSecondary(*PointEvent)
}
// 双击
type DoubleTappable interface {
DoubleTapped(*PointEvent)
}
复制代码接口实现:
func (t *tappableIcon) Tapped(e *fyne.PointEvent) {
log.Println("I have been left tapped at", e)
}
func (t *tappableIcon) TappedSecondary(e *fyne.PointEvent) {
log.Println("I have been right tapped at", e)
}
func (t *tappableIcon) DoubleTapped(e *fyne.PointEvent) {
log.Println("I have been double tapped at", e)
}
复制代码最后使用:
func main() {
a := app.New()
w := a.NewWindow("Tappable")
w.SetContent(newTappableIcon(theme.FyneLogo()))
w.Resize(fyne.NewSize(200, 200))
w.ShowAndRun()
}
复制代码运行,点击图标控制台有相应输出:
2020/06/18 06:44:02 I have been left tapped at &{{110 97} {106 93}}
2020/06/18 06:44:03 I have been left tapped at &{{110 97} {106 93}}
2020/06/18 06:44:05 I have been right tapped at &{{88 102} {84 98}}
2020/06/18 06:44:06 I have been right tapped at &{{88 102} {84 98}}
2020/06/18 06:44:06 I have been left tapped at &{{88 101} {84 97}}
2020/06/18 06:44:07 I have been double tapped at &{{88 101} {84 97}}
复制代码fyne.PointEvent
Layout
Layoutfyne.NewContainerWithLayout()
BoxLayout
BoxLayoutfynelayout.NewHBoxLayout()layout.NewVBoxLayout()MinSize().WidthMinSize().Height
垂直布局中的控件都排列在一列中,每个控件的高度等于其内容的最小高度,它们都拥有相同的宽度,即所有控件的最大宽度。
BoxLayoutlayout.NewSpacer()layout.NewSpacer()layout.NewSpacer()layout.NewSpacer()
func main() {
myApp := app.New()
myWindow := myApp.NewWindow("Box Layout")
hcontainer1 := fyne.NewContainerWithLayout(layout.NewHBoxLayout(),
canvas.NewText("left", color.White),
canvas.NewText("right", color.White))
// 左对齐
hcontainer2 := fyne.NewContainerWithLayout(layout.NewHBoxLayout(),
layout.NewSpacer(),
canvas.NewText("left", color.White),
canvas.NewText("right", color.White))
// 右对齐
hcontainer3 := fyne.NewContainerWithLayout(layout.NewHBoxLayout(),
canvas.NewText("left", color.White),
canvas.NewText("right", color.White),
layout.NewSpacer())
// 中间对齐
hcontainer4 := fyne.NewContainerWithLayout(layout.NewHBoxLayout(),
layout.NewSpacer(),
canvas.NewText("left", color.White),
canvas.NewText("right", color.White),
layout.NewSpacer())
// 两边对齐
hcontainer5 := fyne.NewContainerWithLayout(layout.NewHBoxLayout(),
canvas.NewText("left", color.White),
layout.NewSpacer(),
canvas.NewText("right", color.White))
myWindow.SetContent(fyne.NewContainerWithLayout(layout.NewVBoxLayout(),
hcontainer1, hcontainer2, hcontainer3, hcontainer4, hcontainer5))
myWindow.Resize(fyne.NewSize(200, 200))
myWindow.ShowAndRun()
}
复制代码运行效果:
GridLayout
GridLayoutlayout.NewGridLayout(cols)
func main() {
myApp := app.New()
myWindow := myApp.NewWindow("Grid Layout")
img1 := canvas.NewImageFromResource(theme.FyneLogo())
img2 := canvas.NewImageFromResource(theme.FyneLogo())
img3 := canvas.NewImageFromResource(theme.FyneLogo())
myWindow.SetContent(fyne.NewContainerWithLayout(layout.NewGridLayout(2),
img1, img2, img3))
myWindow.Resize(fyne.NewSize(300, 300))
myWindow.ShowAndRun()
}
复制代码运行效果:
该布局有个优势,我们缩放界面时,控件会自动调整大小。试试看~
GridWrapLayout
GridWrapLayoutGridLayoutGridWrapLayoutsizesizesize
func main() {
myApp := app.New()
myWindow := myApp.NewWindow("Grid Wrap Layout")
img1 := canvas.NewImageFromResource(theme.FyneLogo())
img2 := canvas.NewImageFromResource(theme.FyneLogo())
img3 := canvas.NewImageFromResource(theme.FyneLogo())
myWindow.SetContent(
fyne.NewContainerWithLayout(
layout.NewGridWrapLayout(fyne.NewSize(150, 150)),
img1, img2, img3))
myWindow.ShowAndRun()
}
复制代码初始:
加大宽度:
再加大宽度:
BorderLayout
BorderLayoutToolbarBorderLayoutlayout.NewBorderLayout(top, bottom, left, right)
func main() {
myApp := app.New()
myWindow := myApp.NewWindow("Border Layout")
left := canvas.NewText("left", color.White)
right := canvas.NewText("right", color.White)
top := canvas.NewText("top", color.White)
bottom := canvas.NewText("bottom", color.White)
content := widget.NewLabel(`Lorem ipsum dolor,
sit amet consectetur adipisicing elit.
Quidem consectetur ipsam nesciunt,
quasi sint expedita minus aut,
porro iusto magnam ducimus voluptates cum vitae.
Vero adipisci earum iure consequatur quidem.`)
container := fyne.NewContainerWithLayout(
layout.NewBorderLayout(top, bottom, left, right),
top, bottom, left, right, content,
)
myWindow.SetContent(container)
myWindow.ShowAndRun()
}
复制代码效果:
FormLayout
FormLayoutGridLayout
func main() {
myApp := app.New()
myWindow := myApp.NewWindow("Border Layout")
nameLabel := canvas.NewText("Name", color.Black)
nameValue := canvas.NewText("dajun", color.White)
ageLabel := canvas.NewText("Age", color.Black)
ageValue := canvas.NewText("18", color.White)
container := fyne.NewContainerWithLayout(
layout.NewFormLayout(),
nameLabel, nameValue, ageLabel, ageValue,
)
myWindow.SetContent(container)
myWindow.Resize(fyne.NewSize(150, 150))
myWindow.ShowAndRun()
}
复制代码运行效果:
CenterLayout
CenterLayoutCenterLayout
func main() {
myApp := app.New()
myWindow := myApp.NewWindow("Center Layout")
image := canvas.NewImageFromResource(theme.FyneLogo())
image.FillMode = canvas.ImageFillOriginal
text := canvas.NewText("Fyne Logo", color.Black)
container := fyne.NewContainerWithLayout(
layout.NewCenterLayout(),
image, text,
)
myWindow.SetContent(container)
myWindow.ShowAndRun()
}
复制代码运行结果:
Fyne Logotextimage
MaxLayout
MaxLayoutCenterLayoutMaxLayoutCenterLayoutImageFillOriginalMinSize(1, 1)fmt.Println(image.MinSize())
MaxLayout
func main() {
myApp := app.New()
myWindow := myApp.NewWindow("Max Layout")
image := canvas.NewImageFromResource(theme.FyneLogo())
text := canvas.NewText("Fyne Logo", color.Black)
container := fyne.NewContainerWithLayout(
layout.NewMaxLayout(),
image, text,
)
myWindow.SetContent(container)
myWindow.Resize(fyne.Size(200, 200))
myWindow.ShowAndRun()
}
复制代码运行结果:
canvas.TextAlignmentfyne.TextAlignCenter
自定义 Layout
layoutfyne.Layout
// src/fyne.io/fyne/layout.go
type Layout interface {
Layout([]CanvasObject, Size)
MinSize(objects []CanvasObject) Size
}
复制代码fyne.Layout
type diagonal struct {
}
func (d *diagonal) MinSize(objects []fyne.CanvasObject) fyne.Size {
w, h := 0, 0
for _, o := range objects {
childSize := o.MinSize()
w += childSize.Width
h += childSize.Height
}
return fyne.NewSize(w, h)
}
func (d *diagonal) Layout(objects []fyne.CanvasObject, containerSize fyne.Size) {
pos := fyne.NewPos(0, 0)
for _, o := range objects {
size := o.MinSize()
o.Resize(size)
o.Move(pos)
pos = pos.Add(fyne.NewPos(size.Width, size.Height))
}
}
复制代码MinSize()MinSizeLayout()
func main() {
myApp := app.New()
myWindow := myApp.NewWindow("Diagonal Layout")
img1 := canvas.NewImageFromResource(theme.FyneLogo())
img1.FillMode = canvas.ImageFillOriginal
img2 := canvas.NewImageFromResource(theme.FyneLogo())
img2.FillMode = canvas.ImageFillOriginal
img3 := canvas.NewImageFromResource(theme.FyneLogo())
img3.FillMode = canvas.ImageFillOriginal
container := fyne.NewContainerWithLayout(
&diagonal{},
img1, img2, img3,
)
myWindow.SetContent(container)
myWindow.ShowAndRun()
}
复制代码运行结果:
fyne demo
fyne
$ go get fyne.io/fyne/cmd/fyne_demo
$ fyne_demo
复制代码效果图:
fyne
fynefynefynefyne
$ go get fyne.io/fyne/cmd/fyne
复制代码fyne$GOPATH/bin$GOPATH/bin$PATHfyne
静态资源
fynefyne.FyneLogo()image1.png/image2.jpgfyne bundle
$ fyne bundle image1.png >> bundled.go
$ fyne bundle -append image2.jpg >> bundled.go
复制代码-append
// bundled.go
package main
import "fyne.io/fyne"
var resourceImage1Png = &fyne.StaticResource{
StaticName: "image1.png",
StaticContent: []byte{...}}
var resourceImage2Jpg = &fyne.StaticResource{
StaticName: "image2.jpg",
StaticContent: []byte{...}}
复制代码canvas.NewImageFromResource()resourceImage1PngresourceImage2Jpgcanvas.Image
func main() {
myApp := app.New()
myWindow := myApp.NewWindow("Bundle Resource")
img1 := canvas.NewImageFromResource(resourceImage1Png)
img1.FillMode = canvas.ImageFillOriginal
img2 := canvas.NewImageFromResource(resourceImage2Jpg)
img2.FillMode = canvas.ImageFillOriginal
img3 := canvas.NewImageFromResource(theme.FyneLogo())
img3.FillMode = canvas.ImageFillOriginal
container := fyne.NewContainerWithLayout(
layout.NewGridLayout(1),
img1, img2, img3,
)
myWindow.SetContent(container)
myWindow.ShowAndRun()
}
复制代码运行结果:
go run main.gogo run .
theme.FyneLogo()bundled-icons.go
// src/fyne.io/fyne/theme/icons.go
func FyneLogo() fyne.Resource {
return fynelogo
}
// src/fyne.io/fyne/theme/bundled-icons.go
var fynelogo = &fyne.StaticResource{
StaticName: "fyne.png",
StaticContent: []byte{}}
复制代码发布应用程序
fynefyne packagefyne package.exe.app.tar.xz
exe
$ fyne package -os windows -icon icon.jpg
复制代码bundle.exefyne.sysobundle.exe
fyne
总结
fynefynefyne
大家如果发现好玩、好用的 Go 语言库,欢迎到 Go 每日一库 GitHub 上提交 issue????
参考
我
欢迎关注我的微信公众号【GoUpUp】,共同学习,一起进步~