Added Area resizing. Everything mostly works, but not making things smaller...
This commit is contained in:
parent
0cc13633cb
commit
a41f582866
37
area.go
37
area.go
|
@ -21,12 +21,14 @@ import (
|
||||||
// in platform-native ways is painful.
|
// in platform-native ways is painful.
|
||||||
// [Use TextArea instead, providing a TextAreaHandler.]
|
// [Use TextArea instead, providing a TextAreaHandler.]
|
||||||
//
|
//
|
||||||
// To facilitate development and debugging, for the time being, Areas have a fixed size of 320x240 and only work on GTK+.
|
// To facilitate development and debugging, for the time being, Areas only work on GTK+.
|
||||||
type Area struct {
|
type Area struct {
|
||||||
lock sync.Mutex
|
lock sync.Mutex
|
||||||
created bool
|
created bool
|
||||||
sysData *sysData
|
sysData *sysData
|
||||||
handler AreaHandler
|
handler AreaHandler
|
||||||
|
initwidth int
|
||||||
|
initheight int
|
||||||
}
|
}
|
||||||
|
|
||||||
// AreaHandler represents the events that an Area should respond to.
|
// AreaHandler represents the events that an Area should respond to.
|
||||||
|
@ -210,18 +212,34 @@ const (
|
||||||
// TODO add Super
|
// TODO add Super
|
||||||
)
|
)
|
||||||
|
|
||||||
// NewArea creates a new Area.
|
// NewArea creates a new Area with the given size and handler.
|
||||||
// It panics if handler is nil.
|
// It panics if handler is nil.
|
||||||
func NewArea(handler AreaHandler) *Area {
|
func NewArea(width int, height int, handler AreaHandler) *Area {
|
||||||
if handler == nil {
|
if handler == nil {
|
||||||
panic("handler passed to NewArea() must not be nil")
|
panic("handler passed to NewArea() must not be nil")
|
||||||
}
|
}
|
||||||
return &Area{
|
return &Area{
|
||||||
sysData: mksysdata(c_area),
|
sysData: mksysdata(c_area),
|
||||||
handler: handler,
|
handler: handler,
|
||||||
|
initwidth: width,
|
||||||
|
initheight: height,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// SetSize sets the Area's internal drawing size.
|
||||||
|
// It has no effect on the actual control size.
|
||||||
|
func (a *Area) SetSize(width int, height int) {
|
||||||
|
a.lock.Lock()
|
||||||
|
defer a.lock.Unlock()
|
||||||
|
|
||||||
|
if a.created {
|
||||||
|
a.sysData.setAreaSize(width, height)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
a.initwidth = width
|
||||||
|
a.initheight = height
|
||||||
|
}
|
||||||
|
|
||||||
func (a *Area) make(window *sysData) error {
|
func (a *Area) make(window *sysData) error {
|
||||||
a.lock.Lock()
|
a.lock.Lock()
|
||||||
defer a.lock.Unlock()
|
defer a.lock.Unlock()
|
||||||
|
@ -231,6 +249,7 @@ func (a *Area) make(window *sysData) error {
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
a.sysData.setAreaSize(a.initwidth, a.initheight)
|
||||||
a.created = true
|
a.created = true
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
|
@ -24,7 +24,7 @@ import "C"
|
||||||
|
|
||||||
func gtkAreaNew() *gtkWidget {
|
func gtkAreaNew() *gtkWidget {
|
||||||
drawingarea := C.gtk_drawing_area_new()
|
drawingarea := C.gtk_drawing_area_new()
|
||||||
C.gtk_widget_set_size_request(drawingarea, 320, 240)
|
C.gtk_widget_set_size_request(drawingarea, 100, 100) // default initial size (TODO do we need it?); use C. to avoid casting drawingarea
|
||||||
// we need to explicitly subscribe to mouse events with GtkDrawingArea
|
// we need to explicitly subscribe to mouse events with GtkDrawingArea
|
||||||
C.gtk_widget_add_events(drawingarea,
|
C.gtk_widget_add_events(drawingarea,
|
||||||
C.GDK_BUTTON_PRESS_MASK | C.GDK_BUTTON_RELEASE_MASK | C.GDK_POINTER_MOTION_MASK | C.GDK_BUTTON_MOTION_MASK)
|
C.GDK_BUTTON_PRESS_MASK | C.GDK_BUTTON_RELEASE_MASK | C.GDK_POINTER_MOTION_MASK | C.GDK_BUTTON_MOTION_MASK)
|
||||||
|
|
|
@ -217,3 +217,7 @@ func gtk_progress_bar_set_fraction(w *gtkWidget, percent int) {
|
||||||
func gtk_progress_bar_pulse(w *gtkWidget) {
|
func gtk_progress_bar_pulse(w *gtkWidget) {
|
||||||
C.gtk_progress_bar_pulse(togtkprogressbar(w))
|
C.gtk_progress_bar_pulse(togtkprogressbar(w))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func gtk_widget_queue_draw(widget *gtkWidget) {
|
||||||
|
C.gtk_widget_queue_draw(togtkwidget(widget))
|
||||||
|
}
|
||||||
|
|
|
@ -76,6 +76,9 @@ func (c *cSysData) setProgress(int) {
|
||||||
func (c *cSysData) len() int {
|
func (c *cSysData) len() int {
|
||||||
panic(runtime.GOOS + " sysData does not define len()")
|
panic(runtime.GOOS + " sysData does not define len()")
|
||||||
}
|
}
|
||||||
|
func (c *cSysData) setAreaSize(int, int) {
|
||||||
|
panic(runtime.GOOS + " sysData does not define setAreaSize()")
|
||||||
|
}
|
||||||
|
|
||||||
// signal sends the event signal. This raise is done asynchronously to avoid deadlocking the UI task.
|
// signal sends the event signal. This raise is done asynchronously to avoid deadlocking the UI task.
|
||||||
// Thanks skelterjohn for this techinque: if we can't queue any more events, drop them
|
// Thanks skelterjohn for this techinque: if we can't queue any more events, drop them
|
||||||
|
|
|
@ -350,3 +350,15 @@ func (s *sysData) len() int {
|
||||||
}
|
}
|
||||||
return <-ret
|
return <-ret
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (s *sysData) setAreaSize(width int, height int) {
|
||||||
|
ret := make(chan struct{})
|
||||||
|
defer close(ret)
|
||||||
|
uitask <- func() {
|
||||||
|
c := gtkAreaGetControl(s.widget)
|
||||||
|
gtk_widget_set_size_request(c, width, height)
|
||||||
|
gtk_widget_queue_draw(c) // force repaint (TODO doesn't have an effect when shrinking?)
|
||||||
|
ret <- struct{}{}
|
||||||
|
}
|
||||||
|
<-ret
|
||||||
|
}
|
||||||
|
|
24
test/main.go
24
test/main.go
|
@ -10,6 +10,7 @@ import (
|
||||||
_ "image/png"
|
_ "image/png"
|
||||||
"bytes"
|
"bytes"
|
||||||
"time"
|
"time"
|
||||||
|
"strconv"
|
||||||
. "github.com/andlabs/ui"
|
. "github.com/andlabs/ui"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -158,13 +159,25 @@ func areaTest() {
|
||||||
img := image.NewNRGBA(ximg.Bounds())
|
img := image.NewNRGBA(ximg.Bounds())
|
||||||
draw.Draw(img, img.Rect, ximg, image.ZP, draw.Over)
|
draw.Draw(img, img.Rect, ximg, image.ZP, draw.Over)
|
||||||
w := NewWindow("Area Test", 100, 100)
|
w := NewWindow("Area Test", 100, 100)
|
||||||
a := NewArea(&areaHandler{
|
a := NewArea(320, 240, &areaHandler{
|
||||||
img: img,
|
img: img,
|
||||||
})
|
})
|
||||||
timedisp := NewLabel("")
|
timedisp := NewLabel("")
|
||||||
timechan := time.Tick(time.Second)
|
timechan := time.Tick(time.Second)
|
||||||
|
widthbox := NewLineEdit("320")
|
||||||
|
heightbox := NewLineEdit("240")
|
||||||
|
resize := NewButton("Resize")
|
||||||
|
sizeStack := NewHorizontalStack(widthbox, heightbox, resize)
|
||||||
|
sizeStack.SetStretchy(0)
|
||||||
|
sizeStack.SetStretchy(1)
|
||||||
|
sizeStack.SetStretchy(2)
|
||||||
|
sizeStack = NewHorizontalStack(sizeStack, Space(), Space())
|
||||||
|
sizeStack.SetStretchy(0)
|
||||||
|
sizeStack.SetStretchy(1)
|
||||||
|
sizeStack.SetStretchy(2)
|
||||||
layout := NewVerticalStack(a,
|
layout := NewVerticalStack(a,
|
||||||
NewHorizontalStack(timedisp))
|
NewHorizontalStack(timedisp),
|
||||||
|
sizeStack)
|
||||||
layout.SetStretchy(0)
|
layout.SetStretchy(0)
|
||||||
err = w.Open(layout)
|
err = w.Open(layout)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -176,6 +189,13 @@ func areaTest() {
|
||||||
return
|
return
|
||||||
case t := <-timechan:
|
case t := <-timechan:
|
||||||
timedisp.SetText(t.String())
|
timedisp.SetText(t.String())
|
||||||
|
case <-resize.Clicked:
|
||||||
|
width, err := strconv.Atoi(widthbox.Text())
|
||||||
|
if err != nil { println(err); continue }
|
||||||
|
height, err := strconv.Atoi(heightbox.Text())
|
||||||
|
if err != nil { println(err); continue }
|
||||||
|
println(width, height)
|
||||||
|
a.SetSize(width, height)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue