gui2: added Button, RootWindow. Touch now works again.

This commit is contained in:
Martin Preuss
2026-01-19 18:33:36 +01:00
parent 715c4f22c4
commit edc291261f
6 changed files with 959 additions and 527 deletions

View File

@@ -118,85 +118,6 @@ Widget_OnCreate:
; ---------------------------------------------------------------------------
; @routine Widget_OnTouch @global
;
; @param Z byte address of widget object (for LPM!)
; @param xl param1
; @param xh param2
; @return CFLAG set if signal handled
; @clobbers any, !Z
Widget_OnTouch:
; check whether inputs are handled by this widget
adiw zh:zl, WIDGET_OFFS_OPTS_LO
lpm r16, Z
sbiw zh:zl, WIDGET_OFFS_OPTS_LO
andi r16, (1<<WIDGET_OPTSLO_INPUT_BIT)
clc
breq Widget_OnTouch_ret
rcall Widget_GetSdramPtr
; check whether widget is active
ldd r17, Y+WIDGET_SD_OFFS_FLAGS
andi r17, (1<<WIDGET_FLAGS_ACTIVE_BIT)
breq Widget_OnTouch_secRet ; nope, jmp
; read touch signal data from X
ld r18, X+ ; WIDGET_DATA_TOUCH_OFFS_X_LO
ld r19, X+ ; WIDGET_DATA_TOUCH_OFFS_X_HI
ld r20, X+ ; WIDGET_DATA_TOUCH_OFFS_Y_LO
ld r21, X+ ; WIDGET_DATA_TOUCH_OFFS_Z_HI
ld r22, X+ ; WIDGET_DATA_TOUCH_OFFS_STATE
; check for change of touch press
mov r16, r22
andi r16, (1<<DISPLAY_IFLAGS_CHGPRESS_BIT)
breq Widget_OnTouch_secRet ; no press change, jmp
; check for position inside this widget
rcall widgetLoadCoordsForFullWidget
rcall Widget_MakeAbsPos ; (R16, R17)
rcall Widget_IsPointInRect ; (R16, R17)
sbci r16, 0 ; r16=ff if touched inside, 0 otherwise
; touch changed, check whether touch came down or up
mov r18, r22
andi r18, (1<<DISPLAY_IFLAGS_PRESSED_BIT)
breq Widget_OnTouch_up
; touch came down
ldd r17, Y+WIDGET_SD_OFFS_FLAGS
andi r17, (1<<WIDGET_FLAGS_PRESSED_BIT)
brne Widget_OnTouch_secRet ; already down
tst r16 ; down inside this widget?
brne Widget_OnTouch_secRet ; nope, jmp
ldd r17, Y+WIDGET_SD_OFFS_FLAGS
ori r17, (1<<WIDGET_FLAGS_PRESSED_BIT) | (1<<WIDGET_FLAGS_DIRTY_BIT) ; up, dirty
std Y+WIDGET_SD_OFFS_FLAGS, r17
rjmp Widget_OnTouch_secRet
Widget_OnTouch_up:
ldd r17, Y+WIDGET_SD_OFFS_FLAGS
andi r17, (1<<WIDGET_FLAGS_PRESSED_BIT)
breq Widget_OnTouch_secRet ; already up
ldd r17, Y+WIDGET_SD_OFFS_FLAGS
cbr r17, (1<<WIDGET_FLAGS_PRESSED_BIT) ; up
ori r17, (1<<WIDGET_FLAGS_DIRTY_BIT)
std Y+WIDGET_SD_OFFS_FLAGS, r17
tst r16 ; was touch lost inside this widget?
brne Widget_OnTouch_secRet ; nope, jmp
; emit "CLICKED" signal
ldi r16, WIDGET_SIGNAL_CLICKED
rcall OBJ_EmitSignal
Widget_OnTouch_secRet:
sec
Widget_OnTouch_ret:
ret
; @end
; ---------------------------------------------------------------------------
; @routine Widget_OnDraw @global
;
@@ -278,8 +199,8 @@ Widget_IsPointInRect:
mov r16, r20 ; checkY-widgetY
mov r17, r21
sub r16, r8
sbc r17, r9
sub r16, r6
sbc r17, r7
brcs Widget_IsPointInRect_no ; jmp if above widget
sub r16, r10 ; sub height
sbc r17, r11
@@ -348,6 +269,110 @@ Widget_GetSdramPtr:
; ---------------------------------------------------------------------------
; @routine Widget_GetRootWidget @global
;
; @param Z byte address of object (for LPM!)
; @return Z byte address pointer to RootWidget
; @clobbers r18, r19
Widget_GetRootWidget:
rcall OBJ_IsObject ; (none)
brcc Widget_GetRootWidget_end
Widget_GetRootWidget_loop:
bigcall OBJ_GetParent ; (none)
brcc Widget_GetRootWidget_found ; no parent, return current Z
mov zl, r18
mov zh, r19
rjmp Widget_GetRootWidget_loop
Widget_GetRootWidget_found:
sec
Widget_GetRootWidget_end:
ret
; @end
; ---------------------------------------------------------------------------
; @routine Widget_GetApp @global
;
; @param Z byte address of object (for LPM!)
; @return R19:R18 byte address pointer to GuiApp
; @clobbers (r18, r19)
Widget_GetApp:
rcall OBJ_IsObject ; (none)
brcc Widget_GetApp_ret
push zl
push zh
rcall Widget_GetRootWidget ; Z:=rootWidget (r18, r19)
brcc Widget_GetApp_popRet
rcall RootWidget_GetApp ; R19:R18=app (none)
Widget_GetApp_popRet:
pop zh
pop zl
Widget_GetApp_ret:
ret
; @end
; ---------------------------------------------------------------------------
; @routine Widget_GrabTouchEvents @global
;
; Let this widget grab touch events until ungrabbed.
;
; @param Z byte address of object (for LPM!)
; @return CFLAG set if grabbed, cleared on error
; @clobbers X, Y (r16, r17, r18, r19)
Widget_GrabTouchEvents:
push zl
push zh
mov xl, zl
mov xh, zh
rcall Widget_GetApp ; R19:R18:=app
brcc Widget_GrabTouchEvents_popRet
mov zl, r18
mov zh, r19
bigcall GuiApp_GrabTouchEvents ; (R16, R17)
Widget_GrabTouchEvents_popRet:
pop zh
pop zl
ret
; @end
; ---------------------------------------------------------------------------
; @routine Widget_UngrabTouchEvents @global
;
; Let this widget un-grab touch events.
;
; @param Z byte address of object (for LPM!)
; @return CFLAG set if ungrabbed, cleared on error
; @clobbers X (r16, r17, r18, r19)
Widget_UngrabTouchEvents:
push zl
push zh
mov xl, zl
mov xh, zh
rcall Widget_GetApp ; R19:R18:=app
brcc Widget_UngrabTouchEvents_popRet
mov zl, r18
mov zh, r19
bigcall GuiApp_UngrabTouchEvents ; (R16, R17)
Widget_UngrabTouchEvents_popRet:
pop zh
pop zl
ret
; @end
; ---------------------------------------------------------------------------
; @routine Widget_AddFlagsDown @global
;
@@ -1264,13 +1289,14 @@ Widget_CalcStringWidthFLASH_done:
; ---------------------------------------------------------------------------
; @routine Widget_AlignPosXY
; @routine widgetLoadCoordsForFullWidget
;
; @param Z byte address of widget object (for LPM!)
; @return r5:r4 X (0)
; @return r7:r6 Y (0)
; @return r9:r8 widget width
; @return r11:R10 widget height
; @clobbers none
widgetLoadCoordsForFullWidget:
clr r4