home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Fish 'n' More 2
/
fishmore-publicdomainlibraryvol.ii1991xetec.iso
/
dirs
/
popupmenu_422.lzh
/
PopUpMenu
/
Source
/
PopUpMenu.a
< prev
next >
Wrap
Text File
|
1990-12-31
|
76KB
|
2,827 lines
opt l+,c+,d+,y+
opt ow1+,ow2+,ow3+,ow4+,ow5+,ow6+
INCLUDE "exec/types.i"
INCLUDE "PopUpMenu.i"
xdef @PopUpMenu
xdef @FindMenuPtr
xdef @FindItemNr
xdef @QueTimer
xdef @HighLightCurrItemBehind
xdef @FindMouseItem
xdef @MouseInWindow
xdef @OpenItemWindow
xdef @CloseItemWindow
xdef @DrawAllItems
xdef @SwapBits
xdef @HighLightItem
xdef @ToggleMenu
xdef @MySetMenuStrip
xdef @MyClearMenuStrip
xdef @MyOnMenu
xdef @MyOffMenu
xdef @SelectItem
xdef @FinalSelect
xref _AmigaKeyHighRes
xref _AmigaKeyLoRes
xref _SubItemPointerH
xref _SubItemPointerL
BORDERSIZE EQU 2
OVERLAP EQU 7
section text,code
**********************************************
* PopUpMenu(InputSignals) *
* *
* Input: *
* InputSignals - Inputhandler signals. *
* Output: *
* none *
* Functions: *
* FindWindow, InitGlobals, OpenMenuWindow, *
* QueTimer, SelectItem, FinalSelect, *
* SwapBits, FindWindow, RemoveBitMap, *
* CloseItemWindow, TellWindow *
**********************************************
@PopUpMenu: MOVEM.L D2-D7/A2-A3/A5-A6,-(SP)
MOVEA.L A0,A3
* ------------ ObtainSemaphore(&PopUpSemaphore)
LEA _PopUpSemaphore(A4),A0
MOVEA.L (AbsExecBase).W,A6
JSR _LVOObtainSemaphore(A6)
* ------------ Is Window still open ?
JSR @FindWindow(PC)
TST.W D0
BEQ.W Abort
* ------------ Lock the screen.
MOVEA.L _Screen(A4),A2
ADDA.W #sc_LayerInfo,A2
MOVEA.L A2,A0
MOVEA.L _LayersBase(A4),A6
JSR _LVOLockLayers(A6)
* ------------ Init the global variables
* ------------ ItemWindow.BitMapOk = FALSE
MOVEQ.L #0,D0
MOVE.W D0,_ItemWindow(A4)
* ------------ SubWindow.BitMapOk = FALSE
MOVE.W D0,(A4) * _SubWindow
* ------------ MenuWindow.BitMapOk = FALSE
MOVE.W D0,_MenuWindow(A4)
* ------------ CurrentMenuNr = 0
MOVE.W D0,_CurrentMenuNr(A4)
* ------------ CurrentMenuPtr = NULL
MOVE.L D0,_CurrentMenuPtr(A4)
* ------------ CurrentItem = NULL
MOVE.L D0,_CurrentItem(A4)
* ------------ CurrentSubItem = NULL
MOVE.L D0,_CurrentSubItem(A4)
* ------------ ScreenType = (Screen->ViewPort.Modes & HIRES) == 0
MOVEA.L _Screen(A4),A5
BTST #7,sc_ViewPort+vp_Modes(A5)
BNE.B 1$
MOVEQ.L #1,D0
1$ MOVE.W D0,_ScreenType(A4)
* ------------ Menues = ActiveWindow->MenuStrip
MOVEA.L _ActiveWindow(A4),A0
MOVE.L wd_MenuStrip(A0),_Menues(A4)
* ------------ InitRastPort(&Rp)
LEA _Rp(A4),A1
MOVEA.L _GfxBase(A4),A6
JSR _LVOInitRastPort(A6)
* ------------ SetFont(&Rp,Screen->RastPort.Font)
LEA _Rp(A4),A1
MOVEA.L sc_RastPort+rp_Font(A5),A0
JSR _LVOSetFont(A6)
* ------------ Rp.BitMap = &Screen->BitMap
ADDA.W #sc_BitMap,A5
MOVE.L A5,_Rp+rp_BitMap(A4)
* ------------ MenuFontSize = Rp.TxHeight + 2
MOVE.W _Rp+rp_TxHeight(A4),D0
ADDQ.W #2,D0
MOVE.W D0,_MenuFontSize(A4)
* ------------ Any menues at all ?
TST.L _Menues(A4)
BEQ.W NoMenues
* ------------ Same menues as last time ?
MOVEQ.L #0,D0
MOVEA.L _ActiveWindow(A4),A0
CMPA.L _LastWindow(A4),A0
BNE.B OpenMenues
* ------------ Yes: Start at last menu selection.
MOVE.W _LastSelectedNum(A4),D0
SUBQ.W #1,D0
MULU.W _MenuFontSize(A4),D0
* ------------ Open the menues.
OpenMenues: JSR @OpenMenuWindow(PC)
TST.W D0
BEQ.W NoMenues
* ------------ MenuButtonSignals = MenuUpSig | MenuDownSig
MOVE.L sd_MenuUpSig(A3),D6
OR.L sd_MenuDownSig(A3),D6
* ------------ MouseMovedSignal = MouseMovedSig
MOVE.L sd_MouseMovedSig(A3),D5
* ------------ ButtonSignals = MenuButtonSignals | SelectDownSig
MOVE.L D6,D4
OR.L sd_SelectDownSig(A3),D4
* ------------ Waiting = FALSE
MOVEQ.L #0,D3
* ------------ No selections done so far.
* ------------ MenuNumber = LastSelected = MENUNULL;
MOVEQ.L #-1,D7
MOVE.W D7,_LastSelected(A4)
* ------------ Clear old timermessages and set mousemoved signal.
* ------------ SetSignal(MouseMovedSignal,TimerSignal | MouseMovedSignal)
MOVE.L D5,D0
MOVE.L _TimerSignal(A4),D1
OR.L D5,D1
MOVEA.L (AbsExecBase).W,A6
JSR _LVOSetSignal(A6)
* ------------ Is the timer already running.
* ------------ CheckIO(TimerReqBlock)
MOVEA.L _TimerReqBlock(A4),A1
JSR _LVOCheckIO(A6)
TST.L D0
BNE.B IOReady
* ------------ Yes: wait for the time.
* ------------ WaitIO(TimerReqBlock)
MOVEA.L _TimerReqBlock(A4),A1
JSR _LVOWaitIO(A6)
* ------------ Remove the message.
MOVEA.L _TimerPort(A4),A0
JSR _LVOGetMsg(A6)
* ------------ Start up the timer.
IOReady: JSR @QueTimer(PC)
* ------------ Main loop starts here.
* ------------ SignalBits = Wait(MouseMovedSignal | ButtonSignals | TimerSignal)
WaitNextSig: MOVE.L D5,D0
OR.L D4,D0
OR.L _TimerSignal(A4),D0
MOVEA.L (AbsExecBase).W,A6
JSR _LVOWait(A6)
MOVE.L D0,D2
*********************************************
* D0 = SignalBits A2 = LayerInfo *
* D2 = SignalBits A3 = InputSignals *
* D3 = Waiting A6 = ExecBase *
* D4 = ButtonSignals *
* D5 = MouseMovedSignal *
* D6 = MenuButtonSignal *
* D7 = MenuNumber *
*********************************************
* ------------ Mouse moved ?
AND.L D5,D0
BEQ.B NotMoved
* ------------ Waiting = FALSE
MOVEQ.L #0,D3
* ------------ Get new coordinates for the mouse.
MOVEA.L _Screen(A4),A0
MOVE.W sc_MouseX(A0),D0
MOVE.W sc_MouseY(A0),D1
CMP.W _MouseX(A4),D0
BNE.B Moved
CMP.W _MouseY(A4),D1
BEQ.B NotMoved
* ------------ MouseX = Screen->MouseX
* ------------ MouseY = Screen->MouseY
Moved: MOVE.W D0,_MouseX(A4)
MOVE.W D1,_MouseY(A4)
* ------------ Select the item under the mousepointer.
JSR @SelectItem(PC)
* ------------ Any button pressed ?
NotMoved: MOVE.L D2,D0
AND.L D4,D0
BEQ.B NoButton
* ------------ Find MENUPICK value for selected item.
JSR @FinalSelect(PC)
* ------------ Waiting = FALSE
MOVEQ.L #0,D3
MOVE.W D4,-(SP)
MOVE.W D0,D4
MOVE.W _LastSelected(A4),D1
**********************************************
* D0 = Selected A2 = LayerInfo *
* D1 = LastSelected A3 = InputSignals *
* D2 = SignalBits A6 = ExecBase *
* D3 = Waiting *
* D4 = Selected *
* D5 = MouseMovedSignal *
* D6 = MenuButtonSignal *
* D7 = MenuNumber *
**********************************************
* ------------ Same item selected as last time ?
CMP.W D0,D1
BEQ.B SameItem
* ------------ First selection ?
MOVEQ.L #-1,D0
CMP.W D0,D7
BNE.B MultipSelect
* ------------ MenuNumber = Selected
MOVE.W D4,D7
BRA.B SelectionDone
* ------------ ItemAddress(Menues,LastSelected)->NextSelect = Selected
MultipSelect: MOVEQ.L #0,D0
MOVE.W D1,D0
MOVEA.L _Menues(A4),A0
MOVEA.L _IntuitionBase(A4),A6
JSR _LVOItemAddress(A6)
MOVEA.L D0,A0
MOVE.W D4,mi_NextSelect(A0)
* ------------ LastSelected = Selected
SelectionDone: MOVE.W D4,_LastSelected(A4)
SameItem: MOVE.W (SP)+,D4
* ------------ Selected with menubutton ?
MOVE.L D2,D0
AND.L D6,D0
BNE.W NoMoreSel
********************************************
* D2 = SignalBits A2 = LayerInfo *
* D3 = Waiting A3 = InputSignals *
* D4 = ButtonSignals *
* D5 = MouseMovedSignal *
* D6 = MenuButtonSignal *
* D7 = MenuNumber *
********************************************
* ------------ Timer ?
NoButton: MOVE.L D2,D0
AND.L _TimerSignal(A4),D0
BEQ.W WaitNextSig
* ------------ Remove the message.
MOVEA.L _TimerPort(A4),A0
MOVEA.L (AbsExecBase).W,A6
JSR _LVOGetMsg(A6)
* ------------ 2 TimerSignals in a row ?
TST.W D3
BEQ.B NoLockUp
* ------------ The input.device has stopped.
* ------------ Remove everything from the screen.
MOVEA.L A4,A0 * _SubWindow
JSR @SwapBits(PC)
LEA _ItemWindow(A4),A0
JSR @SwapBits(PC)
LEA _MenuWindow(A4),A0
JSR @SwapBits(PC)
* ------------ Unlock the screen.
MOVEA.L A2,A0
MOVEA.L _LayersBase(A4),A6
JSR _LVOUnlockLayers(A6)
* ------------ Wait for the input.device.
MOVE.L D5,D0
MOVEA.L (AbsExecBase).W,A6
JSR _LVOWait(A6)
* ------------ Is the window still open ?
JSR @FindWindow(PC)
TST.W D0
BNE.B OKToLock
* ------------ No: the window is gone. Abort.
MOVEA.L A4,A0 * _SubWindow
JSR @RemoveBitMap(PC)
LEA _ItemWindow(A4),A0
JSR @RemoveBitMap(PC)
LEA _MenuWindow(A4),A0
JSR @RemoveBitMap(PC)
BRA.B Abort
* ------------ Lock the screen again.
OKToLock: MOVEA.L A2,A0
MOVEA.L _LayersBase(A4),A6
JSR _LVOLockLayers(A6)
* ------------ Put everything back on the screen.
LEA _MenuWindow(A4),A0
JSR @SwapBits(PC)
LEA _ItemWindow(A4),A0
JSR @SwapBits(PC)
MOVEA.L A4,A0 * _SubWindow
JSR @SwapBits(PC)
* ------------ Start a new timer.
NoLockUp: JSR @QueTimer(PC)
* ------------ Waiting = !Waiting
MOVEQ.L #1,D0
SUB.W D3,D0
MOVE.W D0,D3
BRA.W WaitNextSig
* ------------ Selections done.
* ------------ Close all windows.
NoMoreSel: MOVEA.L A4,A0 * _SubWindow
JSR @CloseItemWindow(PC)
LEA _ItemWindow(A4),A0
JSR @CloseItemWindow(PC)
LEA _MenuWindow(A4),A0
JSR @CloseItemWindow(PC)
* ------------ Remember the selection for next time.
NoMenues: MOVE.L _ActiveWindow(A4),_LastWindow(A4)
* ------------ Unlock the screen.
MOVEA.L A2,A0
MOVEA.L _LayersBase(A4),A6
JSR _LVOUnlockLayers(A6)
* ------------ Tell the window the good news (MENUPICK).
MOVE.L D7,D0
JSR @TellWindow(PC)
* ------------ ReleaseSemaphore(&PopUpSemaphore);
Abort: LEA _PopUpSemaphore(A4),A0
MOVEA.L (AbsExecBase).W,A6
JSR _LVOReleaseSemaphore(A6)
* ------------ Free the sorted menulist * New 3.42
LEA _SortRemember(A4),A0
MOVEQ.L #TRUE,D0
MOVEA.L _IntuitionBase(A4),A6
JSR _LVOFreeRemember(A6)
MOVEM.L (SP)+,D2-D7/A2-A3/A5-A6
RTS
************************************************
* FindMenuPtr(Number) - Find Menu structure. *
* *
* Input: *
* Number.W - Number of the menu to look for. *
* Output: *
* return - Ptr to the Menu structure. *
************************************************
@FindMenuPtr: MOVEA.L _MenuSorted+ms_Next(A4),A0
1$ SUBQ.W #1,D0
BEQ.B 2$
MOVEA.L (A0),A0 * ms_Next
MOVE.L A0,D1
BNE.B 1$
MOVEQ.L #0,D0
RTS
2$ MOVE.L ms_MenuPtr(A0),D0
RTS
************************************************
* FindItemNr(Item,ItemList) - Find nr of item. *
* *
* Input: *
* Item - Item to look for. *
* ItemList - all items on same level. *
* Output: *
* return - Nr of Item. *
************************************************
* ------------ Count = 0
@FindItemNr: MOVEQ.L #00,D0
* ------------ ItemList == NULL ?
1$ MOVE.L A1,D1
BEQ.B 2$
* ------------ ItemList == Item ?
CMPA.L A0,A1
BEQ.B 3$
* ------------ Count++
ADDQ.W #1,D0
* ------------ ItemList = ItemList->NextItem
MOVEA.L (A1),A1
BRA.B 1$
2$ MOVEQ.L #NOITEM,D0
3$ RTS
******************************************************
* QueTimer() - Queue the timer to go of after 0.2s *
* *
* Input: *
* none *
* Output: *
* none: *
******************************************************/
@QueTimer: MOVE.L A6,-(SP)
* ------------ TimerReqBlock->tr_node.io_Command = TR_ADDREQUEST
MOVEA.L _TimerReqBlock(A4),A1
MOVE.W #TR_ADDREQUEST,IO_COMMAND(A1)
* ------------ TimerReqBlock->tr_time.tv_secs = 0
CLR.L IOTV_TIME+TV_SECS(A1)
* ------------ TimerReqBlock->tr_time.tv_micro = 200000
MOVE.L #200000,IOTV_TIME+TV_MICRO(A1)
* ------------ SendIO(TimerReqBlock)
MOVEA.L (AbsExecBase).W,A6
JSR _LVOSendIO(A6)
MOVEA.L (SP)+,A6
RTS
*************************************************
* FindWindow() - Check if window is still open. *
* *
* Input: *
* none *
* Output: *
* return - TRUE if window is open. *
*************************************************
@FindWindow: MOVE.L D2,-(SP)
MOVE.L A6,-(SP)
MOVEQ.L #0,D0
MOVEA.L _IntuitionBase(A4),A6
JSR _LVOLockIBase(A6)
* ------------ TestScreen = IntuitionBase->FirstScreen
MOVEA.L ib_FirstScreen(A6),A0
* ------------ TestScreen == NULL ?
1$ MOVE.L A0,D1
BEQ.B 5$
* ------------ TestScreen == Screen ?
CMPA.L _Screen(A4),A0
BNE.B 4$
* ------------ TestWindow = TestScreen->FirstWindow
MOVEA.L sc_FirstWindow(A0),A1
* ------------ TestWindow == NULL ?
2$ MOVE.L A1,D1
BEQ.B 5$
* ------------ TestWindow == ActiveWindow ?
CMPA.L _ActiveWindow(A4),A1
BNE.B 3$
MOVEQ.L #TRUE,D2
BRA.B 6$
* ------------ TestWindow = TestWindow->NextWindow
3$ MOVEA.L (A1),A1
BRA.B 2$
* ------------ TestScreen = TestScreen->NextScreen
4$ MOVEA.L (A0),A0
BRA.B 1$
5$ MOVEQ.L #FALSE,D2
* ------------ UnlockIBase(Lock)
6$ MOVEA.L D0,A0
JSR _LVOUnlockIBase(A6)
MOVE.L D2,D0
MOVEA.L (SP)+,A6
MOVE.L (SP)+,D2
RTS
***************************************************
* MouseInWindow(Window) - Is mouse inside window. *
* *
* Input: *
* Window - Window to check. *
* Output: *
* return - TRUE if mouse inside. *
***************************************************
@MouseInWindow:
MOVEQ.L #FALSE,D0
* ------------ MouseX > Window->LeftEdge ?
MOVE.W _MouseX(A4),D1
CMP.W wwd_LeftEdge(A0),D1
BLE.B 1$
* ------------ MouseX < Window->RightEdge ?
CMP.W wwd_RightEdge(A0),D1
BGE.B 1$
* ------------ MouseY > Window->TopEdge ?
MOVE.W _MouseY(A4),D1
CMP.W wwd_TopEdge(A0),D1
BLE.B 1$
* ------------ MouseY < Window->Bottom ?
CMP.W wwd_Bottom(A0),D1
BGE.B 1$
MOVEQ.L #TRUE,D0
1$ RTS
****************************************************************
* FindMouseItem(ItemWindow) - Check if mouse inside an item. *
* *
* Input: *
* ItemWindow - Window with items *
* Output: *
* return - Pointer to item under the mousepointer (or NULL). *
****************************************************************/
@FindMouseItem:
MOVE.W D2,-(SP)
* ------------ MouseWinX = MouseX + ItemWindow->LeftValue
MOVE.W _MouseX(A4),D1
ADD.W wwd_LeftValue(A0),D1
* ------------ MouseWinY = MouseY + ItemWindow->TopValue
MOVE.W _MouseY(A4),D2
ADD.W wwd_TopValue(A0),D2
* ------------ Item = ItemWindow->Items
MOVEA.L wwd_Items(A0),A0
* ------------ MouseWinY >= Item->TopEdge ?
1$ MOVE.W mi_TopEdge(A0),D0
CMP.W D0,D2
BLT.B 2$
* ------------ MouseWinY <= Item->TopEdge + Item->Height ?
ADD.W mi_Height(A0),D0
CMP.W D0,D2
BGT.B 2$
* ------------ MouseWinX >= Item->LeftEdge ?
MOVE.W mi_LeftEdge(A0),D0
CMP.W D0,D1
BLT.B 2$
* ------------ MouseWinX <= Item->LeftEdge + Item->Width ?
ADD.W mi_Width(A0),D0
CMP.W D0,D1
BGT.B 2$
* ------------ return Item.
MOVE.L A0,D0
BRA.B 3$
* ------------ Try next item.
2$ MOVEA.L (A0),A0
MOVE.L A0,D0
BNE.B 1$
3$ MOVE.W (SP)+,D2
RTS
*********************************************************
* HighLightCurrItemBehind(Mode) - Highlight currentitem *
* behind subwindow. *
* Input: *
* Mode.W - HIGHLIGHTON or HIGHLIGHTOFF. *
* Output: *
* none *
* Functions: *
* SwapBits, HighLightItem *
*********************************************************
@HighLightCurrItemBehind:
MOVE.W D2,-(SP)
MOVE.W D0,D2
* ------------ SwapBits(SubWindow)
MOVEA.L A4,A0 * _SubWindow
JSR @SwapBits(PC)
* ------------ HighLightItem(CurrentItem,&ItemWindow,Mode)
MOVE.W D2,D0
MOVEA.L _CurrentItem(A4),A0
LEA _ItemWindow(A4),A1
JSR @HighLightItem(PC)
* ------------ SwapBits(SubWindow)
MOVEA.L A4,A0 * _SubWindow
JSR @SwapBits(PC)
MOVE.W (SP)+,D2
RTS
******************************************
* OpenMenuWindow(StartPos) *
* *
* Input: *
* StartPos - Position from menutop. *
* Output: *
* return - TRUE if window opened. *
* Functions: *
* Mystrlen, BuildBitMap, DrawAllMenues *
******************************************
@OpenMenuWindow:
MOVEM.L D5-D7/A3/A5,-(SP)
MOVE.W D0,D7
* ------------ Sort menues after their LeftEdge
JSR @SortMenues(PC)
TST.L D0
BEQ.W OpenMenuDone
* ------------ MenuWidth = 0
MOVEQ.L #0,D6
* ------------ MenuHeight = BORDERSIZE + 1
MOVEQ.L #3,D5
****************************************
* Find width & height of window needed *
****************************************
FindWidthHeight:
MOVEA.L _Menues(A4),A3
MOVEA.L _GfxBase(A4),A6
***********************************
* D5 = MenuHeight A3 = Menues *
* D6 = MenuWidth A6 = GfxBase *
* D7 = MenuTop *
***********************************
* ------------ Length = TextLength(&Rp,MenuPtr->MenuName,Mystrlen(MenuPtr->MenuName))
1$ MOVEA.L mu_MenuName(A3),A0
JSR @Mystrlen(PC)
LEA _Rp(A4),A1
MOVEA.L mu_MenuName(A3),A0
JSR _LVOTextLength(A6)
* ------------ MenuPtr->Width > Length ?
MOVE.W mu_Width(A3),D1
CMP.W D0,D1
BLS.B 2$ * No
* ------------ Length = MenuPtr->Width
MOVE.L D1,D0
* ------------ Length > MenuWidth ?
2$ CMP.W D6,D0
BLS.B 3$ * No
* ------------ MenuWidth = Length
MOVE.W D0,D6
* ------------ MenuHeight += MenuFontSize
3$ ADD.W _MenuFontSize(A4),D5
* ------------ Check next menu.
MOVEA.L (A3),A3
MOVE.L A3,D0
BNE.B 1$
* ------------ MenuWidth += (2 * BORDERSIZE + 1)
ADDQ.W #5,D6
************************************
* Position window on screen (Left) *
************************************
***********************************
* D5 = MenuHeight A6 = GfxBase *
* D6 = MenuWidth *
* D7 = MenuTop *
***********************************
* ------------ MenuLeft = Screen->MouseX - MenuWidth / 2
PosLeft: MOVE.W D6,D0
LSR.W #1,D0
MOVEA.L _Screen(A4),A0
MOVE.W sc_MouseX(A0),D1
SUB.W D0,D1
* ------------ MenuLeft < 0 ?
BGE.B 1$ * No
* ------------ MenuLeft = 0
MOVEQ.L #0,D1
* ------------ MenuLeft > Screen->Width - MenuWidth ?
1$ MOVE.W sc_Width(A0),D0
SUB.W D6,D0
CMP.W D0,D1
BLE.B 2$ * No
* ------------ MenuLeft = Screen->Width - MenuWidth
MOVE.W D0,D1
* ------------ MenuWindow.LeftEdge = MenuLeft
2$ MOVE.W D1,_MenuWindow+wwd_LeftEdge(A4)
* ------------ MenuWindow.Width = MenuWidth;
MOVE.W D6,_MenuWindow+wwd_Width(A4)
***********************************
* Position window on screen (Top) *
***********************************
***********************************
* D5 = MenuHeight A0 = Screen *
* D6 = MenuWidth A6 = GfxBase *
* D7 = MenuTop *
***********************************
* ------------ MenuTop > MenuHeight ? (Menues has changed)
PosTop: CMP.W D5,D7
BLE.B 1$ * No
* ------------ MenuTop = 0
MOVEQ #0,D7
* ------------ MenuTop = Screen->MouseY - MenuFontSize/2 - MenuTop
1$ MOVE.W _MenuFontSize(A4),D0
LSR.W #1,D0
ADD.W D0,D7
SUB.W sc_MouseY(A0),D7
NEG.W D7
* ------------ MenuTop < 0 ?
BPL.B 2$ * No
* ------------ MenuTop = 0
MOVEQ.L #0,D7
* ------------ MenuTop > Screen->Height - MenuHeight ?
2$ MOVE.W sc_Height(A0),D0
SUB.W D5,D0
CMP.W D0,D7
BLE.B 3$ * No
* ------------ MenuTop = Screen->Height - MenuHeight
MOVE.L D0,D7
* ------------ MenuWindow.TopEdge = MenuTop
3$ MOVE.W D7,_MenuWindow+wwd_TopEdge(A4)
* ------------ MenuWindow.Height = MenuHeight
MOVE.W D5,_MenuWindow+wwd_Height(A4)
*******************************
* Open window with right size *
*******************************
* ------------ BuildBitMap(MenuWindow)
Open: LEA _MenuWindow(A4),A0
JSR @BuildBitMap(PC)
* ------------ Window open ?
TST.W D0
BEQ.B OpenMenuDone * No
* ------------ Draw all menues
JSR @DrawAllMenues(PC)
* ------------ return (TRUE)
MOVEQ.L #TRUE,D0
OpenMenuDone: MOVEM.L (SP)+,D5-D7/A3/A6
RTS
**********************************
* BOOL SortMenues() *
* *
* Input: *
* none. *
* Output: *
* TRUE if everything is ok. *
**********************************
@SortMenues: MOVEM.L A2-A3/A5-A6,-(SP)
MOVEA.L _IntuitionBase(A4),A6
MOVEQ.L #0,D1
MOVE.L D1,_SortRemember(A4)
MOVE.L D1,_MenuSorted+ms_Next(A4)
MOVEA.L _Menues(A4),A5
0$ LEA _SortRemember(A4),A0
MOVEQ.L #ms_SIZEOF,D0
MOVEQ.L #0,D1
JSR _LVOAllocRemember(A6)
TST.L D0
BEQ.B 3$
MOVE.L D0,A0
MOVE.L A5,ms_MenuPtr(A0)
MOVE.W mu_LeftEdge(A5),D1
LEA _MenuSorted(A4),A3
**************************************************
* D1 = LeftEdge for TestMenu A3 = MenuSorted *
* A5 = TestMenu *
* A6 = IntuitionBase *
**************************************************
1$ MOVEA.L (A3),A1 * ms_Next(A3)
MOVE.L A1,D0
BEQ.B 2$
MOVEA.L ms_MenuPtr(A1),A2
CMP.W mu_LeftEdge(A2),D1
BLE.B 2$
MOVEA.L A1,A3
BRA.B 1$
2$ MOVE.L A1,(A0) * ms_Next(A0)
MOVE.L A0,(A3) * ms_Next(A3)
MOVEA.L (A5),A5 * mu_NextMenu
MOVE.L A5,D0
BNE.B 0$
MOVEQ.L #TRUE,D0
3$ MOVEM.L (SP)+,A2-A3/A5-A6
RTS
**************************************************************
* OpenItemWindow(ItemWindow,ParentWindow,TopPos,WindowType) *
* *
* Input: *
* ItemWindow - Window to open. *
* ParentWindow - *
* TopPos.W - Top position for new window. *
* WindowType.W - ITEMWINDOW or SUBWINDOW *
* Output: *
* none *
* Functions: *
* FindItemWinSize, PosItemWinLeft, PosItemWinTop, *
* BuildBitMap, DrawAllItems *
**************************************************************
@OpenItemWindow:
MOVEM.L D6-D7/A2-A3,-(SP)
MOVEA.L A0,A3
MOVEA.L A1,A2
MOVE.W D0,D7
MOVE.W D1,D6
* ------------ FindItemWinSize(ItemWindow,WindowType)
MOVE.W D6,D0
JSR @FindItemWinSize(PC)
* ------------ PosItemWinLeft(ItemWindow,ParentWindow,WindowType)
MOVE.W D6,D0
MOVEA.L A3,A0
MOVEA.L A2,A1
BSR.B @PosItemWinLeft
* ------------ PosItemWinTop(ItemWindow,TopPos)
MOVE.W D7,D0
MOVEA.L A3,A0
JSR @PosItemWinTop(PC)
* ------------ BuildBitMap(ItemWindow)
MOVEA.L A3,A0
JSR @BuildBitMap(PC)
TST.W D0
BEQ.B 1$
* ------------ DrawAllItems(ItemWindow)
MOVEA.L A3,A0
JSR @DrawAllItems(PC)
1$ MOVEM.L (SP)+,D6-D7/A2-A3
RTS
******************************************************
* PosItemWinLeft(ItemWindow,ParentWindow,WindowType) *
* - Position window on screen (left) *
* *
* Input: *
* ItemWindow - Window to position. *
* ParentWindow - Window to position next to. *
* WindowType.W - ITEMWINDOW or SUBWINDOW. *
* *
* Possible positions: *
* 1. At real position (a'la intuition). *
* 2. At right side of parent. *
* 3. At left side of parent. *
* 4. On the side that covers parent least. *
******************************************************
@PosItemWinLeft:
MOVEM.L D3-D7/A2,-(SP)
* ------------ LeftValue = Size.Left - BORDERSIZE
MOVE.W _Size+ws_Left(A4),D6
SUBQ.W #BORDERSIZE,D6
* ------------ WindowWidth = Size.Right - LeftValue + BORDERSIZE
MOVE.W _Size+ws_Right(A4),D5
SUB.W D6,D5
ADDQ.W #BORDERSIZE,D5
* ------------ LeftPos2 = ParentWindow->LeftEdge - WindowWidth + OVERLAP
MOVE.W wwd_LeftEdge(A1),D1
MOVE.W D1,D4
SUB.W D5,D4
ADDQ.W #OVERLAP,D4
* ------------ MaxLeft = Screen->Width - WindowWidth
MOVEA.L _Screen(A4),A2
MOVE.W sc_Width(A2),D3
SUB.W D5,D3
**********************************************
* D0 = WindowType A0 = ItemWindow *
* D1 = Parent->LeftEdge A1 = ParentWindow *
* D2 = A2 = Screen *
* D3 = MaxLeft *
* D4 = LeftPos2 *
* D5 = WindowWidth *
* D6 = LeftValue *
* D7 = WindowLeft *
**********************************************
* ------------ WindowType == ITEMWINDOW ?
TST.W D0
BEQ.B 1$ * Yes
* ------------ WindowLeft = ParentWindow->LeftEdge + LeftValue
MOVE.W D1,D7
ADD.W D6,D7
* ------------ WindowLeft > MaxLeft ?
CMP.W D7,D3
BLT.B 1$ * Yes
* ------------ WindowLeft < 0 ?
TST.W D7
BPL.B 2$ * No
* ------------ WindowLeft = ParentWindow->RightEdge - OVERLAP
1$ MOVE.W wwd_RightEdge(A1),D7
SUBQ.W #OVERLAP,D7
* ------------ WindowLeft > MaxLeft ?
2$ CMP.W D7,D3
BGE.B 4$ * No
* ------------ LeftPos2 > MaxLeft - WindowLeft ?
MOVE.W D3,D0
SUB.W D7,D0
CMP.W D4,D0
BGE.B 3$ * No
* ------------ WindowLeft = (LeftPos2 > 0) ? LeftPos2 : 0
MOVE.W D4,D7
BGT.B 4$
MOVEQ.L #0,D7
BRA.B 4$
* ------------ WindowLeft = MaxLeft
3$ MOVE.W D3,D7
* ------------ WindowWidth < ParentWindow->LeftEdge + OVERLAP - WindowLeft ?
4$ MOVE.W D1,D0
ADDQ.W #OVERLAP,D0
SUB.W D7,D0
CMP.W D5,D0
BLE.B 5$ * No
* ------------ WindowWidth = ParentWindow->LeftEdge + OVERLAP - WindowLeft
MOVE.W D0,D5
* ------------ ItemWindow->LeftEdge = WindowLeft
5$ MOVE.W D7,wwd_LeftEdge(A0)
* ------------ ItemWindow->LeftValue = LeftValue - WindowLeft
SUB.W D7,D6
MOVE.W D6,wwd_LeftValue(A0)
* ------------ ItemWindow->Width = WindowWidth
MOVE.W D5,wwd_Width(A0)
MOVEM.L (SP)+,D3-D7/A2
RTS
**************************************
* PosItemWinTop(ItemWindow,TopPos) *
* - Position Window on screen (Top). *
* *
* Input: *
* ItemWindow - Window to position. *
* TopPos.W - *
**************************************
@PosItemWinTop:
MOVEM.L D4-D7,-(SP)
* ------------ TopValue = Size.Top - BORDERSIZE
MOVE.W _Size+ws_Top(A4),D6
SUBQ.W #BORDERSIZE,D6
* ------------ WindowTop = TopPos + TopValue
MOVE.W D0,D5
ADD.W D6,D5
* ------------ WindowHeight = Size.Bottom - TopValue + BORDERSIZE
MOVE.W _Size+ws_Bottom(A4),D4
SUB.W D6,D4
ADDQ.W #BORDERSIZE,D4
MOVEA.L _Screen(A4),A1
***************************************
* D0 = TopPos A0 = ItemWindow *
* D4 = WindowHeight A1 = Screen *
* D5 = WindowTop *
* D6 = TopValue *
***************************************
* ------------ WindowTop > Screen->Height - WindowHeight ?
MOVE.W sc_Height(A1),D0
SUB.W D4,D0
CMP.W D5,D0
BGE.B 1$ * No
* ------------ WindowTop = Screen->Height - WindowHeight
MOVE.W D0,D5
* ------------ WindowTop < 0 ?
1$ TST.W D5
BPL.B 2$ * No
* ------------ WindowTop = 0
MOVEQ.L #0,D5
* ------------ ItemWindow->TopEdge = WindowTop
2$ MOVE.W D5,wwd_TopEdge(A0)
* ------------ ItemWindow->TopValue = TopValue - WindowTop
SUB.W D5,D6
MOVE.W D6,wwd_TopValue(A0)
* ------------ ItemWindow->Height = WindowHeight
MOVE.W D4,wwd_Height(A0)
MOVEM.L (SP)+,D4-D7
RTS
************************************************
* TellWindow(MenuNum) - Send Fake Menu Event. *
* *
* Input: *
* MenuNum - Menu nimber to send. *
* Output: *
* none *
* Functions: *
* FindWindow *
************************************************
@TellWindow: MOVE.L A2,-(SP)
MOVE.L A6,-(SP)
LEA -ie_SIZEOF(SP),SP
* ------------ MyFakeEvent.ie_Class = IECLASS_MENULIST
MOVE.B #IECLASS_MENULIST,ie_Class(SP)
* ------------ MyFakeEvent.ie_Code = MenuNumber
MOVE.W D0,ie_Code(SP)
* ------------ MyFakeEvent.ie_Qualifier = 0
CLR.W ie_Qualifier(SP)
* ------------ MyFakeEvent.ie_NextEvent = NULL
CLR.L (SP)
* ------------ MyFakeEvent.ie_EventAddress = NULL
CLR.L ie_EventAddress(SP)
* ------------ Get current time.
LEA ie_TimeStamp+TV_SECS(SP),A0
LEA ie_TimeStamp+TV_MICRO(SP),A1
MOVEA.L _IntuitionBase(A4),A6
JSR _LVOCurrentTime(A6)
* ------------ InputReqBlock->io_Command = IND_WRITEEVENT
MOVEA.L _InputReqBlock(A4),A2
MOVE.W #IND_WRITEEVENT,IO_COMMAND(A2)
* ------------ InputReqBlock->io_Flags = 0
CLR.B IO_FLAGS(A2)
* ------------ InputReqBlock->io_Length = sizeof(struct InputEvent)
MOVEQ.L #ie_SIZEOF,D0
MOVE.L D0,IO_LENGTH(A2)
* ------------ InputReqBlock->io_Data = &MyFakeEvent
MOVE.L SP,IO_DATA(A2)
* ------------ Be sure the right window will get the message.
JSR @FindWindow(PC)
TST.W D0
BEQ.B 1$
MOVEA.L _ActiveWindow(A4),A0
JSR _LVOActivateWindow(A6)
* ------------ DoIO(InputReqBlock)
MOVEA.L A2,A1
MOVEA.L (AbsExecBase).W,A6
JSR _LVODoIO(A6)
1$ LEA ie_SIZEOF(SP),SP
MOVEA.L (SP)+,A6
MOVEA.L (SP)+,A2
RTS
****************************************
* DrawAllItems(ItemWindow) *
* *
* Input: *
* ItemWindow - Window to draw into. *
* *
* Output: *
* none *
* Functions: *
* ClearWindow, DrawMenuItem *
****************************************
@DrawAllItems: MOVE.L A2,-(SP)
MOVE.L A3,-(SP)
MOVEA.L A0,A3
* ------------ Item = ItemWindow->Items
MOVEA.L wwd_Items(A3),A2
* ------------ ClearWindow(ItemWindow)
BSR.B @ClearWindow
* ------------ DrawMenuItem(Item, ItemWindow, ITEMFILL)
1$ MOVEQ.L #0,D0
MOVEA.L A2,A0
MOVEA.L A3,A1
JSR @DrawMenuItem(PC)
* ------------ Item = Item->NextItem
MOVEA.L (A2),A2
MOVE.L A2,D0
BNE.B 1$
MOVEA.L (SP)+,A3
MOVEA.L (SP)+,A2
RTS
*********************************
* ClearWindow(window) *
* *
* Input: *
* Window - Window to clear. *
* Output: *
* none *
*********************************
@ClearWindow: MOVEM.L D2-D3/A2-A3/A5-A6,-(SP)
MOVEA.L A0,A3
LEA _Rp(A4),A2
MOVEA.L _ActiveWindow(A4),A5
MOVEA.L _GfxBase(A4),A6
*********************
* A2 = Rp *
* A3 = Window *
* A5 = ActiveWindow *
* A6 = GfxBase *
*********************
* ------------ SetDrMd(Rp, JAM1)
MOVEA.L A2,A1
MOVEQ.L #RP_JAM1,D0
JSR _LVOSetDrMd(A6)
* ------------ SetAPen(Rp,ActiveWindow->BlockPen)
MOVEA.L A2,A1
MOVEQ.L #0,D0
MOVE.B wd_BlockPen(A5),D0
JSR _LVOSetAPen(A6)
* ------------ SetOPen(Rp,ActiveWindow->DetailPen)
MOVE.B wd_DetailPen(A5),_Rp+rp_AOlPen(A4)
BSET #3,_Rp+rp_Flags+1(A4) * AREAOUTLINE
* ------------ RectFill(Rp,Window->LeftEdge,Window->TopEdge,
* ------------ Window->RightEdge,Window->Bottom)
MOVE.W wwd_LeftEdge(A3),D0
EXT.L D0
MOVE.W wwd_TopEdge(A3),D1
EXT.L D1
MOVE.W wwd_RightEdge(A3),D2
EXT.L D2
MOVE.W wwd_Bottom(A3),D3
EXT.L D3
MOVEA.L A2,A1
JSR _LVORectFill(A6)
* ------------ BNDRYOFF(Rp)
BCLR #3,_Rp+rp_Flags+1(A4)
MOVEM.L (SP)+,D2-D3/A2-A3/A5-A6
RTS
*******************************
* CloseItemWindow(Window) *
* *
* Input: *
* Window - Window to close. *
* Output: *
* none *
* Functions: *
* SwapBits, RemoveBitMap *
*******************************
@CloseItemWindow:
MOVE.L A3,-(SP)
MOVEA.L A0,A3
* ------------ Remove window from screen.
JSR @SwapBits(PC)
* ------------ Remove all bitplanes.
MOVEA.L A3,A0
JSR @RemoveBitMap(PC)
MOVEA.L (SP)+,A3
RTS
****************************************
* BuildBitMap(Window) - OpenWindow *
* *
* Input: *
* Window - Window to open. *
* Output: *
* return - TRUE if window opened. *
****************************************
@BuildBitMap: MOVEM.L D2-D5/A2-A3/A6,-(SP)
MOVEA.L A0,A3
* ------------ WindowWidth = Window->Width
MOVE.W wwd_Width(A3),D3
EXT.L D3
* ------------ WindowHeight = Window->Height
MOVE.W wwd_Height(A3),D2
EXT.L D2
MOVEA.L _Screen(A4),A0
**************************************
* D2 = WindowHeight A0 = Screen *
* D3 = WindowWidth A3 = Window *
**************************************
* ------------ Is window to big for screen ?
* ------------ WindowWidth > Screen->Width
CMP.W sc_Width(A0),D3
BGT.B Fail * Yes
* ------------ WindowHeight > Screen->Height
CMP.W sc_Height(A0),D2
BGT.B Fail * Yes
* ------------ Window->RightEdge = Window->LeftEdge + WindowWidth - 1
MOVE.L D3,D0
ADD.W wwd_LeftEdge(A3),D0
SUBQ.L #1,D0
MOVE.W D0,wwd_RightEdge(A3)
* ------------ Window->Bottom = Window->TopEdge + WindowHeight - 1
MOVE.L D2,D0
ADD.W wwd_TopEdge(A3),D0
SUBQ.L #1,D0
MOVE.W D0,wwd_Bottom(A3)
* ------------ Depth = Screen->BitMap.Depth
MOVEQ.L #0,D5
MOVE.B sc_BitMap+bm_Depth(A0),D5
MOVEA.L _GfxBase(A4),A6
***************************************
* D2 = WindowHeight A0 = Screen *
* D3 = WindowWidth A3 = Window *
* D5 = Depth A6 = GfxBase *
***************************************
* ------------ InitBitMap(&Window->Bm,Depth,WindowWidth,WindowHeight)
LEA wwd_Bm(A3),A0
MOVE.L D5,D0
MOVE.L D3,D1
JSR _LVOInitBitMap(A6)
* ------------ Window->BitMapOk = TRUE
MOVE.W #TRUE,(A3)
MOVEQ.L #0,D4
* ------------ Plane = &Window->Bm.Planes[0]
LEA wwd_Bm+bm_Planes(A3),A2
***************************************
* D2 = WindowHeight A2 = Planen *
* D3 = WindowWidth A3 = Window *
* D4 = Counter A6 = GfxBase *
* D5 = Depth *
***************************************
* ------------ More planes to allocate ?
BuildNextPl: CMP.W D4,D5
BEQ.B AllRastersOK
ADDQ.W #1,D4
* ------------ Plane++ = AllocRaster(WindowWidth,WindowHeight)
MOVE.L D3,D0
MOVE.L D2,D1
JSR _LVOAllocRaster(A6)
MOVE.L D0,(A2)+
* ------------ Out of ChipRam ?
BNE.B BuildNextPl * No
* ------------ RemoveBitMap(Window)
MOVEA.L A3,A0
BSR.B @RemoveBitMap
* ------------ return FALSE
Fail: MOVEQ.L #FALSE,D0
BRA.B BuildDone
* ------------ Make window visible.
AllRastersOK: MOVEA.L A3,A0
BSR.B @SwapBits
* ------------ ClearWindow(Window)
MOVEA.L A3,A0
JSR @ClearWindow(PC)
* ------------ return TRUE
MOVEQ.L #TRUE,D0
BuildDone: MOVEM.L (SP)+,D2-D5/A2-A3/A6
RTS
****************************************************************************
* RemoveBitMap(Window) - Remove allocated rasters in the BitMap structure. *
* *
* Input: *
* Window - Window with bitmap. *
* Output: *
* none *
****************************************************************************
@RemoveBitMap: MOVEM.L D4-D7/A2/A6,-(SP)
* ------------ Anything to remove ?
TST.W (A0) * BitMapOK
BEQ.B RemoveDone
CLR.W (A0) * BitMapOK
* ------------ Remove all allocated rasters.
MOVEQ.L #0,D7
LEA wwd_Bm(A0),A2
MOVE.B bm_Depth(A2),D7
MOVE.W wwd_Width(A0),D6
EXT.L D6
MOVE.W wwd_Height(A0),D5
EXT.L D5
ADDQ.L #bm_Planes,A2
MOVEA.L _GfxBase(A4),A6
MOVEQ.L #0,D4
*************************************
* D4 = Counter A2 = Planes *
* D5 = WindowHeight A0 = Window *
* D6 = WindowWidth A6 = GfxBase *
* D7 = Depth *
*************************************
RemoveNextPl: CMP.W D4,D7
BEQ.B RemoveDone
ADDQ.W #1,D4
* ------------ This raster allocated ?
MOVEA.L (A2)+,A0
MOVE.L A0,D0
BEQ.B RemoveDone
* ------------ FreeRaster(Planes++,Width,Height);
MOVE.L D6,D0
MOVE.L D5,D1
JSR _LVOFreeRaster(A6)
BRA.B RemoveNextPl
RemoveDone: MOVEM.L (SP)+,D4-D7/A2/A6
RTS
*****************************************************************************
* SwapBits(Window) - Works like SwapBitsRastPortClipRect() without bugs :-) *
* *
*****************************************************************************
ALLPLANES EQU -1
B_XOR_C EQU ABNC+ANBC
* ------------ Check to see that window is open
@SwapBits: TST.W (A0)
BEQ.B NoWindow
MOVEM.L D2-D7/A2/A6,-(SP)
* ------------ SrcX
MOVEQ.L #0,D0
MOVE.W wwd_LeftEdge(A0),D0
* ------------ SrcY
MOVEQ.L #0,D1
MOVE.W wwd_TopEdge(A0),D1
* ------------ SizeX
MOVEQ.L #0,D4
MOVE.W wwd_Width(A0),D4
* ------------ SizeY
MOVEQ.L #0,D5
MOVE.W wwd_Height(A0),D5
* ------------ MinTerm
MOVEQ.L #B_XOR_C,D6
* ------------ Mask
MOVEQ.L #ALLPLANES,D7
* ------------ TempA
SUB.L A2,A2
MOVE.L _GfxBase(A4),A6
* ------------ Off-screen bitmap
LEA wwd_Bm(A0),A1
* ------------ On-screen bitmap
MOVE.L _Rp+rp_BitMap(A4),A0
* ------------ DestX
MOVEQ.L #0,D2
* ------------ DestY
MOVEQ.L #0,D3
* ------------ OffScreen = OffScreen XOR OnScreen
BSR.B Swap
* ------------ OnScreen = OnScreen XOR OffScreen (= OffScreen)
BSR.B Swap
* ------------ OffScreen = OffScreen XOR OnScreen (= OnScreen)
BSR.B Swap
MOVEM.L (SP)+,D2-D7/A2/A6
NoWindow: RTS
Swap: MOVEM.L D0/D1/A0/A1,-(SP)
JSR _LVOBltBitMap(A6)
MOVEM.L (SP)+,D0/D1/A0/A1
EXG.L A0,A1
EXG.L D0,D2
EXG.L D1,D3
RTS
********************************************
* FindItemWinSize(ItemWindow,WindowType) *
* *
* Find with and hight needed for all items *
********************************************
@FindItemWinSize:
MOVE.L A2,-(SP)
* ------------ Item = ItemWindow->Items
MOVEA.L wwd_Items(A0),A2
* ------------ Size.Left = WORD_MAX
MOVE.W #$7FFF,_Size(A4)
* ------------ Size.Top = WindowType (ITEMWINDOW -> TopPos >= 0), SUBWINDOW -> no limit */
MOVE.W D0,_Size+ws_Top(A4)
* ------------ Size.Right = Size.Bottom = WORD_MIN
MOVE.W #$8000,D0
MOVE.W D0,_Size+ws_Right(A4)
MOVE.W D0,_Size+ws_Bottom(A4)
* ------------ CheckItemSize(Item,Item->ItemFill)
1$ MOVEA.L A2,A0
MOVEA.L mi_ItemFill(A0),A1
BSR.B @CheckItemSize
* ------------ Item->Flags & HIGHFLAGS == HIGHIMAGE ?
MOVE.W #HIGHFLAGS,D0
AND.W mi_Flags(A2),D0
BNE.B 2$
* ------------ CheckItemSize(Item,Item->SelectFill)
MOVEA.L A2,A0
MOVEA.L mi_SelectFill(A0),A1
BSR.B @CheckItemSize
* ------------ Check next item.
2$ MOVEA.L (A2),A2
MOVE.L A2,D0
BNE.B 1$
MOVE.L (SP)+,A2
RTS
*********************************************************
* CheckItemSize(Item,Contents) - *
* find the size needed to include Item in window. *
* *
* Input: *
* Item (A0) Item to check. *
* Contents (A1) What to fill (ItemFill/SelectFill). *
* Output: *
* Size New size of window *
*********************************************************
@CheckItemSize:
MOVEM.L D2-D7/A2-A3/A5-A6,-(SP)
MOVEA.L A0,A2 * A2 = Item to check
MOVEA.L A1,A5 * A5 = What to check
LEA _Size(A4),A3 * A3 = SizeSoFar
* ------------ Anything to check ?
Check: MOVE.L A5,D0
BEQ.W CheckDone
MOVE.W mi_LeftEdge(A2),D3 * D3 = LeftEdge
MOVE.W mi_TopEdge(A2),D2 * D2 = TopEdge
MOVE.W D3,D7 * D7 = Left
MOVE.W D2,D6 * D6 = Top
* ------------ ITEMTEXT or ITEMIMAGE ?
MOVEQ.L #ITEMTEXT,D0
AND.W mi_Flags(A2),D0
BEQ.B ItemImage
* ------------ Add IText position to left and top.
ADD.W it_LeftEdge(A5),D7
ADD.W it_TopEdge(A5),D6
MOVE.W D7,D5 * D5 = Right
MOVE.W D6,D4 * D4 = Bottom
* ------------ What font to use ?
MOVE.L it_ITextFont(A5),D0
BEQ.B DefaultFont
* ------------ Find hight of string in pixels and add to top.
MOVEA.L D0,A0
ADD.W ta_YSize(A0),D4 * D4 = Bottom
* ------------ Find length of string in pixels.
MOVEA.L A5,A0
MOVEA.L _IntuitionBase(A4),A6
JSR _LVOIntuiTextLength(A6)
* ------------ Add to LeftEdge.
ADD.W D0,D5 * D5 = Right
BRA.B NextText
* ------------ Find length of string with default font.
DefaultFont: MOVEA.L it_IText(A5),A0
JSR @Mystrlen(PC)
LEA _Rp(A4),A1
MOVEA.L it_IText(A5),A0
MOVEA.L _GfxBase(A4),A6
JSR _LVOTextLength(A6)
* ------------ Add to LeftEdge to get rightedge.
ADD.W D0,D5
* ------------ Find hight of string in pixels and add to top to get bottom.
MOVE.W _Rp+rp_TxHeight(A4),D4
ADD.W D6,D4
* ------------ Move to next text.
NextText: MOVEA.L it_NextText(A5),A5
BRA.B CheckLeft
* ------------ Add Image position to left and top.
ItemImage: ADD.W (A5),D7
ADD.W ig_TopEdge(A5),D6
* ------------ Add Image width and height to right and bottom.
MOVE.W D7,D5
MOVE.W D6,D4
ADD.W ig_Width(A5),D5 * D5 = Right
ADD.W ig_Height(A5),D4 * D4 = Bottom
* ------------ Move to next image
MOVE.L ig_NextImage(A5),A5
* ------------ Find lowest leftedge.
CheckLeft: CMP.W D7,D3 * D3 = LeftEdge
BGE.B 1$
MOVE.W D3,D7
1$: CMP.W (A3),D7
BGE.B CheckRight
MOVE.W D7,(A3)
* ------------ Find Biggest RightEdge
CheckRight: ADD.W mi_Width(A2),D3 * D3 = RightEdge
CMP.W D5,D3
BLE.B 1$
MOVE.W D3,D5
* ------------ If item has subitem make room for pointer.
1$: TST.L mi_SubItem(A2)
BEQ.B 2$
ADDQ.W #6,D5
* ------------ If screentype is HIRESSCREEN make pointer bigger.
TST.W _ScreenType(A4)
BNE.B 2$
ADDQ.W #4,D5
2$: CMP.W ws_Right(A3),D5
BLE.B CheckTop
MOVE.W D5,ws_Right(A3)
* ------------ Find lowest Topedge.
CheckTop: CMP.W D6,D2 * D2 = TopEdge
BGE.B 1$
MOVE.W D2,D6
1$: CMP.W ws_Top(A3),D6
BGE.B CheckBottom
MOVE.W D6,ws_Top(A3)
* ------------ Find biggest bottompos.
CheckBottom: ADD.W mi_Height(A2),D2 * D2 = BottomEdge
CMP.W D4,D2
BLE.B 1$
MOVE.W D2,D4
1$: CMP.W ws_Bottom(A3),D4
BLE.B 2$ * Size comes before speed.
MOVE.W D4,ws_Bottom(A3)
2$ BRA.W Check
CheckDone: MOVEM.L (SP)+,D2-D7/A2-A3/A5-A6
RTS
**********************************************************
* Select() - Do selection *
**********************************************************
@SelectItem: MOVEM.L D2-D3/A2-A3/A5,-(SP)
********************
* Check subwindow. *
********************
* ------------ SubWindow.BitMapOk == TRUE ?
MOVEA.L A4,A2 * _SubWindow
TST.W (A2)
BEQ.B CheckItem * No
* ------------ NewSubItem = FindMouseItem(&SubWindow)
MOVEA.L A2,A0
JSR @FindMouseItem(PC)
MOVEA.L D0,A3
********************
* A2 = SubWindow *
* A3 = NewSubItem *
********************
* ------------ NewSubItem == CurrentSubItem ?
MOVEA.L _CurrentSubItem(A4),A0
CMPA.L A0,A3
BEQ.B 4$ * Yes
***********************
* A0 = CurrentSubItem *
* A2 = SubWindow *
* A3 = NewSubItem *
***********************
* ------------ CurrentSubItem == NULL ?
MOVE.L A0,D0
BEQ.B 1$ * Yes
* ------------ HighLightItem(CurrentSubItem,&SubWindow,HIGHLIGHTOFF)
MOVEQ.L #1,D0
MOVEA.L A2,A1
JSR @HighLightItem(PC)
BRA.B 2$
* ------------ TempItem == NULL ?
1$ MOVE.L _TempItem(A4),D2
BEQ.B 2$ * Yes
* ------------ CurrentItem = TempItem.
MOVE.L D2,_CurrentItem(A4)
* ------------ TempItem = NULL.
CLR.L _TempItem(A4)
* ------------ HighLightCurrItemBehind(HIGHLIGHTON)
MOVEQ.L #0,D0
JSR @HighLightCurrItemBehind(PC)
* ------------ CurrentSubItem = NewSubItem.
2$ MOVE.L A3,_CurrentSubItem(A4)
* ------------ CurrentSubItem == NULL ?
BEQ.B 3$ * Yes
* ------------ HighLightItem(NewSubItem,&SubWindow,HIGHLIGHTON)
MOVEQ.L #0,D0
MOVEA.L A3,A0
MOVEA.L A2,A1
JSR @HighLightItem(PC)
BRA.B 4$
* ------------ HighLightCurrItemBehind(HIGHLIGHTOFF)
3$ MOVEQ.L #1,D0
JSR @HighLightCurrItemBehind(PC)
* ------------ TempItem = CurrentItem.
MOVE.L _CurrentItem(A4),_TempItem(A4)
* ------------ CurrentItem = NULL.
CLR.L _CurrentItem(A4)
* ------------ Mouse in SubWindow ?
4$ MOVEA.L A2,A0
JSR @MouseInWindow(PC)
TST.W D0
BNE.W SelectDone * Yes
*********************
* Check itemwindow. *
*********************
* ------------ ItemWindow.BitMapOk == TRUE ?
CheckItem: LEA _ItemWindow(A4),A3
TST.W (A3)
BEQ.W CheckMenu * No
* ------------ Mouse in ItemWindow ?
MOVEA.L A3,A0
JSR @MouseInWindow(PC)
TST.W D0
BEQ.B 3$ * No
* ------------ NewItem = FindMouseItem(&ItemWindow).
MOVEA.L A3,A0
JSR @FindMouseItem(PC)
MOVEA.L D0,A5
MOVE.L _CurrentItem(A4),D2
***************************************
* A2 = SubWindow D2 = CurrentItem *
* A3 = ItemWindow *
* A5 = NewItem *
***************************************
* ------------ NewItem != CurrentItem
CMPA.L _CurrentItem(A4),A5
BEQ.W SelectDone * No
* ------------ SubWindow open ?
TST.W (A2)
BEQ.B 1$ * No
* ------------ Close it.
MOVEA.L A2,A0
JSR @CloseItemWindow(PC)
* ------------ TempItem = NULL.
CLR.L _TempItem(A4)
* ------------ CurrentItem != NULL ?
1$ TST.L D2
BEQ.B 2$ * No
* ------------ HighLightItem(CurrentItem,&ItemWindow,HIGHLIGHTOFF)
MOVEQ.L #1,D0
MOVE.L D2,A0
MOVEA.L A3,A1
JSR @HighLightItem(PC)
* ------------ CurrentItem = NewItem.
2$ MOVE.L A5,_CurrentItem(A4)
MOVE.L A5,D2
* ------------ NewItem != NULL ?
BEQ.W SelectDone * Yes
* ------------ HighLightItem(NewItem,&ItemWindow,HIGHLIGHTON)
MOVEQ #0,D0
MOVEA.L A5,A0
MOVEA.L A3,A1
JSR @HighLightItem(PC)
* ------------ SubWindow.ItemsEnabled = ItemWindow.ItemsEnabled ?
* ------------ (NewItem->Flags & ITEMENABLED) : 0
MOVE.W _ItemWindow+wwd_ItemsEnabled(A4),D0
BEQ.B 25$
MOVEQ.L #ITEMENABLED,D0
AND.W mi_Flags(A5),D0
25$ MOVE.W D0,_SubWindow+wwd_ItemsEnabled(A4)
* ------------ SubWindow.Items = NewItem->SubItem.
MOVE.L mi_SubItem(A5),_SubWindow+wwd_Items(A4)
* ------------ SubItem.Window != NULL ?
BEQ.W SelectDone * No
* ------------ Open item window
MOVE.L D2,A0
MOVE.W mi_TopEdge(A0),D0
SUB.W _ItemWindow+wwd_TopValue(A4),D0
MOVE.W #$7FFF,D1
MOVEA.L A2,A0
MOVEA.L A3,A1
JSR @OpenItemWindow(PC)
BRA.W SelectDone
* ------------ CurrentItem != NULL ?
3$ TST.L _CurrentItem(A4)
BEQ.B CheckMenu
* ------------ SubWindow open ?
TST.W (A2)
BEQ.B 4$ * No
* ------------ HighLightCurrItemBehind(HIGHLIGHTOFF)
MOVEQ.L #1,D0
JSR @HighLightCurrItemBehind(PC)
* ------------ TempItem = CurrentItem.
MOVE.L _CurrentItem(A4),_TempItem(A4)
BRA.B 5$
* ------------ HighLightItem(CurrentItem,&ItemWindow,HIGHLIGHTOFF)
4$ MOVEQ.L #1,D0
MOVEA.L _CurrentItem(A4),A0
MOVEA.L A3,A1
JSR @HighLightItem(PC)
* ------------ CurrentItem = NULL.
5$ CLR.L _CurrentItem(A4)
*********************
* Check menuwindow. *
*********************
**********************
* A2 = SubWindow *
* A3 = ItemWindow *
**********************
* ------------ MouseInWindow(MenuWindow) ?
CheckMenu: LEA _MenuWindow(A4),A5
MOVEA.L A5,A0
JSR @MouseInWindow(PC)
TST.W D0
BEQ.W SelectDone * No
* ------------ NewMenuNr = (MouseY - MenuWindow.TopEdge - BORDERSIZE)/MenuFontSize + 1
MOVE.W _MouseY(A4),D2
SUB.W wwd_TopEdge(A5),D2
SUBQ.W #2,D2
ANDI.L #$0000FFFF,D2
DIVU.W _MenuFontSize(A4),D2
ADDQ.W #1,D2
* ------------ NewMenuNr == CurrentMenuNr ?
MOVE.W _CurrentMenuNr(A4),D3
CMP.W D3,D2
BEQ.B SelectDone * Yes
****************************************
* A2 = SubWindow D2 = NewMenuNr *
* A3 = ItemWindow D3 = CurrentMenuNr *
* A5 = MenuWindow *
****************************************
* ------------ CurrentMenuNr == 0 ?
TST.W D3
BEQ.B 2$ * Yes
* ------------ ItemWindow.BitMapOk
TST.W (A3)
BEQ.B 1$ * No
* ------------ CloseItemWindow(SubWindow)
MOVEA.L A2,A0
JSR @CloseItemWindow(PC)
* ------------ CloseItemWindow(&ItemWindow);
MOVEA.L A3,A0
JSR @CloseItemWindow(PC)
* ------------ TempItem = NULL
CLR.L _TempItem(A4)
* ------------ ToggleMenu(CurrentMenuNr,CurrentMenuPtr) - HIGHLIGHTOFF -
1$ MOVE.W D3,D0
MOVEA.L _CurrentMenuPtr(A4),A0
JSR @ToggleMenu(PC)
* ------------ CurrentMenuPtr = FindMenuPtr(NewMenuNr)
2$ MOVE.W D2,D0
JSR @FindMenuPtr(PC)
MOVE.L D0,_CurrentMenuPtr(A4)
* ------------ CurrentMenuPtr == NULL ?
TST.L D0
BNE.B 3$ * No
* ------------ CurrentMenuNr = 0
CLR.W _CurrentMenuNr(A4)
BRA.B SelectDone
* ------------ CurrentMenuNr = NewMenuNr
3$ MOVE.W D2,_CurrentMenuNr(A4)
MOVE.W D2,_LastSelectedNum(A4)
MOVE.W D2,D3
* ------------ ItemWindow.ItemsEnabled = CurrentMenuPtr->Flags & MENUENABLED
MOVEA.L _CurrentMenuPtr(A4),A0
MOVEQ.L #MENUENABLED,D0
AND.W mu_Flags(A0),D0
MOVE.W D0,_ItemWindow+wwd_ItemsEnabled(A4)
* ------------ ItemWindow.Items = CurrentMenuPtr->FirstItem
MOVE.L mu_FirstItem(A0),_ItemWindow+wwd_Items(A4)
* ------------ ToggleMenu(NewMenuNr,CurrentMenuPtr) - HIGHLIGHTON -
MOVE.W D2,D0
JSR @ToggleMenu(PC)
* ------------ ItemWindow->Items == NULL ?
TST.L _ItemWindow+wwd_Items(A4)
BEQ.B SelectDone * Yes
* ------------ ItemsTopPos = (CurrentMenuNr - 1) * MenuFontSize + MenuWindow.TopEdge
MOVE.W D3,D0
SUBQ.W #1,D0
MULU.W _MenuFontSize(A4),D0
ADD.W _MenuWindow+wwd_TopEdge(A4),D0
* ------------ OpenItemWindow(ItemWindow,MenuWindow,ItemsTopPos,ITEMWINDOW)
MOVEA.L A3,A0
MOVEA.L A5,A1
MOVEQ.L #0,D1
JSR @OpenItemWindow(PC)
SelectDone: MOVEM.L (SP)+,D2-D3/A2-A3/A5
RTS
*****************************************************************
* FinalSelect() - Do checkmarking and calculate Menupick value. *
* *
* Input: *
* none *
* Output: *
* return - MenuPick-value or MENUNULL. *
*****************************************************************
@FinalSelect: MOVEM.L D6-D7/A2-A3,-(SP)
* ------------ SubItemNr = NOSUB
MOVEQ #$1F,D7
MOVEA.L _CurrentSubItem(A4),A2
MOVEA.L _CurrentItem(A4),A3
* ------------ CurrentSubItem == NULL ?
MOVE.L A2,D0
BEQ.B 1$ * Yes
* ------------ CurrentSubItem->Flags & SubWindow.ItemsEnabled & ITEMENABLED
MOVEQ.L #ITEMENABLED,D0
AND.W mi_Flags(A2),D0
AND.W _SubWindow+wwd_ItemsEnabled(A4),D0
BEQ.B 1$ * No
* ------------ Subitem selected -> checkmark and draw all subitems again.
* ------------ CheckMark(CurrentSubItem,SubWindow.Items)
MOVEA.L A2,A0
MOVEA.L _SubWindow+wwd_Items(A4),A1
JSR @CheckMark(PC)
* ------------ DrawAllItems(&SubWindow)
MOVEA.L A4,A0 * _SubWindow
JSR @DrawAllItems(PC)
* ------------ HighLightItem(CurrentSubItem,&SubWindow,HIGHLIGHTON)
MOVEQ.L #0,D0
MOVEA.L A2,A0
MOVEA.L A4,A1 * _SubWindow
JSR @HighLightItem(PC)
* ------------ CurrentSubItem->NextSelect = MENUNULL
MOVE.W #$FFFF,mi_NextSelect(A2)
* ------------ Find the number of the selected subitem
MOVEA.L A2,A0
MOVEA.L _SubWindow+wwd_Items(A4),A1
JSR @FindItemNr(PC)
MOVE.L D0,D7
* ------------ Remove the subitem-window so we can checkmark the items
MOVEA.L A4,A0 * _SubWindow
JSR @SwapBits(PC)
BRA.B 3$
* ------------ CurrentItem == NULL ?
1$ MOVE.L A3,D0
BEQ.B 2$
* ------------ CurrentItem->Flags & ITEMENABLED ?
MOVEQ.L #ITEMENABLED,D0
AND.W mi_Flags(A3),D0
BEQ.B 2$ * No
* ------------ ItemWindow.ItemsEnabled & MENUENABLED ?
TST.W _ItemWindow+wwd_ItemsEnabled(A4)
BEQ.B 2$ * No
* ------------ CurrentItem->SubItem == NULL ?
TST.L mi_SubItem(A3)
BNE.B 2$ * No
* ------------ CurrentItem->NextSelect = MENUNULL
MOVE.W #$FFFF,mi_NextSelect(A3)
BRA.B 3$
* ------------ Nothing is selected -> exit
2$ MOVEQ.L #-1,D0
BRA.B 6$
* ------------ CheckMark(CurrentItem,ItemWindow.Items)
3$ MOVEA.L A3,A0
MOVEA.L _ItemWindow+wwd_Items(A4),A1
BSR.B @CheckMark
* ------------ Find number of selected item,
MOVEA.L A3,A0
MOVEA.L _ItemWindow+wwd_Items(A4),A1
JSR @FindItemNr(PC)
MOVE.L D0,D6
* ------------ DrawAllItems(&ItemWindow)
LEA _ItemWindow(A4),A0
JSR @DrawAllItems(PC)
* ------------ HighLightItem(CurrentItem,&ItemWindow,HIGHLIGHTON)
MOVEQ.L #0,D0
MOVEA.L A3,A0
LEA _ItemWindow(A4),A1
JSR @HighLightItem(PC)
* ------------ Restore subwindow.
MOVEA.L A4,A0 * _SubWindow
JSR @SwapBits(PC)
* ------------ MenuNum = SHIFTMENU(FindRealMenuNum(CurrentMenuNr)) |
* ------------ SHIFTITEM(ItemNr) |
* ------------ SHIFTSUB(SubItemNr)
MOVE.W _CurrentMenuNr(A4),D0
JSR @FindMenuPtr(PC)
MOVEA.L D0,A1
MOVEA.L _Menues(A4),A0
MOVEQ.L #0,D0
4$ CMPA.L A0,A1
BEQ.B 5$
MOVEA.L (A0),A0 * mu_NextMenu(A0)
ADDQ.L #1,D0
BRA.B 4$
* ------------ SHIFTITEM(ItemNr)
5$ ANDI.W #$3F,D6
ASL.W #5,D6
OR.W D6,D0
* ------------ SHIFTSUB(SubItemNr)
ANDI.W #$1F,D7
ASL.W #8,D7
ASL.W #3,D7
OR.W D7,D0
6$ MOVEM.L (SP)+,D6-D7/A2-A3
RTS
********************************************************
* CheckMark(Selected,Items) - Checkmark selected item. *
* *
* Input: *
* Selected - The selected item. *
* Items - All items on the same level. *
* Output: *
* none *
********************************************************
@CheckMark: MOVE.W mi_Flags(A0),D1
* ------------ Selected->Flags & CHECKIT ?
MOVEQ.L #CHECKIT,D0
AND.W D1,D0
BEQ.B 4$ * No
* ------------ Selected->Flags & CHECKED ?
MOVE.W #CHECKED,D0
AND.W D1,D0
BEQ.B 1$ * No
* ------------ Selected->Flags & MENUTOGGLE ?
MOVEQ.L #MENUTOGGLE,D0
AND.W D1,D0
BEQ.B 4$ * No
* ------------ Selected->Flags &= ~CHECKED - Togglemenu -
BCLR #0,mi_Flags(A0)
BRA.B 4$
* ------------ Selected->Flags |= CHECKED
1$ BSET #0,mi_Flags(A0)
* ------------ Handle mutual exclusion.
* ------------ Exclude = Selected->MutualExclude
MOVE.L mi_MutualExclude(A0),D1
BEQ.B 4$
* ------------ Exclude >>= 1
2$ LSR.L #1,D1
BCC.B 3$
* ------------ Items->Flags &= ~CHECKED
BCLR #0,mi_Flags(A1)
* ------------ Items = Items->NextItem
3$ MOVEA.L (A1),A1
* ------------ More items ?
MOVE.L A1,D0
BNE.B 2$ * Yes
4$ RTS
************************************************************
* DrawMenuItem(Item, ItemWindow, Mode) *
* *
* Input: *
* Item - Item to draw. *
* ItemWindow - Data about window to draw item into. *
* Mode.W - ITEMFILL = Draw Item. *
* SELECTFILL = Draw selected item (if any).*
* OUTPUT *
* none *
************************************************************
@DrawMenuItem: MOVEM.L D2-D7/A2-A3/A5-A6,-(SP)
MOVEA.L A0,A3
MOVE.L A1,-(SP)
***************************************
* D0 = Mode A0 = Item *
* A1 = ItemWindow *
* A3 = Item *
***************************************
* ------------ Left = Item->LeftEdge - ItemWindow->LeftValue
MOVE.W mi_LeftEdge(A3),D7
SUB.W wwd_LeftValue(A1),D7
EXT.L D7
* ------------ Right = Left + Item->Width - 1
MOVE.L D7,D2
ADD.W mi_Width(A3),D2
SUBQ.L #1,D2
* ------------ Top = Item->TopEdge - ItemWindow->TopValue
MOVE.W mi_TopEdge(A3),D6
SUB.W wwd_TopValue(A1),D6
EXT.L D6
* ------------ Bottom = Top + Item->Height - 1
MOVE.L D6,D3
ADD.W mi_Height(A3),D3
SUBQ.L #1,D3
LEA _Rp(A4),A5
MOVEA.L _IntuitionBase(A4),A6
* ------------ Find what to Draw.
MOVEA.L mi_ItemFill(A3),A2
TST.W D0 * Mode == ITEMFILL ?
BEQ.B CheckDraw
* ------------ Use selectfill.
MOVEA.L mi_SelectFill(A3),A2
*************************************************
* D0 = Mode A0 = Item *
* D2 = Right A2 = Fill *
* D3 = Bottom A3 = Item *
* D6 = Top A5 = Rp *
* D7 = Left A6 = IntuitionBase *
*************************************************
* ------------ Anything to draw ?
CheckDraw: MOVE.L A2,D0
BEQ.W DrawDone
* ------------ Draw the item.
DrawItem: MOVE.L D6,D4
MOVEA.L A5,A0 * Rp
MOVEA.L A2,A1 * Fill
MOVE.L D7,D0 * Left
MOVE.L D6,D1 * Top
MOVEQ.L #ITEMTEXT,D5
AND.W mi_Flags(A3),D5
BEQ.B DrawImage
* ------------ PrintIText(Fill, Left, Top)
JSR _LVOPrintIText(A6)
ADD.W it_TopEdge(A2),D4
BRA.B DrawCheckMark
* ------------ DrawImage(Fill, Left, Top)
DrawImage: JSR _LVODrawImage(A6)
ADD.W ig_TopEdge(A2),D4
*********************************************
* D2 = Right A2 = Fill *
* D3 = Bottom A3 = Item *
* D4 = ItemTop A5 = Rp *
* D6 = Top A6 = IntuitionBase *
* D7 = Left *
*********************************************
* ------------ Draw CheckMark ?
DrawCheckMark: MOVE.W #CHECKIT+CHECKED,D0
AND.W mi_Flags(A3),D0
CMPI.W #CHECKIT+CHECKED,D0
BNE.B DrawCommKey
* ------------ DrawImage(ActiveWindow->CheckMark, Left, Top)
MOVEA.L _ActiveWindow(A4),A0
MOVEA.L wd_CheckMark(A0),A1 * CheckMark
MOVE.L D7,D0 * Left
MOVE.L D6,D1 * Top
MOVEA.L A5,A0 * Rp
JSR _LVODrawImage(A6)
*********************************************
* D2 = Right A2 = Fill *
* D3 = Bottom A3 = Item *
* D4 = ItemTop A5 = Rp *
* D6 = Top A6 = IntuitionBase *
* D7 = Left *
*********************************************
* ------------ SetDrMd(JAM1)
DrawCommKey: MOVEA.L _GfxBase(A4),A6
MOVEA.L A5,A1 * Rp
MOVEQ.L #RP_JAM1,D0 * JAM1
JSR _LVOSetDrMd(A6)
* ------------ Has item CommadKey ?
MOVEQ.L #COMMSEQ,D0
AND.W mi_Flags(A3),D0
BEQ.B GhostItem
* ------------ KeyLeft = Right - Rp.TxWidth
MOVE.L D2,D5
SUB.W _Rp+rp_TxWidth(A4),D5
*******************************************
* D2 = Right A2 = Fill *
* D3 = Bottom A3 = Item *
* D4 = ItemTop A5 = Rp *
* D5 = KeyLeft A6 = GfxBase *
* D6 = Top *
* D7 = Left *
*******************************************
* ------------ Move(KeyLeft, ItemTop + Rp.TxHeight - 2);
MOVE.L D5,D0
MOVE.L D4,D1
ADD.W _Rp+rp_TxHeight(A4),D1
SUBQ.L #2,D1
MOVEA.L A5,A1
JSR _LVOMove(A6)
* ------------ SetAPen(ActiveWindow->DetailPen)
MOVEQ #00,D0
MOVEA.L _ActiveWindow(A4),A0
MOVE.B wd_DetailPen(A0),D0
MOVEA.L A5,A1
JSR _LVOSetAPen(A6)
* ------------ Text(&Item->Command,1);
LEA mi_Command(A3),A0
MOVEA.L A5,A1
MOVEQ #1,D0
JSR _LVOText(A6)
* ------------ DrawImage(&MyAmigaKeyImage[ScreenType],KeyLeft, ItemTop);
LEA _MyAmigaKeyImage(PC),A1
MOVE.L D5,D0
BSR.B DrawMyImage
MOVEA.L _GfxBase(A4),A6
*******************************************
* D2 = Right A2 = Fill *
* D3 = Bottom A3 = Item *
* D4 = ItemTop A5 = Rp *
* D6 = Top A6 = GfxBase *
* D7 = Left *
*******************************************
* ------------ Ghost Item ?
GhostItem: MOVEQ.L #ITEMENABLED,D0
AND.W mi_Flags(A3),D0
BEQ.B 1$
MOVEA.L (SP),A2
TST.W wwd_ItemsEnabled(A2)
BNE.B SubItem
* ------------ SetAfPt(&Rp, GhostPattern, 1)
1$ LEA _GhostPattern(PC),A0
MOVE.L A0,_Rp+rp_AreaPtrn(A4)
MOVE.B #01,_Rp+rp_AreaPtSz(A4)
* ------------ SetAPen(ActiveWindow->BlockPen)
MOVEQ #0,D0
MOVEA.L _ActiveWindow(A4),A0
MOVE.B wd_BlockPen(A0),D0
MOVEA.L A5,A1
JSR _LVOSetAPen(A6)
* ------------ RectFill(Left, Top, Right, Bottom)
MOVEA.L A5,A1
MOVE.L D7,D0
MOVE.L D6,D1
JSR _LVORectFill(A6)
* ------------ SetAfPt(NormalPattern, 1)
LEA _NormalPattern(PC),A0
MOVE.L A0,_Rp+rp_AreaPtrn(A4)
*******************************************
* D2 = Right *
* D3 = Bottom A3 = Item *
* D4 = ItemTop A5 = Rp *
* D6 = Top A6 = GfxBase *
* D7 = Left *
*******************************************
* ------------ SubItem ?
SubItem: TST.L mi_SubItem(A3)
BEQ.B DrawDone
* ------------ DrawImage(&MySubItemImage[ScreenType],Right,ItemTop);
LEA _MySubItemImage(PC),A1
MOVE.L D2,D0
BSR.B DrawMyImage
DrawDone: ADDQ.L #4,A7
MOVEM.L (SP)+,D2-D7/A2-A3/A5-A6
RTS
******************************
* DrawMyImage *
* A1 - What to draw *
* A5 - Rp *
* D0 - Left *
* D4 - Top *
* *
* Destroyed: D0-D1/A0-A1/A6 *
******************************
DrawMyImage: TST.W _ScreenType(A4)
BEQ.B 1$
MOVEQ.L #ig_SIZEOF,D1
ADDA.L D1,A1
1$ MOVEA.L A5,A0
MOVE.L D4,D1
MOVEA.L _IntuitionBase(A4),A6
JMP _LVODrawImage(A6)
***************************************************
* HighLightItem(Item, ItemWindow, Mode) *
* *
* Input: *
* Item - Item to highlight. *
* ItemWindow - Data for the window to draw in. *
* Mode.W - HIGHLIGHTON or HIGHLIGHTOFF. *
* Output: *
* none *
***************************************************
@HighLightItem:
MOVEM.L D2-D7/A2-A3/A5-A6,-(SP)
MOVEA.L A0,A3
MOVEA.L A1,A2
* ------------ Possible to highlight item ?
MOVEQ.L #ITEMENABLED,D1
AND.W mi_Flags(A3),D1
BEQ.B HighlightDone
TST.W wwd_ItemsEnabled(A2)
BEQ.B HighlightDone
* ------------ Start highlighting.
LEA _Rp(A4),A5
MOVEA.L _GfxBase(A4),A6
MOVE.W #HIGHFLAGS,D7
AND.W mi_Flags(A3),D7
BNE.B NotHighImage
* ------------ Invert Mode and call DrawMenuItem.
* ------------ DrawMenuItem(Item, ItemWindow, !Mode);
HighImage: MOVEQ.L #1,D1
ADDQ.W #1,D0
AND.W D1,D0
JSR @DrawMenuItem(PC)
BRA.B HighlightDone
* ------------ Left = Item->LeftEdge - ItemWindow->LeftValue
NotHighImage: MOVE.W mi_LeftEdge(A3),D6
SUB.W wwd_LeftValue(A2),D6
EXT.L D6
* ------------ Right = Left + Item->Width
MOVE.W mi_Width(A3),D5
EXT.L D5
ADD.L D6,D5
* ------------ Top = Item->TopEdge - ItemWindow->TopValue
MOVE.W mi_TopEdge(A3),D4
SUB.W wwd_TopValue(A2),D4
EXT.L D4
* ------------ Bottom = Top + Item->Height
MOVE.W mi_Height(A3),D3
EXT.L D3
ADD.L D4,D3
* ------------ Set drawmode = COMPLEMENT.
MOVEQ.L #RP_COMPLEMENT,D0
MOVEA.L A5,A1
JSR _LVOSetDrMd(A6)
* ------------ Check out kind of highlighting.
CMPI.W #HIGHBOX,D7
BEQ.B HighBox
CMPI.W #HIGHCOMP,D7
BNE.B HighlightDone
* ------------ RectFill(Left, Top, Right - 1, Bottom - 1)
HighComp: MOVE.L D6,D0
MOVE.L D4,D1
MOVEA.L A5,A1
MOVE.L D5,D2
SUBQ.L #1,D2
SUBQ.L #1,D3
JSR _LVORectFill(A6)
BRA.B HighlightDone
* ------------ DrawRect(Left, Top, Right, Bottom)
HighBox: BSR.B DrawRect
* ------------ DrawRect(Left - 1, Top - 1, Right + 1, Bottom + 1)
ADDQ.L #1,D5
ADDQ.L #1,D3
BSR.B DrawRect
HighlightDone: MOVEM.L (SP)+,D2-D7/A2-A3/A5-A6
RTS
* ------------ Draw a rectangle.
* ------------ Move(--Left,Top).
DrawRect: SUBQ.L #1,D6
MOVE.L D6,D0
MOVE.L D4,D1
MOVEA.L A5,A1
JSR _LVOMove(A6)
* ------------ Draw(Left,Bottom).
MOVE.L D6,D0
MOVE.L D3,D1
BSR.B Draw
* ------------ Draw(Right,Bottom).
MOVE.L D5,D0
MOVE.L D3,D1
BSR.B Draw
* ------------ Draw(Right,--Top).
SUBQ.L #1,D4
MOVE.L D5,D0
MOVE.L D4,D1
BSR.B Draw
* ------------ Draw(Left,Top).
MOVE.L D6,D0
MOVE.L D4,D1
Draw: MOVEA.L A5,A1 * Get RastPort
JMP _LVODraw(A6)
*********************************************
* ToggleMenu(Number,Menu) *
* *
* Input: *
* Number.W - Menu to highlight. *
* Menu - Pointer to the Menu structure. *
* Output: *
* none *
*********************************************
@ToggleMenu: MOVEM.L D2-D3/A6,-(A7)
* ------------ Menu enabled ?
MOVEQ.L #MENUENABLED,D2
AND.W mu_Flags(A0),D2
BEQ.B ToggleDone
MOVE.W D0,D3
* ------------ Set drawmode = COMPLEMENT.
LEA _Rp(A4),A1
MOVEQ #RP_COMPLEMENT,D0
MOVEA.L _GfxBase(A4),A6
JSR _LVOSetDrMd(A6)
* ------------ Invert menu.
* ------------ Bottom = Number * MenuFontSize + MenuWindow.TopEdge.
MOVE.W _MenuFontSize(A4),D2
MULU.W D2,D3
ADD.W _MenuWindow+wwd_TopEdge(A4),D3
* ------------ Top = Bottom - MenuFontSize + BORDERSIZE.
MOVE.L D3,D1
SUB.L D2,D1
ADDQ.L #BORDERSIZE,D1
* ------------ Left = MenuWindow.LeftEdge + BORDERSIZE.
MOVEQ.L #BORDERSIZE,D0
ADD.W _MenuWindow+wwd_LeftEdge(A4),D0
* ------------ Right = MenuWindow.RightEdge - BORDERSIZE.
MOVE.W _MenuWindow+wwd_RightEdge(A4),D2
SUBQ.L #BORDERSIZE,D2
LEA _Rp(A4),A1
JSR _LVORectFill(A6)
ToggleDone: MOVEM.L (A7)+,D2-D3/A6
RTS
******************
* DrawAllMenus() *
* *
******************
@DrawAllMenues:
MOVEM.L D2-D4/D7/A2-A3/A5-A6,-(SP)
* ------------ MenuLeft = MenuWindow.LeftEdge + BORDERSIZE
MOVE.W _MenuWindow+wwd_LeftEdge(A4),D7
ADDQ.W #BORDERSIZE,D7
EXT.L D7
* ------------ MenuTop = MenuWindow.TopEdge
MOVE.W _MenuWindow+wwd_TopEdge(A4),D3
EXT.L D3
* ------------ MenuRight = MenuWindow.RightEdge - BORDERSIZE
MOVE.W _MenuWindow+wwd_RightEdge(A4),D2
SUBQ.W #BORDERSIZE,D2
EXT.L D2
* ------------ MenuPtr = MenuSorted;
MOVEA.L _ActiveWindow(A4),A2
MOVEA.L _MenuSorted(A4),A3
LEA _Rp(A4),A5
MOVEA.L _GfxBase(A4),A6
****************************************
* D2 = MenuRight A2 = ActiveWindow *
* D3 = MenuTop A3 = Menues *
* D7 = MenuLeft A5 = Rp *
* A6 = GfxBase *
****************************************
* ------------ MenuTopOld = MenuTop;
NextMenu: MOVE.L D3,D4
* ------------ MenuTop += MenuFontSize;
ADD.W _MenuFontSize(A4),D3
* ------------ SetAPen(Rp,ActiveWindow->DetailPen)
MOVEQ.L #0,D0
MOVE.B wd_DetailPen(A2),D0
MOVEA.L A5,A1
JSR _LVOSetAPen(A6)
* ------------ Move(Rp, MenuLeft, MenuTop - 1)
MOVE.L D7,D0
MOVE.L D3,D1
SUBQ.L #1,D1
MOVEA.L A5,A1
JSR _LVOMove(A6)
* ------------ Text(Rp,MenuSorted->MenuPtr->MenuName,Mystrlen(MenuSorted->MenuPtr->MenuName))
MOVE.L ms_MenuPtr(A3),A0
MOVEA.L mu_MenuName(A0),A0
MOVE.L A0,-(SP)
JSR @Mystrlen(PC)
MOVEA.L A5,A1
MOVEA.L (SP)+,A0
JSR _LVOText(A6)
* ------------ GhostItem ?
MOVEQ.L #MENUENABLED,D0
MOVE.L ms_MenuPtr(A3),A0
AND.W mu_Flags(A0),D0
BNE.B NoMenuGhost
* ------------ SetAfPt(Rp, GhostPattern, 1)
LEA _GhostPattern(PC),A0
MOVE.L A0,_Rp+rp_AreaPtrn(A4)
MOVE.B #1,_Rp+rp_AreaPtSz(A4)
* ------------ SetAPen(Rp,ActiveWindow->BlockPen)
MOVE.B wd_BlockPen(A2),D0
MOVEA.L A5,A1
JSR _LVOSetAPen(A6)
* ------------ RectFill(Rp,MenuLeft,MenuTopOld + BORDERSIZE,MenuRight,MenuTop)
MOVE.L D7,D0
MOVE.L D4,D1
ADDQ.W #2,D1
MOVEA.L A5,A1
JSR _LVORectFill(A6)
* ------------ SetAfPt(&Rp,NormalPattern,1);
LEA _NormalPattern(PC),A0
MOVE.L A0,_Rp+rp_AreaPtrn(A4)
* ------------ MenuSaved = MenuSaved->Next
NoMenuGhost: MOVEA.L (A3),A3 * ms_Next(A3)
* ------------ More menues ?
MOVE.L A3,D0
BNE.B NextMenu
MOVEM.L (SP)+,D2-D4/D7/A2-A3/A5-A6
RTS
********************************************
* MySetMenuStrip, MyClearMenuStrip, *
* MyOnMenu, MyOffMenu *
* *
* My replacements for intuition functions. *
********************************************
@MySetMenuStrip:
MOVE.L A2,-(SP)
MOVEA.L _OldSetMenuStrip,A2
BRA.B CallOldFunction
@MyClearMenuStrip:
MOVE.L A2,-(SP)
MOVEA.L _OldClearMenuStrip,A2
BRA.B CallOldFunction
@MyOnMenu: MOVE.L A2,-(SP)
MOVEA.L _OldOnMenu,A2
BRA.B CallOldFunction
@MyOffMenu: MOVE.L A2,-(SP)
MOVEA.L _OldOffMenu,A2
* ------------ Obtain semaphore and then call the intuition function.
CallOldFunction:
MOVE.L A6,-(SP)
MOVEM.L D0/A0-A1/A6,-(SP)
LEA _PopUpSemaphore,A0
MOVE.L (AbsExecBase).W,A6
JSR _LVOObtainSemaphore(A6)
MOVEM.L (SP)+,D0/A0-A1/A6
JSR (A2)
LEA _PopUpSemaphore,A0
MOVE.L (AbsExecBase).W,A6
JSR _LVOReleaseSemaphore(A6)
MOVE.L (SP)+,A6
MOVE.L (SP)+,A2
RTS
* ------------ This is the shortest strlen (I think).
@Mystrlen: MOVEQ.L #-1,D0
1$: ADDQ.L #1,D0
TST.B (A0)+
BNE.B 1$
RTS
* Put these images in the code segment
_MyAmigaKeyImage:
dc.w -25,0,23,8,1
dc.l _AmigaKeyHighRes
dc.b 1,0
dc.l 0
dc.w -16,0,14,8,1
dc.l _AmigaKeyLoRes
dc.b 1,0
dc.l 0
_MySubItemImage:
dc.w 2,0,8,7,1
dc.l _SubItemPointerH
dc.b 1,0
dc.l 0
dc.w 1,0,4,7,1
dc.l _SubItemPointerL
dc.b 1,0
dc.l 0
_GhostPattern: dc.w $1111,$4444
_NormalPattern: dc.w $ffff,$ffff
section __MERGED,bss
xref _PopUpSemaphore
xref _Screen
xref _LayersBase
xref _Menues
xref _ActiveWindow
xref _LastWindow
xref _LastSelected
xref _MenuFontSize
xref _TimerSignal
xref _TimerReqBlock
xref _TimerPort
xref _MouseX
xref _MouseY
xref _IntuitionBase
xref _SubWindow
xref _ItemWindow
xref _MenuWindow
xref _CurrentMenuNr
xref _CurrentMenuPtr
xref _CurrentItem
xref _CurrentSubItem
xref _TempItem
xref _ScreenType
xref _Rp
xref _GfxBase
xref _Size
xref _InputReqBlock
xref _OldSetMenuStrip
xref _OldClearMenuStrip
xref _OldOffMenu
xref _OldOnMenu
xref _SortRemember
xref _MenuSorted
xref _LastSelectedNum
END