diff --git a/gui.s b/gui.s index ccc642b..0c5399a 100644 --- a/gui.s +++ b/gui.s @@ -54,6 +54,8 @@ main: jsr WGEnableMouse keyLoop: + jsr WGPendingViewAction + lda KBD bpl keyLoop sta KBDSTRB @@ -193,6 +195,10 @@ WGInit_clearMemLoop: dey bpl WGInit_clearMemLoop + lda #$ff + sta WG_PENDINGACTIONVIEW + sta WG_FOCUSVIEW + RESTORE_AXY rts diff --git a/guidemo.dsk b/guidemo.dsk index d238a7e..55bd8c7 100644 Binary files a/guidemo.dsk and b/guidemo.dsk differ diff --git a/macros.s b/macros.s index bd41338..15949eb 100644 --- a/macros.s +++ b/macros.s @@ -60,6 +60,18 @@ .endmacro +.macro SAVE_XY ; Saves X and Y index + phx + phy +.endmacro + + +.macro RESTORE_XY ; Restores X and Y index + ply + plx +.endmacro + + .macro SAVE_ZPP ; Saves Zero Page locations we use for parameters lda PARAM0 pha @@ -134,9 +146,9 @@ ; Rendering macros ; -.macro LDY_ACTIVEVIEW - lda WG_ACTIVEVIEW ; Find our new view record - asl + +.macro LDY_AVIEW + asl ; Find our new view record asl asl asl ; Records are 16 bytes wide @@ -144,6 +156,12 @@ .endmacro +.macro LDY_ACTIVEVIEW + lda WG_ACTIVEVIEW ; Find our new view record + LDY_AVIEW +.endmacro + + .macro LDX_ACTIVEVIEW lda WG_ACTIVEVIEW ; Find our new view record asl @@ -156,11 +174,7 @@ .macro LDY_FOCUSVIEW lda WG_FOCUSVIEW ; Find our new view record - asl - asl - asl - asl ; Records are 16 bytes wide - tay + LDY_AVIEW .endmacro diff --git a/memory.s b/memory.s index 316b46b..7c5c69c 100644 --- a/memory.s +++ b/memory.s @@ -54,6 +54,9 @@ WG_ACTIVEVIEW: WG_FOCUSVIEW: .byte 0 +WG_PENDINGACTIONVIEW: +.byte 0 + WG_VIEWCLIP: ; X0,Y0,X1,Y1. Edges of current window, in view space, right span .byte 0,0,0,0,0 diff --git a/mouse.s b/mouse.s index d2ea50b..dc22cd8 100644 --- a/mouse.s +++ b/mouse.s @@ -323,7 +323,15 @@ WGMouseInterruptHandler: bne WGMouseInterruptHandler_intDone WGMouseInterruptHandler_button: + lda WG_MOUSEPOS_X + sta PARAM0 + lda WG_MOUSEPOS_Y + sta PARAM1 + jsr WGViewFromPoint + bmi WGMouseInterruptHandler_intDone + ; Button was clicked in a view, so make a note of it + sta WG_PENDINGACTIONVIEW WGMouseInterruptHandler_intDone: jsr WGDrawPointer ; Redraw the pointer @@ -348,6 +356,8 @@ WGMouseInterruptHandler_disregard: WGUndrawPointer: SAVE_AXY + lda WG_MOUSEACTIVE + beq WGUndrawPointer_done ; Mouse not enabled lda WG_MOUSEBG beq WGUndrawPointer_done ; Mouse pointer has never rendered @@ -403,6 +413,9 @@ WGUndrawPointer_done: WGDrawPointer: SAVE_AXY + lda WG_MOUSEACTIVE + beq WGDrawPointer_done ; Mouse not enabled + ldx WG_MOUSEPOS_Y cpx #24 bcs WGDrawPointer_done diff --git a/views.s b/views.s index d0fd3d1..4340d74 100644 --- a/views.s +++ b/views.s @@ -627,6 +627,9 @@ WGViewFocus: lda WG_ACTIVEVIEW ; Stash current selection pha + lda WG_FOCUSVIEW + bmi WGViewFocus_noCurrent + LDY_FOCUSVIEW ; Unfocus current view lda WG_VIEWRECORDS+9,y and #%01111111 @@ -636,6 +639,7 @@ WGViewFocus: jsr WGSelectView jsr WGPaintView +WGViewFocus_noCurrent: pla sta WG_FOCUSVIEW ; Focus on our original selection jsr WGSelectView @@ -652,6 +656,34 @@ WGViewFocus: rts +;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; +; WGViewUnfocus +; Unfocuses all views +; Side effects: Changes selected view, repaints some views +; +WGViewUnfocus: + pha + + lda WG_FOCUSVIEW + bmi WGViewUnfocus_done + + LDY_FOCUSVIEW ; Unfocus current view + lda WG_VIEWRECORDS+9,y + and #%01111111 + sta WG_VIEWRECORDS+9,y + + lda WG_FOCUSVIEW + jsr WGSelectView + jsr WGPaintView + + lda #$ff + sta WG_FOCUSVIEW + +WGViewUnfocus_done: + pla + rts + + ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ; WGViewFocusNext ; Shifts focus to the next view @@ -660,6 +692,9 @@ WGViewFocus: WGViewFocusNext: SAVE_AY + lda WG_FOCUSVIEW + bmi WGViewFocusNext_loop + LDY_FOCUSVIEW ; Unfocus current view lda WG_VIEWRECORDS+9,y and #%01111111 @@ -706,6 +741,9 @@ WGViewFocusNext_focus: WGViewFocusPrev: SAVE_AXY + lda WG_FOCUSVIEW + bmi WGViewFocusPrev_hadNone + LDY_FOCUSVIEW ; Unfocus current view lda WG_VIEWRECORDS+9,y and #%01111111 @@ -719,6 +757,7 @@ WGViewFocusPrev_loop: dec WG_FOCUSVIEW ; Decrement and wrap bpl WGViewFocusPrev_wantFocus +WGViewFocusPrev_hadNone: ldx #$f WGViewFocusPrev_findEndLoop: stx WG_FOCUSVIEW @@ -760,6 +799,9 @@ WGViewFocusPrev_focus: WGViewFocusAction: SAVE_AY + lda WG_FOCUSVIEW + bmi WGViewFocusAction_done + LDY_FOCUSVIEW lda WG_VIEWRECORDS+4,y ; What kind of view is it? and #$f ; Mask off flag bits @@ -824,6 +866,46 @@ WGViewFocusAction_knownRTS: rts +;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; +; WGPendingViewAction +; Performs the action of the pending view, if any +; OUT V : Set if the caller should perform an Applesoft GOSUB +; Side effects: Changes selected view, Repaints some views +; +WGPendingViewAction: + pha + + lda WG_PENDINGACTIONVIEW + bmi WGPendingViewAction_done + + jsr WGUndrawPointer + + jsr WGSelectView + jsr WGViewFocus + jsr WGViewFocusAction + jsr WGViewUnfocus + + jsr WGDrawPointer ; Leave pointer hidden, but ensure + jsr WGUndrawPointer ; Background is correct when it moves next + + lda #$ff + sta WG_PENDINGACTIONVIEW + +WGPendingViewAction_done: + pla + rts + + +;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; +; WGPendingView +; Returns the view that is currently pending +; OUT A : Pending view ID, or $ff if none +; +WGPendingView: + lda WG_PENDINGACTIONVIEW + rts + + ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ; WGViewSetTitle ; Sets the title of the active view @@ -1114,6 +1196,61 @@ WGViewPaintAll_done: rts +;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; +; WGViewFromPoint +; Finds a view containing the given point +; PARAM0:X +; PARAM1:Y +; OUT A: View ID (or $ff if no match) +WGViewFromPoint: + SAVE_XY + + ldx #$f ; Scan views backwards, because controls are usually at the end + +WGViewFromPoint_loop: + txa + LDY_AVIEW + + lda WG_VIEWRECORDS+2,y + beq WGViewFromPoint_loopNext ; Not an allocated view + + lda PARAM0 ; Check left edge + cmp WG_VIEWRECORDS+0,y + bcc WGViewFromPoint_loopNext + + lda PARAM1 ; Check top edge + cmp WG_VIEWRECORDS+1,y + bcc WGViewFromPoint_loopNext + + lda WG_VIEWRECORDS+0,y ; Check right edge + clc + adc WG_VIEWRECORDS+2,y + cmp PARAM0 + bcc WGViewFromPoint_loopNext + beq WGViewFromPoint_loopNext + + lda WG_VIEWRECORDS+1,y ; Check bottom edge + clc + adc WG_VIEWRECORDS+3,y + cmp PARAM1 + bcc WGViewFromPoint_loopNext + beq WGViewFromPoint_loopNext + + txa ; Found a match + RESTORE_XY + rts + +WGViewFromPoint_loopNext: + dex + bmi WGViewFromPoint_noMatch + bra WGViewFromPoint_loop + +WGViewFromPoint_noMatch: + lda #$ff + RESTORE_XY + rts + + ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ; cacheClipPlanes ; Internal routine to cache the clipping planes for the view