/* * mainloop.c V1.4 * * main event loop * * (c) 1991 by Stefan Becker * */ #include "ToolManager.h" /* structures for quit requester */ static struct EasyStruct QuitES={sizeof(struct EasyStruct),0,MyName, "Really quit?","Ok|Cancel"}; /* Set global quit flag, if no WB tool is currently active */ /* Display a safety requester if the user wants it */ void SetQuitFlag(void) { if (running=(wbactive>0)) /* Is a WB tool currently active? */ DisplayBeep(NULL); /* Yes, we can't quit! */ else if (ShowQuitReq) /* Shall we show a quit requester? */ running=!EasyRequest(NULL,&QuitES,NULL,NULL); } /* The main processing loop */ void mainloop(void) { ULONG sigs,bsigs,psigs,csigs; /* Buffers for signals */ /* Init icon position */ MyIcon->do_CurrentX=IconXPos; MyIcon->do_CurrentY=IconYPos; if (ShowIcon) /* Display our icon? */ { /* If we have an icon, we don't need the "Open TM Window" menu entry */ RemoveAppMenuItem(OTWAppMenuItem); /* Notify Workbench about icon */ if (!(MyAppIcon=AddAppIcon(NULL,NULL,MyName,MyMP,NULL,MyIcon,TAG_DONE))) cleanup(9); } /* Add TM pop up window hot key */ AttachCxObj(MyBroker,HotKey(PopUpHotKey,MyBrokerPort,NULL)); /* Commodities error? */ if (CxObjError(MyBroker)) cleanup(10); /* All things set up --> activate our broker */ ActivateCxObj(MyBroker,1); bsigs=SIGBREAKF_CTRL_C| /* break signals */ SIGBREAKF_CTRL_D|SIGBREAKF_CTRL_E|SIGBREAKF_CTRL_F; psigs=1L<mp_SigBit; /* port signal */ csigs=1L<mp_SigBit; /* Commodities Broker port signal */ sigs=bsigs|psigs|csigs; /* merge signals */ /* Show status window on startup? */ if (ShowStatusWindow) OpenStatusWindow(); while (running) /* main event loop */ { ULONG gotsigs; /* received signals */ /* Wait for specified signals */ gotsigs=Wait(sigs|statwinsig|editwinsig); if ((gotsigs&bsigs)) /* Got break signals and is no WB tool */ SetQuitFlag(); /* running? Yes, quit program */ if (gotsigs&psigs) /* Message arrived at message port? */ { struct AppMessage *msg; /* pointer to received message */ while (msg=GetMsg(MyMP)) /* Yes, empty message queue */ if (msg->am_Message.mn_Node.ln_Type==NT_REPLYMSG) /* Replied message? */ { /* This is the death message from a tool we started some time ago */ struct WBStartup *wbs=(struct WBStartup *) msg; struct WBArg *wa=wbs->sm_ArgList; int i=wbs->sm_NumArgs; while (i--) { UnLock(wa->wa_Lock); /* Free WB argument */ if (wa->wa_Name) free(wa->wa_Name); wa++; } if (wbs->sm_ToolWindow) /* Free tool window specification */ free(wbs->sm_ToolWindow); UnLoadSeg(wbs->sm_Segment); /* Unload code */ free(wbs); /* Free WBStartup */ wbactive--; /* One tool closed down */ } else { switch(msg->am_Type) /* Switch between message types */ { case MTYPE_APPWINDOW: /* Window action */ /* Add Workbench parameters to tool list */ if (!WBAddToolNode(msg->am_ArgList,msg->am_NumArgs)) DisplayBeep(NULL); if (statwinsig) /* Refresh status window if open */ RefreshStatusWindow(); break; case MTYPE_APPICON: /* Icon action */ if (msg->am_ID) /* Tool icon selected? */ /* Start Tool, ID == Address of ToolNode */ StartTool((struct ToolNode *) msg->am_ID,msg); else /* User selected program icon */ if (msg->am_NumArgs==0) /* Did the user double click my icon? */ OpenStatusWindow(); /* Yes! Open status window */ else /* User dropped an icon on my icon */ { /* Add Workbench parameters to tool list */ if (!WBAddToolNode(msg->am_ArgList,msg->am_NumArgs)) DisplayBeep(NULL); if (statwinsig) /* Refresh status window if open */ RefreshStatusWindow(); } break; case MTYPE_APPMENUITEM: /* Menu action */ switch(msg->am_ID) { case 0: /* "Quit ToolManager" menu item */ SetQuitFlag(); break; case 1: /* "Open TM Window" menu item */ OpenStatusWindow(); break; default: /* Default: Tool selected */ /* Start Tool, ID == Address of ToolNode */ StartTool((struct ToolNode *) msg->am_ID,msg); break; } break; } /* end of switch(msg->am_Type) */ ReplyMsg((struct Message *) msg); /* Reply message to sender */ } /* end of if (msg->......) */ } /* end of if (gotsigs&psigs) */ if (gotsigs&csigs) /* Got broker port signal? */ { /* Handle commodities event */ struct CxMsg *msg; while (msg=GetMsg(MyBrokerPort)) /* Retrieve Messages from port */ { switch(CxMsgType(msg)) { case CXM_IEVENT: /* Received a hot key event */ struct ToolNode *tn; /* ID contains pointer to corresponding ToolNode */ if (tn=(struct ToolNode *) CxMsgID(msg)) StartTool(tn,NULL); else OpenStatusWindow(); /* Pop up window hot key */ break; case CXM_COMMAND: /* Received a commodities command */ switch(CxMsgID(msg)) { case CXCMD_DISABLE: /* Disable broker */ ActivateCxObj(MyBroker,0); break; case CXCMD_ENABLE: /* Enable broker */ ActivateCxObj(MyBroker,1); break; case CXCMD_APPEAR: /* Open status window */ OpenStatusWindow(); break; case CXCMD_DISAPPEAR: /* Close status window */ CloseStatusWindow(); break; case CXCMD_KILL: /* Quit application */ SetQuitFlag(); break; } break; } ReplyMsg(msg); /* Reply message to sender */ } /* end of while (msg=....) */ } /* if (gotsigs&csigs) */ if (gotsigs&statwinsig) /* Got status window signal? */ HandleStatWinEvent(); /* Handle status window event */ if (gotsigs&editwinsig) /* Got edit window signal? */ HandleEditWinEvent(); /* Handle edit window event */ } /* end of main loop */ /* If window open, close it */ CloseStatusWindow(); CloseEditWindow(); /* Exit program */ cleanup(99); }