home *** CD-ROM | disk | FTP | other *** search
- /** ** *** MakeRev Header *** **
- **
- ** ** StickySelect - Selector for ScreenSelect. **
- **
- ** Copyright © 1993,1994 Markus Aalto
- **
- ** Creation date: 27-Jul-93
- **
- ** ------------------------------------------------------------------
- ** $Filename: StickySelect.c $
- ** $Revision: 1.1 $
- ** $Date: 22-Jan-94 $
- **
- ** $Author: Markus_Aalto $
- ** $Comment: Freely Distributable. Use to create your own interfaces. $
- **
- */
-
-
- #include "StickySelect.h"
-
- extern UBYTE version[] = "$VER: StickySelect 1.1 (30-Jan-94)";
-
- void CleanUp( void );
- void ProcessSignals( void );
- void RemoveSemaphoreHook( void );
- BOOL InstallSemaphoreHook( void );
- BOOL OpenInterface( void );
- BOOL UpdateList( void );
- void SignalScreenSelect( ULONG code );
- BOOL ReadParameters( void );
-
- extern struct IntuitionBase *IntuitionBase;
- extern struct GfxBase *GfxBase;
- extern struct Library *GadToolsBase;
- extern struct Library *UtilitiesBase;
-
- struct List screenname_list;
- struct Window *sticky_window = NULL;
- struct Gadget *listview;
- struct Gadget *gadg_context = NULL;
- LONG update_signal = -1;
- SignalUpdateNode *update_node = NULL;
- LONG TopX = 0, TopY = 0;
- LONG Width = 150, Height = 100;
- char *pubscreen_name = NULL;
- APTR vi = NULL;
- struct TextAttr my_font;
- ULONG ARGS[ARG_COUNT] = { NULL, NULL, NULL, NULL, NULL };
-
- int main( int argc, char **argv )
- {
-
- NewList(&screenname_list);
-
-
- if( ReadParameters() ) {
- if( InstallSemaphoreHook() ) {
- if( UpdateList() ) {
-
- ProcessSignals();
- }
-
- RemoveSemaphoreHook();
- }
- }
-
- CleanUp();
-
- return(0);
- }
-
-
- /* Clean up most of the allocated stuff. */
- void CleanUp()
- {
- struct Node *screennode;
-
- if( sticky_window ) CloseWindow( sticky_window );
-
- if( gadg_context ) FreeGadgets(gadg_context);
-
- if( vi ) FreeVisualInfo( vi );
-
- if( pubscreen_name ) FreeVec((void *)pubscreen_name);
-
- if( update_node ) FreeVec((void *)update_node);
-
- if( update_signal != -1 ) FreeSignal( update_signal );
-
- while( screennode = RemHead(&screenname_list) ) {
- if( screennode->ln_Name ) FreeVec((void *)screennode->ln_Name);
- FreeVec((void *)screennode);
- }
- }
-
-
- /* Install a SignalUpdateNode to TaskList in "ScreenSelect" public semaphore.
- ** And infrom ScreenSelect about it. */
- BOOL InstallSemaphoreHook()
- {
- BOOL retval = FALSE;
- UpdateDataSemaphore *uds;
-
- update_signal = AllocSignal(-1);
- if( update_signal != -1 ) {
- update_node = (SignalUpdateNode *)AllocVec(sizeof(SignalUpdateNode),
- MEMF_PUBLIC|MEMF_CLEAR);
- if( update_node ) {
- update_node->su_Task = FindTask(NULL);
- update_node->su_Signal = update_signal;
-
- Forbid();
- if( uds = (UpdateDataSemaphore *)FindSemaphore(SEMAPHORE_NAME) ) {
- ObtainSemaphore( (struct SignalSemaphore *)uds );
-
- Permit();
-
- AddTail(&uds->ud_TaskList, update_node);
-
- if( uds->ud_ScreenSelectTask ) {
- /* Notify about new client. */
- uds->ud_code = CODE_NEWCLIENT;
- Signal(uds->ud_ScreenSelectTask,
- 1 << uds->ud_ScreenSelectSignal);
- }
-
- ReleaseSemaphore( (struct SignalSemaphore *)uds );
-
- retval = TRUE;
- }
- else Permit();
- }
- }
-
- return(retval);
- }
-
-
- /* Release the SignalUpdateNode from the ScreenSelect sempahore. */
- void RemoveSemaphoreHook()
- {
- UpdateDataSemaphore *uds;
-
- Forbid();
- if( uds = (UpdateDataSemaphore *)FindSemaphore(SEMAPHORE_NAME) ) {
- ObtainSemaphore( (struct SignalSemaphore *)uds );
- Permit();
-
- Remove(update_node);
-
- ReleaseSemaphore( (struct SignalSemaphore *)uds );
- }
- else Permit();
- }
-
-
- void ProcessSignals()
- {
- ULONG signal, signalmask, stickymask;
- BOOL END;
- ULONG class;
- UWORD code;
- ULONG old_secs = 0, old_mics = 0;
- struct IntuiMessage *imsg;
-
-
- END = OpenInterface();
-
- while( !END ) {
- stickymask = (1 << sticky_window->UserPort->mp_SigBit);
- signalmask = (1 << update_signal) | SIGBREAKF_CTRL_C | stickymask;
-
- signal = Wait( signalmask );
-
- if( signal & SIGBREAKF_CTRL_C ) {
- END = TRUE;
- }
- else if( signal & (1 << update_signal) ) {
- GT_SetGadgetAttrs(listview, sticky_window, NULL,
- GTLV_Labels, ~0,
- TAG_END);
-
- END = !UpdateList();
-
- GT_SetGadgetAttrs(listview, sticky_window, NULL,
- GTLV_Labels, &screenname_list,
- TAG_END);
- }
- else if( signal & stickymask ) {
- while( (!END) && (imsg = GT_GetIMsg(sticky_window->UserPort)) ) {
- class = imsg->Class;
- code = imsg->Code;
-
- switch(class)
- {
- case IDCMP_CLOSEWINDOW:
- END = TRUE;
- break;
- case IDCMP_REFRESHWINDOW:
- GT_BeginRefresh(sticky_window);
- GT_EndRefresh(sticky_window,TRUE);
- break;
- case IDCMP_GADGETUP:
- if( DoubleClick( old_secs, old_mics, imsg->Seconds,
- imsg->Micros) ) {
- SignalScreenSelect(code);
- }
- old_secs = imsg->Seconds;
- old_mics = imsg->Micros;
- break;
- }
-
- GT_ReplyIMsg(imsg);
- }
- }
- }
- }
-
- BOOL OpenInterface()
- {
- BOOL END = TRUE;
- struct Screen *pub_screen;
- struct NewGadget ng;
- struct Gadget *gad;
- struct DrawInfo *dri;
-
- if( pub_screen = LockPubScreen(pubscreen_name) ) {
- dri = GetScreenDrawInfo(pub_screen);
- if( dri ) {
- sticky_window = OpenWindowTags(NULL,
- WA_Left, TopX,
- WA_Top, TopY,
- WA_Width, Width,
- WA_Height, Height,
- WA_IDCMP, MY_IDCMP_FLAGS,
- WA_Title, "StickySelect",
- WA_ScreenTitle, "StickySelect 1.1 © (1993) by Markus Aalto",
- WA_PubScreen, pub_screen,
- WA_DragBar, TRUE,
- WA_DepthGadget, TRUE,
- WA_CloseGadget, TRUE,
- WA_SimpleRefresh, TRUE,
- WA_AutoAdjust, TRUE,
- WA_NewLookMenus, TRUE,
- TAG_END);
-
- if( sticky_window ) {
- vi = GetVisualInfo( pub_screen, TAG_END);
-
- if( vi ) {
- SetFont(sticky_window->RPort, dri->dri_Font);
- AskFont(sticky_window->RPort, &my_font);
-
- gad = CreateContext(&gadg_context);
-
- ng.ng_LeftEdge = INTERWIDTH + sticky_window->BorderLeft;
- ng.ng_TopEdge = INTERHEIGHT + sticky_window->BorderTop;
- ng.ng_Width = sticky_window->Width - (2*INTERWIDTH
- + sticky_window->BorderLeft + sticky_window->BorderRight);
- ng.ng_Height = sticky_window->Height - (2*INTERHEIGHT
- + sticky_window->BorderTop + sticky_window->BorderBottom);
- ng.ng_GadgetText = NULL;
- ng.ng_TextAttr = &my_font;
- ng.ng_Flags = NG_HIGHLABEL;
- ng.ng_GadgetID = 0;
- ng.ng_UserData = NULL;
- ng.ng_VisualInfo = vi;
-
- listview = gad = CreateGadget(LISTVIEW_KIND, gad, &ng,
- GTLV_Labels, &screenname_list,
- GTLV_ShowSelected, NULL,
- GTLV_Selected, 0,
- TAG_END);
-
- if( gad == NULL ) {
- FreeGadgets(gadg_context);
- }
- else {
- END = FALSE;
- AddGList(sticky_window, gadg_context, -1, -1, NULL);
- RefreshGList(gadg_context, sticky_window, NULL, -1);
- GT_RefreshWindow(sticky_window,NULL);
- }
- }
- }
-
- FreeScreenDrawInfo(pub_screen, dri);
- }
-
- UnlockPubScreen(NULL,pub_screen);
- }
-
- return(END);
- }
-
-
- /* Recreate the ScreenList for StickySelect. */
- BOOL UpdateList()
- {
- struct Node *screennode;
- struct Node *namenode;
- UpdateDataSemaphore *uds;
- BOOL fine = TRUE;
-
- while( screennode = RemHead(&screenname_list) ) {
- if( screennode->ln_Name ) FreeVec((void *)screennode->ln_Name);
- FreeVec((void *)screennode);
- }
-
- Forbid();
- if( uds = (UpdateDataSemaphore *)FindSemaphore(SEMAPHORE_NAME) ) {
- ObtainSemaphoreShared( (struct SignalSemaphore *)uds );
-
- Permit();
-
- for(namenode = uds->ud_NameList.lh_Head; (namenode->ln_Succ) && fine;
- namenode = namenode->ln_Succ) {
- screennode = (struct Node *)AllocVec(sizeof(struct Node),
- MEMF_ANY|MEMF_CLEAR);
- if( screennode ) {
- screennode->ln_Name = (UBYTE *)AllocVec(
- 1 + strlen(namenode->ln_Name), MEMF_ANY);
- if( screennode->ln_Name ) {
- strcpy( screennode->ln_Name, namenode->ln_Name );
- AddTail(&screenname_list,screennode);
- }
- else {
- fine = FALSE;
- FreeVec((void *)screennode);
- }
- }
- else fine = FALSE;
- }
-
- ReleaseSemaphore( (struct SignalSemaphore *)uds );
- }
- else Permit();
-
- return(fine);
- }
-
- /* Signal ScreenSelect that User have selected new item. */
- void SignalScreenSelect( ULONG code )
- {
- UpdateDataSemaphore *uds;
-
- Forbid();
- if( uds = (UpdateDataSemaphore *)FindSemaphore(SEMAPHORE_NAME) ) {
- ObtainSemaphore( (struct SignalSemaphore *)uds );
- Permit();
-
- /* Check if semaphore is active. This means that ScreenSelect
- ** is around and waiting. */
- if( uds->ud_ScreenSelectTask ) {
- /* Notify about new selection. */
- uds->ud_code = code;
- Signal(uds->ud_ScreenSelectTask, 1 << uds->ud_ScreenSelectSignal);
- }
-
- ReleaseSemaphore( (struct SignalSemaphore *)uds );
- }
- else Permit();
- }
-
-
- BOOL ReadParameters()
- {
- UBYTE *TTString;
- BOOL retval = TRUE;
-
- if( Cli() == NULL ) {
- extern struct WBStartup *_WBenchMsg;
- struct WBStartup *wb_msg;
- struct WBArg *wb_arg;
- BPTR old_dir;
- struct DiskObject *disk_obj;
- char **tools;
-
- wb_msg = _WBenchMsg;
- wb_arg = wb_msg->sm_ArgList;
-
- if(wb_arg->wa_Lock) {
- old_dir = CurrentDir(wb_arg->wa_Lock);
-
- disk_obj = GetDiskObjectNew(wb_arg->wa_Name);
- if( disk_obj ) {
- tools = (char **)disk_obj->do_ToolTypes;
-
- TTString = FindToolType(tools,"PUBSCREEN");
- if( TTString ) {
- pubscreen_name = AllocVec(1+ strlen(TTString),
- MEMF_ANY);
- if( pubscreen_name ) {
- strcpy(pubscreen_name,TTString);
- }
- else retval = FALSE;
- }
-
- TTString = FindToolType(tools,"LEFT");
- if( TTString ) {
- StrToLong(TTString,&TopX);
- }
-
- TTString = FindToolType(tools,"TOP");
- if( TTString ) {
- StrToLong(TTString,&TopY);
- }
-
- TTString = FindToolType(tools,"WIDTH");
- if( TTString ) {
- if( StrToLong(TTString,&Width) == -1 ) Width = 150;
- }
-
- TTString = FindToolType(tools,"HEIGHT");
- if( TTString ) {
- if( StrToLong(TTString,&Height) == -1 ) Height = 100;
- }
-
- FreeDiskObject(disk_obj);
- }
- (void)CurrentDir(old_dir);
- }
-
- }
- else {
- struct RDArgs *my_rda;
-
- my_rda = ReadArgs(TEMPLATE,(LONG *)ARGS,NULL);
- if( my_rda ) {
- if(ARGS[ARG_PUBSCREEN] != 0) {
- TTString = (char *)ARGS[ARG_PUBSCREEN];
- pubscreen_name = (char *)AllocVec(1+strlen(TTString),MEMF_ANY);
- if(pubscreen_name) {
- strcpy(pubscreen_name,TTString);
- }
- else retval = FALSE;
- }
-
- if(ARGS[ARG_LEFT] != 0) {
- TopX = *(ULONG *)ARGS[ARG_LEFT];
- }
-
- if(ARGS[ARG_TOP] != 0) {
- TopY = *(ULONG *)ARGS[ARG_TOP];
- }
-
- if(ARGS[ARG_WIDTH] != 0) {
- Width = *(ULONG *)ARGS[ARG_WIDTH];
- }
-
- if(ARGS[ARG_HEIGHT] != 0) {
- Height = *(ULONG *)ARGS[ARG_HEIGHT];
- }
-
- FreeArgs(my_rda);
- }
- }
-
- return(retval);
- }
-