83 lines
1.7 KiB
Go
83 lines
1.7 KiB
Go
package buttons
|
|
|
|
import (
|
|
"image/color"
|
|
|
|
"git.vezzani.net/ben/games/common/elements/v1"
|
|
"git.vezzani.net/ben/games/common/elements/v1/blocks"
|
|
"git.vezzani.net/ben/games/common/elements/v1/mouse"
|
|
"git.vezzani.net/ben/games/common/ux/v1"
|
|
|
|
"github.com/hajimehoshi/ebiten/v2"
|
|
"github.com/hajimehoshi/ebiten/v2/text"
|
|
"golang.org/x/image/font"
|
|
)
|
|
|
|
func New(ops ...OptFunc) elements.Element {
|
|
b := Button{
|
|
Block: blocks.Block{},
|
|
font: ux.FontFace,
|
|
color: ux.FontColor,
|
|
}
|
|
for op := range ops {
|
|
ops[op](&b)
|
|
}
|
|
|
|
return &b
|
|
}
|
|
|
|
type Button struct {
|
|
blocks.Block
|
|
|
|
label string
|
|
font font.Face
|
|
color color.Color
|
|
|
|
onClick func(ms mouse.State)
|
|
onMouseDown func(ms mouse.State)
|
|
onMouseUp func(ms mouse.State)
|
|
}
|
|
|
|
func (b *Button) Draw(screen *ebiten.Image) {
|
|
b.Block.Draw(screen)
|
|
b.drawLabel(screen)
|
|
}
|
|
|
|
func (b *Button) drawLabel(screen *ebiten.Image) {
|
|
if b.label != "" {
|
|
strBounds, _ := font.BoundString(b.font, b.label)
|
|
|
|
textWidth := strBounds.Max.X - strBounds.Min.X
|
|
textHeight := strBounds.Max.Y - strBounds.Min.Y
|
|
|
|
bnd := b.Bounds()
|
|
tx := bnd.Min.X + (bnd.Width / 2) - (textWidth / 2).Round()
|
|
ty := bnd.Min.Y + (bnd.Height / 2) - (textHeight / 2).Round()
|
|
|
|
text.Draw(screen, b.label, b.font, tx, ty, b.color)
|
|
|
|
}
|
|
}
|
|
|
|
func (b *Button) HandleMouseEvent(ms mouse.State) bool {
|
|
bnd := b.Bounds()
|
|
|
|
if !bnd.Contains(ms.Point()) {
|
|
return false
|
|
}
|
|
|
|
switch {
|
|
case b.onClick != nil && (ms.RightClicked || ms.LeftClicked):
|
|
b.onClick(ms)
|
|
return true
|
|
case b.onMouseUp != nil && (ms.RightChanged && !ms.RightDown || ms.LeftChanged && !ms.LeftDown):
|
|
b.onMouseUp(ms)
|
|
return true
|
|
case b.onMouseDown != nil && (ms.RightChanged && ms.RightDown || ms.LeftChanged && ms.LeftDown):
|
|
b.onMouseDown(ms)
|
|
return true
|
|
}
|
|
|
|
return false
|
|
}
|