home *** CD-ROM | disk | FTP | other *** search
/ AmigActive 24 / AACD 24.iso / AACD / System / ReqToolsLib / Source / reqtools / rtfuncs.c < prev    next >
Encoding:
C/C++ Source or Header  |  2001-07-02  |  17.3 KB  |  600 lines

  1. #include "filereq.h"
  2. #include "boopsi.h"
  3. #include "rtfuncs.h"
  4. #include "globalvars.h"
  5.  
  6. #include <devices/conunit.h>
  7.  
  8. #ifdef _AROS
  9.  
  10. #include <aros/debug.h>
  11. #include <aros/macros.h>
  12.  
  13. #else
  14.  
  15. #define D(x)
  16. #define AROS_ASMSYMNAME(x)  x
  17. #define AROS_LONG2BE(x)     x
  18. #define AROS_WORD2BE(x)     x
  19.  
  20. #endif
  21.  
  22. /****************************************************************************************/
  23.  
  24. struct rtWindowLock
  25. {
  26.     struct Requester     rtwl_Requester;
  27.     LONG                 rtwl_Magic;
  28.     struct rtWindowLock *rtwl_RequesterPtr;
  29.     ULONG                rtwl_LockCount;
  30.     ULONG                rtwl_ReqInstalled;
  31.  
  32.     /* To save window parameters */
  33.     APTR                 rtwl_Pointer;
  34.     BYTE                 rtwl_PtrHeight;
  35.     BYTE                 rtwl_PtrWidth;
  36.     BYTE                 rtwl_XOffset;
  37.     BYTE                 rtwl_YOffset;
  38.     WORD                 rtwl_MinWidth;
  39.     WORD                 rtwl_MaxWidth;
  40.     WORD                 rtwl_MinHeight;
  41.     WORD                 rtwl_MaxHeight;
  42. };
  43.  
  44. /****************************************************************************************/
  45.  
  46. SAVEDS ASM struct ReqToolsBase *RTFuncs_Init(REGPARAM(d0, struct ReqToolsBase *, RTBase),
  47.                                              REGPARAM(a0, BPTR, segList))                          
  48. {
  49. #ifdef _AROS
  50.     /* SysBase is setup in reqtools_init.c */
  51. #else
  52.     SysBase = *(struct ExecBase **)4L;
  53. #endif
  54.  
  55.     RTBase->SegList = segList;
  56.  
  57.     InitSemaphore(&RTBase->ReqToolsPrefs.PrefsSemaphore);
  58.     RTBase->ReqToolsPrefs.PrefsSize = RTPREFS_SIZE;
  59.  
  60.     /* Set default preferences */
  61.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_FILEREQ].Size = 75;
  62.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_FILEREQ].ReqPos = REQPOS_TOPLEFTSCR;
  63.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_FILEREQ].LeftOffset = 25;
  64.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_FILEREQ].TopOffset = 18;
  65.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_FILEREQ].MinEntries = 10;
  66.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_FILEREQ].MaxEntries = 50;
  67.  
  68.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_FONTREQ].Size = 65;
  69.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_FONTREQ].ReqPos = REQPOS_TOPLEFTSCR;
  70.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_FONTREQ].LeftOffset = 25;
  71.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_FONTREQ].TopOffset = 18;
  72.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_FONTREQ].MinEntries = 6;
  73.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_FONTREQ].MaxEntries = 10;
  74.  
  75.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_PALETTEREQ].Size = 65;
  76.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_PALETTEREQ].ReqPos = REQPOS_TOPLEFTSCR;
  77.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_PALETTEREQ].LeftOffset = 25;
  78.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_PALETTEREQ].TopOffset = 18;
  79.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_PALETTEREQ].MinEntries = 6;
  80.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_PALETTEREQ].MaxEntries = 10;
  81.  
  82.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_SCREENMODEREQ].Size = 65;
  83.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_SCREENMODEREQ].ReqPos = REQPOS_TOPLEFTSCR;
  84.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_SCREENMODEREQ].LeftOffset = 25;
  85.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_SCREENMODEREQ].TopOffset = 18;
  86.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_SCREENMODEREQ].MinEntries = 6;
  87.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_SCREENMODEREQ].MaxEntries = 10;
  88.  
  89.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_VOLUMEREQ].Size = 65;
  90.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_VOLUMEREQ].ReqPos = REQPOS_TOPLEFTSCR;
  91.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_VOLUMEREQ].LeftOffset = 25;
  92.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_VOLUMEREQ].TopOffset = 18;
  93.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_VOLUMEREQ].MinEntries = 6;
  94.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_VOLUMEREQ].MaxEntries = 10;
  95.  
  96.     //    RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_OTHERREQ].Size = 65;
  97.     //    RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_OTHERREQ].ReqPos = REQPOS_TOPLEFTSCR;
  98.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_OTHERREQ].LeftOffset = 25;
  99.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_OTHERREQ].TopOffset = 18;
  100.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_OTHERREQ].MinEntries = 6;
  101.     RTBase->ReqToolsPrefs.ReqDefaults[RTPREF_OTHERREQ].MaxEntries = 10;
  102.  
  103.     return RTBase;
  104. }
  105.  
  106. /****************************************************************************************/
  107.  
  108. SAVEDS ASM struct ReqToolsBase *RTFuncs_Open(REGPARAM(a6, struct ReqToolsBase *, RTBase),
  109.                                              REGPARAM(d0, ULONG, ver))
  110. {
  111.     if (DOSBase == NULL)
  112.     {
  113.         UBYTE configbuffer[RTPREFS_SIZE];
  114.     
  115.         DOSBase = RTBase->DOSBase = (struct DosLibrary *)OpenLibrary("dos.library", 37);
  116.         if (DOSBase == NULL)
  117.             return NULL;
  118.  
  119.         
  120.     /* Read config file */
  121.     
  122.         D(bug("reqtools.library: Inside libopen func. Reading config file\n"));
  123.     
  124.     memset(configbuffer, 0, sizeof(configbuffer));
  125.     
  126.     if (GetVar("ReqTools.prefs",
  127.            configbuffer,
  128.            sizeof(configbuffer),
  129.            GVF_BINARY_VAR | GVF_GLOBAL_ONLY | LV_VAR | GVF_DONT_NULL_TERM) == RTPREFS_SIZE)
  130.     {
  131.         UBYTE *configptr = configbuffer;
  132.         ULONG val;
  133.         WORD  i;
  134.  
  135.         D(bug("reqtools.library: Inside libopen func. Configfile loaded successfully\n"));
  136.         
  137. #define READ_ULONG     *((ULONG *)configptr)++
  138. #define READ_UWORD     *((UWORD *)configptr)++
  139. #define RTPREFS     (RTBase->ReqToolsPrefs)
  140.  
  141.         val = READ_ULONG;
  142.         RTPREFS.Flags = AROS_LONG2BE(val);
  143.  
  144.         for(i = 0;i < RTPREF_NR_OF_REQ; i++)
  145.         {
  146.         val = READ_ULONG;
  147.         RTPREFS.ReqDefaults[i].Size = AROS_LONG2BE(val);
  148.  
  149.         val = READ_ULONG;
  150.         RTPREFS.ReqDefaults[i].ReqPos = AROS_LONG2BE(val);
  151.  
  152.         val = READ_UWORD;
  153.         RTPREFS.ReqDefaults[i].LeftOffset = AROS_WORD2BE(val);
  154.  
  155.         val = READ_UWORD;
  156.         RTPREFS.ReqDefaults[i].TopOffset = AROS_WORD2BE(val);
  157.  
  158.         val = READ_UWORD;
  159.         RTPREFS.ReqDefaults[i].MinEntries = AROS_WORD2BE(val);
  160.  
  161.         val = READ_UWORD;
  162.         RTPREFS.ReqDefaults[i].MaxEntries = AROS_WORD2BE(val);        
  163.         }
  164.             
  165.     }
  166.     
  167.     } /* if (DOSBase == NULL) */
  168.     
  169.     if(IntuitionBase == NULL)
  170.     IntuitionBase = RTBase->IntuitionBase = (struct IntuitionBase *)OpenLibrary("intuition.library", 37);
  171.     if(IntuitionBase == NULL)
  172.     return NULL;
  173.  
  174.     if(GfxBase == NULL)
  175.     GfxBase = RTBase->GfxBase = (struct GfxBase *)OpenLibrary("graphics.library", 37);
  176.     if(GfxBase == NULL)
  177.     return NULL;
  178.     
  179.     if(UtilityBase == NULL)
  180.     UtilityBase = RTBase->UtilityBase = (struct UtilityBase *)OpenLibrary("utility.library", 37);
  181.     if(UtilityBase == NULL)
  182.     return NULL;
  183.  
  184.     if(GadToolsBase == NULL)
  185.     GadToolsBase = RTBase->GadToolsBase = OpenLibrary("gadtools.library", 37);
  186.     if(GadToolsBase == NULL)
  187.     return NULL;
  188.  
  189.     if(LayersBase == NULL)
  190.     LayersBase = OpenLibrary("layers.library", 37);
  191.     if(LayersBase == NULL)
  192.     return NULL;
  193.  
  194.     if(LocaleBase == NULL)
  195.     LocaleBase = (struct LocaleBase *)OpenLibrary("locale.library", 37);
  196.     if(LocaleBase == NULL)
  197.     return NULL;
  198.  
  199.     D(bug("reqtools.library: Inside libopen func. Libraries opened successfully.\n"));
  200.  
  201.     if (ConsoleDevice == NULL)
  202.     {
  203.         iorequest.io_Message.mn_Length = sizeof(iorequest);
  204.     
  205.         if (OpenDevice("console.device", CONU_LIBRARY, (struct IORequest *)&iorequest, 0))
  206.     {
  207.         return NULL;
  208.     }
  209.     ConsoleDevice = iorequest.io_Device;
  210.     }
  211.     if (ConsoleDevice == NULL)
  212.         return NULL;
  213.  
  214.     D(bug("reqtools.library: Inside libopen func. Console.device opened successfully.\n"));
  215.     
  216.     if (ButtonImgClass == NULL)
  217.     {
  218.         ButtonImgClass = MakeClass(NULL, IMAGECLASS, NULL, sizeof(struct LocalObjData), 0);
  219.     if (ButtonImgClass)
  220.     {
  221.         ButtonImgClass->cl_Dispatcher.h_Entry = (APTR)AROS_ASMSYMNAME(myBoopsiDispatch);
  222.         ButtonImgClass->cl_Dispatcher.h_SubEntry = NULL;
  223.         ButtonImgClass->cl_UserData = (IPTR)RTBase;
  224.     }
  225.     }
  226.     if (ButtonImgClass == NULL)
  227.         return NULL;
  228.     
  229.     D(bug("reqtools.library: Inside libopen func. ButtonImgClass create successfully.\n"));
  230.  
  231.     /* I have one more opener. */
  232.     RTBase->LibNode.lib_Flags &= ~LIBF_DELEXP;
  233.     RTBase->RealOpenCnt++;
  234.  
  235.     D(bug("reqtools.library: Inside libopen func. Returning success.\n"));
  236.     
  237.     return RTBase;
  238. }
  239.  
  240. /****************************************************************************************/
  241.  
  242. SAVEDS ASM BPTR RTFuncs_Close(REGPARAM(a6, struct ReqToolsBase *, RTBase))
  243. {
  244.     /* I have one fewer opener. */
  245.     RTBase->RealOpenCnt--;
  246.     
  247.     if((RTBase->LibNode.lib_Flags & LIBF_DELEXP) != 0)
  248.     {
  249.         /* CHECKME: used expunge() from reqtools_intern.h. */
  250.     
  251.     if(RTBase->LibNode.lib_OpenCnt == 0)
  252.         return RTFuncs_Expunge(RTBase);
  253.     
  254.     RTBase->LibNode.lib_Flags &= ~LIBF_DELEXP;
  255.     }
  256.  
  257.     return NULL;
  258. }
  259.  
  260. /****************************************************************************************/
  261.  
  262. SAVEDS ASM BPTR RTFuncs_Expunge(REGPARAM(a6, struct ReqToolsBase *, RTBase))
  263. {
  264.     BPTR ret;
  265.     
  266.     if(RTBase->RealOpenCnt != 0)
  267.     {
  268.     /* Set the delayed expunge flag and return. */
  269.     RTBase->LibNode.lib_Flags |= LIBF_DELEXP;
  270.     return NULL;
  271.     }
  272.  
  273.     /* Get rid of the library. Remove it from the list. */
  274.     Remove(&RTBase->LibNode.lib_Node);
  275.  
  276.     /* Get returncode here - FreeMem() will destroy the field. */
  277.     ret = RTBase->SegList;
  278.  
  279.     D(bug("reqtools.library: Inside libexpunge func. Freeing ButtonImgClass.\n"));
  280.  
  281.     if (ButtonImgClass) FreeClass(ButtonImgClass);
  282.  
  283.     D(bug("reqtools.library: Inside libexpunge func. Closing console.device.\n"));
  284.     
  285.     if (ConsoleDevice) CloseDevice((struct IORequest *)&iorequest);
  286.  
  287.     D(bug("reqtools.library: Inside libexpunge func. Closing libraries.\n"));
  288.     
  289.     CloseLibrary((struct Library *)DOSBase);
  290.     CloseLibrary((struct Library *)IntuitionBase);
  291.     CloseLibrary((struct Library *)UtilityBase);
  292.     CloseLibrary((struct Library *)GfxBase);
  293.     CloseLibrary((struct Library *)LocaleBase);
  294.     CloseLibrary(GadToolsBase);
  295.     CloseLibrary(LayersBase);
  296.  
  297.     D(bug("reqtools.library: Inside libexpunge func. Freeing libbase.\n"));
  298.  
  299.     /* Free the memory. */
  300.     FreeMem((char *)RTBase-RTBase->LibNode.lib_NegSize,
  301.         RTBase->LibNode.lib_NegSize + RTBase->LibNode.lib_PosSize);
  302.  
  303.     return ret;
  304. }
  305.  
  306. /****************************************************************************************/
  307.  
  308. SAVEDS ASM int RTFuncs_Null(REGPARAM(a6, struct ReqToolsBase *, RTBase))
  309. {
  310.     return 0;
  311. }
  312.  
  313.  
  314. /****************************************************************************************/
  315.  
  316. SAVEDS ASM struct ReqToolsPrefs *RTFuncs_LockPrefs(REGPARAM(a6, struct ReqToolsBase *, ReqToolsBase))
  317. {
  318.     ObtainSemaphore(&ReqToolsBase->ReqToolsPrefs.PrefsSemaphore);
  319.  
  320.     return &ReqToolsBase->ReqToolsPrefs;
  321. }
  322.  
  323. /****************************************************************************************/
  324.  
  325. SAVEDS ASM void RTFuncs_UnlockPrefs(REGPARAM(a6, struct ReqToolsBase *, ReqToolsBase))
  326. {
  327.     ReleaseSemaphore(&ReqToolsBase->ReqToolsPrefs.PrefsSemaphore);
  328. }
  329.  
  330. /****************************************************************************************/
  331.  
  332. SAVEDS ASM ULONG RTFuncs_rtReqHandlerA(REGPARAM(a1, struct rtHandlerInfo *, handlerinfo),
  333.                                        REGPARAM(d0, ULONG, sigs),
  334.                        REGPARAM(a0, struct TagItem *, taglist))
  335. {
  336.     return  ((ULONG (*)(REGPARAM(a1, struct rtHandlerInfo *,),
  337.                         REGPARAM(d0, ULONG,),
  338.             REGPARAM(a0, struct TagItem *,)))handlerinfo->private1)(handlerinfo, sigs, taglist);
  339. }
  340.  
  341. /****************************************************************************************/
  342.  
  343. SAVEDS ASM void RTFuncs_rtSetWaitPointer(REGPARAM(a0, struct Window *, window))
  344. {
  345.     struct TagItem tags[] = { { WA_BusyPointer, TRUE },
  346.                   { TAG_DONE, NULL } };
  347.  
  348.     SetWindowPointerA(window, (struct TagItem *)&tags);
  349. }
  350.  
  351. /****************************************************************************************/
  352.  
  353. SAVEDS ASM APTR RTFuncs_rtLockWindow(REGPARAM(a0, struct Window *, window))
  354. {
  355.     struct rtWindowLock *winLock;
  356.  
  357.     /* Is this window already locked? */
  358.     if(window->FirstRequest != NULL)
  359.     {
  360.     struct rtWindowLock *wLock = (struct rtWindowLock *)window->FirstRequest;
  361.  
  362.     while(wLock != NULL)
  363.     {
  364.         if(wLock->rtwl_Magic ==  ('r' << 24 | 't' << 16 | 'L' << 8 | 'W'))
  365.         {
  366.         if(wLock->rtwl_RequesterPtr == wLock)
  367.         {
  368.             /* Window was already locked */
  369.             wLock->rtwl_LockCount++;
  370.  
  371.             return wLock;
  372.         }
  373.         }
  374.  
  375.         wLock = (struct rtWindowLock *)wLock->rtwl_Requester.OlderRequest;
  376.     }
  377.     }
  378.     winLock = (struct rtWindowLock *)AllocVec(sizeof(struct rtWindowLock),
  379.                           MEMF_CLEAR);
  380.     
  381.     /* No memory? */
  382.     if(winLock == NULL)
  383.     return NULL;
  384.  
  385.     winLock->rtwl_Magic = 'r' << 24 | 't' << 16 | 'L' << 8 | 'W';
  386.     winLock->rtwl_RequesterPtr = winLock;
  387.     
  388.     winLock->rtwl_MinHeight = window->MinHeight;
  389.     winLock->rtwl_MaxHeight = window->MaxHeight;
  390.     winLock->rtwl_MinWidth  = window->MinWidth;
  391.     winLock->rtwl_MaxWidth  = window->MaxWidth;
  392.  
  393.     WindowLimits(window, window->Width, window->Height,
  394.          window->Width, window->Height);
  395.     
  396.     InitRequester((struct Requester *)winLock);
  397.     winLock->rtwl_ReqInstalled = Request((struct Requester *)winLock, window);
  398.     
  399.     winLock->rtwl_Pointer = window->Pointer;
  400.     winLock->rtwl_PtrHeight = window->PtrHeight;
  401.     winLock->rtwl_PtrWidth = window->PtrWidth;
  402.     
  403.     rtSetWaitPointer(window);
  404.     
  405.     return (APTR)winLock;
  406. }
  407.  
  408. /****************************************************************************************/
  409.  
  410. SAVEDS ASM VOID RTFuncs_rtUnlockWindow(REGPARAM(a0, struct Window *, window),
  411.                                        REGPARAM(a1, APTR, windowlock))
  412. {
  413.     
  414.     struct rtWindowLock *wLock = (struct rtWindowLock *)windowlock;
  415.  
  416.     if(wLock == NULL)
  417.     return;
  418.  
  419.     if(wLock->rtwl_LockCount != 0)
  420.     {
  421.     wLock->rtwl_LockCount--;
  422.     }
  423.     else
  424.     {
  425.     struct TagItem tags[] = { { WA_Pointer, (IPTR)wLock->rtwl_Pointer },
  426.                   { TAG_DONE  , NULL } };
  427.  
  428.     SetWindowPointerA(window, tags);
  429.  
  430.         if (wLock->rtwl_ReqInstalled)
  431.         EndRequest((struct Requester *)wLock, window);
  432.     
  433.     WindowLimits(window, wLock->rtwl_MinWidth, wLock->rtwl_MinHeight,
  434.              wLock->rtwl_MaxWidth, wLock->rtwl_MaxHeight);
  435.  
  436.     FreeVec(wLock);
  437.     }
  438. }
  439.  
  440. /****************************************************************************************/
  441.  
  442. SAVEDS ASM void RTFuncs_rtSpread(REGPARAM(a0, ULONG *, posarray),
  443.                              REGPARAM(a1, ULONG *, sizearray),
  444.                  REGPARAM(d0, ULONG, totalsize),
  445.                  REGPARAM(d1, ULONG, min),
  446.                  REGPARAM(d2, ULONG, max),
  447.                  REGPARAM(d3, ULONG, num))
  448. {
  449.     ULONG gadpos = min << 16;
  450.     ULONG gadgap;
  451.     UWORD i;
  452.  
  453.     gadgap = ((max - min - totalsize) << 16) / (num - 1); 
  454.  
  455.     posarray[0] = min;
  456.  
  457.     for(i = 1; i < num - 1; i++)
  458.     {
  459.     gadpos += (sizearray[i - 1] << 16) + gadgap;
  460.     posarray[i] = gadpos >> 16;
  461.     }
  462.  
  463.     posarray[num - 1] = max - sizearray[i];
  464.  
  465. }
  466.  
  467. /****************************************************************************************/
  468.  
  469. SAVEDS ASM void RTFuncs_ScreenToFrontSafely(REGPARAM(a0, struct Screen *, screen))
  470. {
  471.     struct Screen *scr = IntuitionBase->FirstScreen;
  472.  
  473.     Forbid();
  474.  
  475.     while(scr != NULL)
  476.     {
  477.     if(scr == screen)
  478.     {
  479.         ScreenToFront(screen);
  480.         break;
  481.     }
  482.     
  483.     scr = scr->NextScreen;
  484.     }
  485.  
  486.     Permit();
  487. }
  488.  
  489. /****************************************************************************************/
  490.  
  491. SAVEDS ASM void RTFuncs_rtSetReqPosition(REGPARAM(d0, ULONG, reqpos),
  492.                                         REGPARAM(a0, struct NewWindow *, nw),
  493.                     REGPARAM(a1, struct Screen *, scr),
  494.                     REGPARAM(a2, struct Window *, win))
  495. {
  496. #warning Taken from rtfuncs.asm where the C version was in comments. Might be out of date
  497.  
  498.     int mx, my, val, leftedge, topedge;
  499.     ULONG scrwidth, scrheight;
  500.     int width, height, left, top;
  501.  
  502.     rtGetVScreenSize (scr, &scrwidth, &scrheight);
  503.  
  504.     leftedge = -scr->LeftEdge;    
  505.     if (leftedge < 0) leftedge = 0;
  506.     
  507.     topedge = -scr->TopEdge;
  508.     if (topedge < 0) topedge = 0;
  509.  
  510.     left = leftedge; top = topedge;
  511.     width = scrwidth; height = scrheight;
  512.     
  513.     switch (reqpos)
  514.     {
  515.     case REQPOS_DEFAULT:
  516.         nw->LeftEdge = 25;
  517.         nw->TopEdge = 18;
  518.         goto topleftscr;
  519.         
  520.     case REQPOS_POINTER:
  521.         mx = scr->MouseX; my = scr->MouseY;
  522.         break;
  523.         
  524.     case REQPOS_CENTERWIN:
  525.         if (win)
  526.         {
  527.         left = win->LeftEdge; top = win->TopEdge;
  528.         width = win->Width; height = win->Height;
  529.         }
  530.         
  531.     case REQPOS_CENTERSCR:
  532.         mx = (width - nw->Width) / 2 + left;
  533.         my = (height - nw->Height) / 2 + top;
  534.         break;
  535.         
  536.     case REQPOS_TOPLEFTWIN:
  537.         if (win)
  538.         {
  539.         left = win->LeftEdge;
  540.         top = win->TopEdge;
  541.         }
  542.         
  543.     case REQPOS_TOPLEFTSCR:
  544. topleftscr:
  545.         mx = left; my = top;
  546.         break;
  547.         
  548.     } /* switch (reqpos) */
  549.  
  550.     /* keep window completely visible */
  551.     mx += nw->LeftEdge; my += nw->TopEdge;
  552.     val = leftedge + scrwidth - nw->Width;
  553.     
  554.     if (mx < leftedge) mx = leftedge;
  555.     else if (mx > val) mx = val;
  556.     
  557.     val = topedge + scrheight - nw->Height;
  558.     
  559.     if (my < topedge) my = topedge;
  560.     else if (my > val) my = val;
  561.  
  562.     nw->LeftEdge = mx; nw->TopEdge = my;
  563. }
  564.  
  565.  
  566. /****************************************************************************************/
  567.  
  568. /* This one is from closewindowsafely.asm */
  569.  
  570. SAVEDS ASM void RTFuncs_CloseWindowSafely(REGPARAM(a0, struct Window *, window))
  571. {
  572.     struct IntuiMessage *msg;
  573.  
  574.     Forbid();
  575.  
  576.     if(window->UserPort != NULL)
  577.     {
  578.     while((msg = (struct IntuiMessage *)GetMsg(window->UserPort)) != NULL)
  579.     {
  580.         if(msg->IDCMPWindow == window)
  581.         {
  582.         Remove((struct Node *)msg);
  583.         ReplyMsg((struct Message *)msg);
  584.         }
  585.     }
  586.     }
  587.  
  588.     window->UserPort = NULL;
  589.  
  590.     ModifyIDCMP(window, 0);
  591.  
  592.     Permit();
  593.  
  594.     CloseWindow(window);
  595. }
  596.  
  597. /****************************************************************************************/
  598. /****************************************************************************************/
  599.  
  600.