diff --git a/areahandler.go b/areahandler.go index 5cd7987..f16c243 100644 --- a/areahandler.go +++ b/areahandler.go @@ -5,6 +5,10 @@ package ui // #include // #include "ui.h" // extern void doAreaHandlerDraw(uiAreaHandler *, uiArea *, uiAreaDrawParams *); +// extern void doAreaHandlerMouseEvent(uiAreaHandler *, uiArea *, uiAreaMouseEvent *); +// extern void doAreaHandlerMouseCrossed(uiAreaHandler *, uiArea *, int); +// extern void doAreaHandlerDragBroken(uiAreaHandler *, uiArea *); +// extern int doAreaHandlerKeyEvent(uiAreaHandler *, uiArea *, uiAreaKeyEvent *); // static inline uiAreaHandler *allocAreaHandler(void) // { // uiAreaHandler *ah; @@ -13,6 +17,10 @@ package ui // if (ah == NULL) // return NULL; // ah->Draw = doAreaHandlerDraw; +// ah->MouseEvent = doAreaHandlerMouseEvent; +// ah->MouseCrossed = doAreaHandlerMouseCrossed; +// ah->DragBroken = doAreaHandlerDragBroken; +// ah->KeyEvent = doAreaHandlerKeyEvent; // return ah; // } // static inline void freeAreaHandler(uiAreaHandler *ah) @@ -29,6 +37,10 @@ var areahandlers = make(map[*C.uiAreaHandler]AreaHandler) type AreaHandler interface { // TODO document all these Draw(a *Area, dp *AreaDrawParams) + MouseEvent(a *Area, me *AreaMouseEvent) + MouseCrossed(a *Area, left bool) + DragBroken(a *Area) + KeyEvent(a *Area, ke *AreaKeyEvent) (handled bool) } func registerHandler(ah AreaHandler) *C.uiAreaHandler { @@ -46,14 +58,12 @@ func unregisterAreaHandler(uah *C.uiAreaHandler) { type AreaDrawParams struct { // TODO document all these Context *DrawContext - ClientWidth float64 - ClientHeight float64 + AreaWidth float64 + AreaHeight float64 ClipX float64 ClipY float64 ClipWidth float64 ClipHeight float64 - HScrollPos int - VScrollPos int } //export doAreaHandlerDraw @@ -62,14 +72,150 @@ func doAreaHandlerDraw(uah *C.uiAreaHandler, ua *C.uiArea, udp *C.uiAreaDrawPara a := areas[ua] dp := &AreaDrawParams{ Context: &DrawContext{udp.Context}, - ClientWidth: float64(udp.ClientWidth), - ClientHeight: float64(udp.ClientHeight), + AreaWidth: float64(udp.AreaWidth), + AreaHeight: float64(udp.AreaHeight), ClipX: float64(udp.ClipX), ClipY: float64(udp.ClipY), ClipWidth: float64(udp.ClipWidth), ClipHeight: float64(udp.ClipHeight), - HScrollPos: int(udp.HScrollPos), - VScrollPos: int(udp.VScrollPos), } ah.Draw(a, dp) } + +// TODO document all these +type AreaMouseEvent struct { + X float64 + Y float64 + AreaWidth float64 + AreaHeight float64 + Down uint + Up uint + Count uint + Modifiers Modifiers + Held []uint +} + +func appendBits(out []uint, held C.uint64_t) []uint { + n := uint(1) + for i := 0; i < 64; i++ { + if held & 1 != 0 { + out = append(out, n) + } + held >>= 1 + n++ + } + return out +} + +//export doAreaHandlerMouseEvent +func doAreaHandlerMouseEvent(uah *C.uiAreaHandler, ua *C.uiArea, ume *C.uiAreaMouseEvent) { + ah := areahandlers[uah] + a := areas[ua] + me := &AreaMouseEvent{ + X: float64(ume.X), + Y: float64(ume.Y), + AreaWidth: float64(ume.AreaWidth), + AreaHeight: float64(ume.AreaHeight), + Down: uint(ume.Down), + Up: uint(ume.Up), + Count: uint(ume.Count), + Modifiers: Modifiers(ume.Modifiers), + Held: make([]uint, 0, 64), + } + me.Held = appendBits(me.Held, ume.Held1To64) + ah.MouseEvent(a, me) +} + +//export doAreaHandlerMouseCrossed +func doAreaHandlerMouseCrossed(uah *C.uiAreaHandler, ua *C.uiArea, left C.int) { + ah := areahandlers[uah] + a := areas[ua] + ah.MouseCrossed(a, tobool(left)) +} + +//export doAreaHandlerDragBroken +func doAreaHandlerDragBroken(uah *C.uiAreaHandler, ua *C.uiArea) { + ah := areahandlers[uah] + a := areas[ua] + ah.DragBroken(a) +} + +// TODO document all these +type AreaKeyEvent struct { + Key rune + ExtKey ExtKey + Modifier Modifiers + Modifiers Modifiers + Up bool +} + +//export doAreaHandlerKeyEvent +func doAreaHandlerKeyEvent(uah *C.uiAreaHandler, ua *C.uiArea, uke *C.uiAreaKeyEvent) C.int { + ah := areahandlers[uah] + a := areas[ua] + ke := &AreaKeyEvent{ + Key: rune(uke.Key), + ExtKey: ExtKey(uke.ExtKey), + Modifier: Modifiers(uke.Modifier), + Modifiers: Modifiers(uke.Modifiers), + Up: tobool(uke.Up), + } + return frombool(ah.KeyEvent(a, ke)) +} + +// TODO document +// +// Note: these must be numerically identical to their libui equivalents. +type Modifiers uint +const ( + Ctrl Modifiers = 1 << iota + Alt + Shift + Super +) + +// TODO document +// +// Note: these must be numerically identical to their libui equivalents. +type ExtKey int +const ( + Escape ExtKey = iota + 1 + Insert // equivalent to "Help" on Apple keyboards + Delete + Home + End + PageUp + PageDown + Up + Down + Left + Right + F1 // F1..F12 are guaranteed to be consecutive + F2 + F3 + F4 + F5 + F6 + F7 + F8 + F9 + F10 + F11 + F12 + N0 // numpad keys; independent of Num Lock state + N1 // N0..N9 are guaranteed to be consecutive + N2 + N3 + N4 + N5 + N6 + N7 + N8 + N9 + NDot + NEnter + NAdd + NSubtract + NMultiply + NDivide +)