home *** CD-ROM | disk | FTP | other *** search
/ Club Amiga de Montreal - CAM / CAM_CD_1.iso / files / 073.lha / FileIO / filesupp.c < prev    next >
Encoding:
C/C++ Source or Header  |  1987-06-02  |  18.9 KB  |  683 lines

  1.  
  2. /* *** filesupp.c ***********************************************************
  3.  *
  4.  * File IO Suite  --  Open Requester Routines
  5.  *     from Book 1 of the Amiga Programmers' Suite by RJ Mical
  6.  *
  7.  * Copyright (C) 1986, 1987, Robert J. Mical
  8.  * All Rights Reserved.
  9.  *
  10.  * Created for Amiga developers.
  11.  * Any or all of this code can be used in any program as long as this
  12.  * entire copyright notice is retained, ok?  Thanks.
  13.  *
  14.  * HISTORY      NAME            DESCRIPTION
  15.  * -----------  --------------  --------------------------------------------
  16.  * 4 Feb 87     RJ              Real release
  17.  * 12 Aug 86    RJ >:-{)*       Prepare (clean house) for release
  18.  * 3 May 86     =RJ Mical=      Fix prop gadget for both 1.1 and 1.2
  19.  * 1 Feb 86     =RJ Mical=      Created this file.
  20.  *
  21.  * *********************************************************************** */
  22.  
  23.  
  24. #define FILEIO_SOURCEFILE
  25. #include "fileio.h"
  26.  
  27.  
  28. /* I think these are silly, but I put them here anyway to avoid compiler
  29.  * warnings.
  30.  */
  31. VOID InitOpenProp();
  32. VOID StuffSelectNames();
  33.  
  34.  
  35.  
  36. /* ======================================================================= */
  37. /* === ResetText Routines ================================================ */
  38. /* ======================================================================= */
  39.  
  40. VOID ResetTextGrunt(info, resetbuffer)
  41. struct StringInfo *info;
  42. BOOL resetbuffer;
  43. /* Reset the string position variables, and reset the buffer itself if
  44.  * resetbuffer is TRUE.
  45.  */
  46. {
  47.    info->BufferPos = info->DispPos = 0;
  48.    if (resetbuffer) info->Buffer[0] = '\0';
  49. }
  50.  
  51. VOID ResetNameText(resetbuffer)
  52. BOOL resetbuffer;
  53. {
  54.    ResetTextGrunt(&OpenNameTextInfo, resetbuffer);
  55. }
  56.  
  57. VOID ResetDrawerText(resetbuffer)
  58. BOOL resetbuffer;
  59. {
  60.    ResetTextGrunt(&OpenDrawerTextInfo, resetbuffer);
  61. }
  62.  
  63. VOID ResetDiskText(resetbuffer)
  64. BOOL resetbuffer;
  65. {
  66.    ResetTextGrunt(&OpenDiskTextInfo, resetbuffer);
  67. }
  68.  
  69.  
  70.  
  71. /* ======================================================================= */
  72. /* === WarmStart Initializer ============================================= */
  73. /* ======================================================================= */
  74.  
  75. VOID WarmStartFileIO(fileio)
  76. struct FileIOSupport *fileio;
  77. /* This routine establishes a lock on the current disk and drawer,
  78.  * resets all of the subsystem control variables,
  79.  * gets the file names for the current disk and drawer,
  80.  * initializes the proportional gadget,
  81.  * and then refreshes the requester.
  82.  */
  83. {
  84.    ULONG lock;
  85.  
  86.    /* If the fileio already had a lock, release it before proceeding */
  87.    if (FlagIsSet(fileio->Flags, LOCK_GOTTEN))
  88.       {
  89.       UnLock(fileio->DOSLock);
  90.       ClearFlag(fileio->Flags, LOCK_GOTTEN);
  91.       fileio->DOSLock = OpenSaveLock;
  92.       CurrentDir(OpenSaveLock);
  93.       }
  94.  
  95.    /* Build the lock name using the current disk and drawer names */
  96.    if (StringLength(&fileio->DiskName[0]))
  97.       CopyString(&OpenLockName[0], &fileio->DiskName[0]);
  98.    else
  99.       CopyString(&OpenLockName[0], CurrentVolumeName());
  100.    ConcatString(&OpenLockName[0], &fileio->DrawerName[0]);
  101.  
  102.    /* Can we get a lock on this name? */
  103.    if (lock = Lock(&OpenLockName[0], ACCESS_READ))
  104.       {
  105.       /* Got it! */
  106.       SetFlag(fileio->Flags, LOCK_GOTTEN);
  107.       fileio->DOSLock = lock;
  108.       CurrentDir(lock);
  109.       }
  110.    else
  111.       {
  112.       /* Hey, bad break, this name just won't do.  But the rest of these
  113.        * routines need a valid directory, so go back home.
  114.        */
  115.       Alert(ALERT_BAD_DIRECTORY, OpenReqWindow);
  116.       CopyString(&fileio->DiskName[0], &CurrentDiskString[0]);
  117.       ResetDiskText(FALSE);
  118.       ResetDrawerText(TRUE);
  119.       }
  120.  
  121.    /* Reset the fileio name selection variables */
  122.    fileio->CurrentPick = -1;
  123.    fileio->NameStart = 0;
  124.    fileio->NameCount = 0;
  125.  
  126.    /* Reset the text and gadgets */
  127.    InitOpenProp(TRUE);           /* Initialize the prop gadget */
  128.    BuildNameTable(OpenReqFileIO);   /* Get the file names */
  129.    StuffSelectNames(-1);         /* Display the file names */
  130. }
  131.  
  132.  
  133.  
  134. /* ======================================================================= */
  135. /* === Select Name Routines ============================================== */
  136. /* ======================================================================= */
  137.  
  138. VOID BlankSelectText(index)
  139. SHORT index;
  140. /* This routine truns the SelectText at index into blanks */
  141. {
  142.    UBYTE *ptr;
  143.    SHORT blanklength;
  144.  
  145.    ptr = &OpenSelectBuffers[index][0];
  146.    for (blanklength = VISIBLE_SELECT_LENGTH - 1; blanklength; blanklength--)
  147.       *ptr++ = ' ';
  148.    *ptr = '\0';
  149.  
  150.    OpenSelectText[index].FrontPen = 1;
  151.    OpenSelectText[index].BackPen = 0;
  152. }
  153.  
  154.  
  155.  
  156. VOID DrawSelectNames()
  157. {
  158.    struct Layer *layer;
  159.  
  160.    Forbid();
  161.    if (layer = OpenReq->ReqLayer)
  162.       if (layer->rp)
  163.          PrintIText(layer->rp,
  164.                &OpenSelectText[NAME_ENTRY_COUNT - 1], 
  165.                OPENSELECT_LEFT, OPENSELECT_TOP);
  166.    Permit();
  167. }
  168.  
  169.  
  170.  
  171. VOID StuffSelectNames(refreshcount)
  172. SHORT refreshcount;
  173. /* This routine stuffs the Open Requester's filename gadgets with
  174.  * names from the fileio structure, starting from the 
  175.  * fileio->NameStart name.  If the refreshcount is nonzero, the gadgets
  176.  * will be refreshed too.
  177.  */
  178. {
  179.    SHORT i, end, bufferpos;
  180.    SHORT length, blanklength;
  181.    UBYTE *ptr, *ptr2;
  182.    struct Remember *remember;
  183.    struct Layer *layer;
  184.  
  185.    if (OpenReqFileIO->NameCount 
  186.          > OpenReqFileIO->NameStart + NAME_ENTRY_COUNT) 
  187.       end = OpenReqFileIO->NameStart + NAME_ENTRY_COUNT;
  188.    else end = OpenReqFileIO->NameCount;
  189.  
  190.    bufferpos = 0;
  191.  
  192.    /* The current file names are stored in the fileio's Remember list */
  193.    remember = OpenReqFileIO->NameKey;
  194.    for (i = 0; i < OpenReqFileIO->NameStart; i++) 
  195.       remember = remember->NextRemember;
  196.  
  197.    for (i = OpenReqFileIO->NameStart; i < end; i++) 
  198.       {
  199.       ptr = &OpenSelectBuffers[bufferpos][0];
  200.       ptr2 = remember->Memory;
  201.  
  202.       length = StringLength(ptr2);
  203.       if (length >= VISIBLE_SELECT_LENGTH)
  204.          length = VISIBLE_SELECT_LENGTH - 1;
  205.       blanklength = (VISIBLE_SELECT_LENGTH - 1) - length;
  206.  
  207.       /* By filling up the IntuiText with blanks after the characters,
  208.        * the text, when printed, will overstrike any characters that were 
  209.        * there before.
  210.        */
  211.       for ( ; length; length--) *ptr++ = *ptr2++;
  212.       for ( ; blanklength; blanklength--) *ptr++ = ' ';
  213.       *ptr = '\0';
  214.  
  215.       /* If this is the selected text, then use "highlight" pens */
  216.       if (i == OpenReqFileIO->CurrentPick)
  217.          {
  218.          OpenSelectText[bufferpos].FrontPen = -2;
  219.          OpenSelectText[bufferpos].BackPen = -1;
  220.          }
  221.       else
  222.          {
  223.          OpenSelectText[bufferpos].FrontPen = 1;
  224.          OpenSelectText[bufferpos].BackPen = 0;
  225.          }
  226.  
  227.       bufferpos++;
  228.       remember = remember->NextRemember;
  229.       }
  230.  
  231.    /* Now, for all lines that have no entries, fill with blanks */
  232.    for ( ; bufferpos < NAME_ENTRY_COUNT; bufferpos++)
  233.       BlankSelectText(bufferpos);
  234.  
  235.    /* Finally, redraw the lot */
  236.    if (refreshcount)
  237.       {
  238.       Forbid();
  239.       if (layer = OpenReq->ReqLayer)
  240.          if (layer->rp)
  241.             RefreshGList(&OpenSelectNameGadget, OpenReqWindow, OpenReq,
  242.                   refreshcount);
  243.       DrawSelectNames();
  244.       Permit();
  245.       }
  246. }
  247.  
  248.  
  249.  
  250. VOID SetNameStart()
  251. /* This little guy sets the NameStart based on the current
  252.  * prop gadget setting.
  253.  */
  254. {
  255.    if (OpenReqFileIO->NameCount <= NAME_ENTRY_COUNT)
  256.       OpenReqFileIO->NameStart = 0;
  257.    else
  258.       OpenReqFileIO->NameStart = (OpenPropInfo.VertPot 
  259.             * (OpenReqFileIO->NameCount - NAME_ENTRY_COUNT + 1)) >> 16;
  260. }
  261.  
  262.  
  263.  
  264. VOID StripLastDrawer()
  265. /* This guy strips the end drawer reference off of the drawer string,
  266.  * which includes nulling out the string if there's only one to strip.
  267.  */
  268. {
  269.    UBYTE *ptr;
  270.    SHORT index;
  271.  
  272.    ptr = OpenDrawerTextInfo.Buffer;
  273.    index = IndexString(ptr, "/");
  274.    if (index != -1)
  275.       {
  276.       /* OK, there's more than one drawer reference, so get the ptr + index
  277.        * to the last one.
  278.        */
  279.       do 
  280.          ptr += (index + 1);
  281.       while ((index = IndexString(ptr, "/")) != -1);
  282.       }
  283.    else index = 0;
  284.    /* Zammo! */
  285.    *(ptr + index) = '\0';
  286. }
  287.  
  288.  
  289.  
  290. BOOL DirectoryName()
  291. /* Returns TRUE if the selected name was a directory-type reference
  292.  * (up or down), else returns FALSE for a normal filename.
  293.  */
  294. {
  295.    struct Remember *entry;
  296.    SHORT i;
  297.    UBYTE entryflags;
  298.  
  299.    if (OpenReqFileIO->NameCount)
  300.       {
  301.       /* Find the selected entry in the key list */
  302.       entry = OpenReqFileIO->NameKey;
  303.       for (i = OpenReqFileIO->CurrentPick; i > 0; i--)
  304.          entry = entry->NextRemember;
  305.       i = StringLength(entry->Memory) + 1;
  306.       entryflags = *(entry->Memory + i);
  307.  
  308.       if (FlagIsSet(entryflags, NAMED_DIRECTORY | NAMED_PREVIOUS))
  309.          return(TRUE);
  310.  
  311.       /* else just a normal file name was selected, so fall out to ... */
  312.       }
  313.    return(FALSE);
  314. }
  315.  
  316.  
  317.  
  318. VOID StuffFileName()
  319. /* If the selected name is a normal filename, stuffs the filename into the
  320.  * Name gadget.  If the selected name is a directory reference,
  321.  * adjusts the drawer gadget accordingly.
  322.  * Returns TRUE if the selected name was a directory-type reference
  323.  * (up or down), else returns FALSE for a normal filename.
  324.  */
  325. {
  326.    struct Remember *entry;
  327.    SHORT i;
  328.    UBYTE entryflags;
  329.  
  330.    if (OpenReqFileIO->NameCount)
  331.       {
  332.       /* Find the selected entry in the key list */
  333.       entry = OpenReqFileIO->NameKey;
  334.       for (i = OpenReqFileIO->CurrentPick; i; i--)
  335.          entry = entry->NextRemember;
  336.       i = StringLength(entry->Memory) + 1;
  337.       entryflags = *(entry->Memory + i);
  338.  
  339.       if (FlagIsSet(entryflags, NAMED_DIRECTORY))
  340.          {
  341.          /* If there's already a drawer reference, build a proper
  342.           * extension before adding the new to the end.
  343.           */
  344.          if (StringLength(OpenDrawerTextInfo.Buffer))
  345.             ConcatString(OpenDrawerTextInfo.Buffer, "/");
  346.  
  347.          ConcatString(OpenDrawerTextInfo.Buffer,
  348.                entry->Memory + DIR_TEXT_SIZE);
  349.  
  350.          ResetDrawerText(FALSE);
  351.          ResetNameText(TRUE);
  352.          }
  353.       else if (FlagIsSet(entryflags, NAMED_PREVIOUS))
  354.          {
  355.          /* Remove the last drawer reference */
  356.          StripLastDrawer();
  357.          ResetDrawerText(FALSE);
  358.          ResetNameText(TRUE);
  359.          }
  360.       else
  361.          {
  362.          /* Just a normal old file name was selected */
  363.          CopyString(OpenNameTextInfo.Buffer, entry->Memory);
  364.          ResetNameText(FALSE);
  365.          }
  366.       }
  367. }
  368.  
  369.  
  370.  
  371. /* ======================================================================= */
  372. /* === Proportional Gadget Routines ====================================== */
  373. /* ======================================================================= */
  374.  
  375. VOID SetOpenPropPot(resetpos)
  376. BOOL resetpos;
  377. /* This routine resets the vertical pot of the proportional gadget
  378.  * with respect to the current number of displayable file names.
  379.  */
  380. {
  381.    LONG slack, result;
  382.  
  383.    slack = OpenReqFileIO->NameCount - NAME_ENTRY_COUNT;
  384.  
  385.    if (slack > 0)
  386.       {
  387.       result = ((LONG)OpenReqFileIO->NameStart << 16) / slack;
  388.       if (result > 0xFFFF) result = 0xFFFF;
  389.       OpenPropInfo.VertPot = result;
  390.       }
  391.    else
  392.       OpenPropInfo.VertPot = 0;
  393.  
  394.    if (resetpos) OpenPropImage.TopEdge = 0;
  395. }
  396.  
  397.  
  398.  
  399. VOID InitOpenProp(resetpos)
  400. BOOL resetpos;
  401. /* This routine initializes the variable imagery of the proportional
  402.  * gadget and then initializes the gadget's vertical pot.
  403.  * The BOOL arg resetpos describes whether you want the call to 
  404.  * SetOpenPropPot() to reset the prop's knob position.
  405.  */
  406. {
  407.    LONG namecount, height;
  408.    SHORT i, i2;
  409.  
  410.    namecount = OpenReqFileIO->NameCount;
  411.  
  412.    if (namecount <= NAME_ENTRY_COUNT)
  413.       {
  414.       OpenPropInfo.VertBody = 0xFFFF;
  415.       ClearFlag(OpenPropInfo.Flags, FREEVERT);
  416.       height = OPENPROP_MAXHEIGHT;
  417.       }
  418.    else
  419.       {
  420.       OpenPropInfo.VertBody = ((LONG)NAME_ENTRY_COUNT << 16) / namecount;
  421.       SetFlag(OpenPropInfo.Flags, FREEVERT);
  422.       height = (OPENPROP_MAXHEIGHT * NAME_ENTRY_COUNT)  / namecount;
  423.       if (height < OPENPROP_MINHEIGHT) height = OPENPROP_MINHEIGHT;
  424.       }
  425.  
  426.    OpenPropImage.Height = height;
  427.    for (i = 0; i < OPENPROP_TOPHEIGHT; i++)
  428.       {
  429.       OpenPropData[i] = OpenPropTop[i];
  430.       OpenPropData[i + height] = OpenPropTop[i + OPENPROP_TOPHEIGHT];
  431.       }
  432.  
  433.    for (i = OPENPROP_TOPHEIGHT; i < height - OPENPROP_BOTTOMHEIGHT; i++)
  434.       {
  435.       OpenPropData[i] = OpenPropBottom[0];
  436.       OpenPropData[i + height] = OpenPropBottom[OPENPROP_BOTTOMHEIGHT];
  437.       }
  438.  
  439.    i2 = 0;
  440.    for (i = height - OPENPROP_BOTTOMHEIGHT; i < height; i++)
  441.       {
  442.       OpenPropData[i] = OpenPropBottom[i2];
  443.       OpenPropData[i + height] = OpenPropBottom[i2 + OPENPROP_BOTTOMHEIGHT];
  444.       i2++;
  445.       }
  446.  
  447.    SetOpenPropPot(resetpos);
  448. }
  449.  
  450.  
  451.  
  452.  
  453. /* ======================================================================= */
  454. /* === Requester Handler Routines ======================================== */
  455. /* ======================================================================= */
  456.  
  457. VOID StartOpenRequester()
  458. /* Called after the requester has been opened. */
  459. {
  460.    ActivateGadget(&OpenNameTextGadget, OpenReqWindow, OpenReq);
  461.  
  462.    if (FlagIsClear(OpenReqFileIO->Flags, GOOD_FILENAMES))
  463.       WarmStartFileIO(OpenReqFileIO);
  464.    else DrawSelectNames();
  465. }
  466.  
  467.  
  468.  
  469. SHORT HandleSelect(y, seconds, micros)
  470. SHORT y;
  471. LONG seconds, micros;
  472. /* This routine accepts that a GADGETDOWN occured at the given 
  473.  * pointer y offset.  This is translated into the ordinal number of the 
  474.  * filename selected by the user, and this is assigned to the 
  475.  * CurrentPick variable of the OpenReqFileIO structure.
  476.  * Returns:
  477.  *     1 = DirectoryName() returned TRUE (selection was directory name)
  478.  *     0 = new name selected, DirectoryName() returned FALSE (normal name)
  479.  *    -1 = same name selected, double-clicked
  480.  *    -2 = same name selected, not double-clicked
  481.  */
  482. {
  483.    SHORT returnvalue, oldy;
  484.    LONG oldseconds, oldmicros;
  485.  
  486.    y -= (OpenReq->TopEdge + OPENSELECT_TOP);
  487.    y = y / OPEN_LINEHEIGHT;
  488.    y += OpenReqFileIO->NameStart;
  489.    if (y >= OpenReqFileIO->NameCount)
  490.       y = OpenReqFileIO->NameCount - 1;
  491.  
  492.    oldseconds = OpenClickSeconds;
  493.    oldmicros = OpenClickMicros;
  494.    OpenClickSeconds = seconds;
  495.    OpenClickMicros = micros;
  496.  
  497.    oldy = OpenReqFileIO->CurrentPick;
  498.    OpenReqFileIO->CurrentPick = y;
  499.  
  500.    if (DirectoryName())
  501.       {
  502.       returnvalue = 1;
  503.       }
  504.    else
  505.       {
  506.       if (y == oldy)
  507.          {
  508.          /* User has selected the same name again.
  509.           * Was it done quickly enough to count as a
  510.           * double-click selection?
  511.           */
  512.          if (FlagIsClear(OpenReqFileIO->Flags, DOUBLECLICK_OFF)
  513.                && DoubleClick(oldseconds, oldmicros,
  514.                      OpenClickSeconds, OpenClickMicros))
  515.             returnvalue = -1;
  516.          else returnvalue = -2;
  517.          }
  518.       else
  519.          {
  520.          /* Do this work, what there is of it, only if the user 
  521.           * hasn't reselected an already-selected name.
  522.           */
  523.          returnvalue = 0;
  524.          }
  525.       }
  526.  
  527.    return(returnvalue);
  528. }
  529.  
  530.  
  531.  
  532. LONG HandleGadget(gadget, x, y, seconds, micros)
  533. struct Gadget *gadget;
  534. SHORT x, y;
  535. LONG seconds, micros;
  536. /* This routine handles one gadget selection */
  537. {
  538.    BOOL softbuild, hardbuild;
  539.    SHORT count;
  540.    LONG returnvalue;
  541.  
  542.    /* softbuild causes the file names to be refreshed.
  543.     * hardbuild causes the entire requester to be reestablished.
  544.     * either or both can be set.
  545.     */
  546.    softbuild = hardbuild = FALSE;
  547.  
  548.    /* count refers to the count that will be sent to StuffSelectNames().
  549.     * The default is 2, as you can see.
  550.     */
  551.    count = 2;
  552.  
  553.    /* If the selection of any gadget causes us to want the requester to
  554.     * go away, set the returnvalue non-zero.
  555.     */
  556.    returnvalue = 0;
  557.  
  558.    switch (gadget->GadgetID)
  559.       {
  560.       case OPENGADGET_SELECTNAME:
  561.          if (OpenReqFileIO->NameCount)
  562.             {
  563.             /* So our big name gadget was selected, eh?  Well, which one 
  564.              * was the user really pointing at?
  565.              */
  566.             y = HandleSelect(y, seconds, micros);
  567.             if (y < 0)
  568.                {
  569.                /* The user has reselected the old name */
  570.                if (y == -1) returnvalue = -1;
  571.                }
  572.             else
  573.                {
  574.                /* The user has selected a new name */
  575.                StuffFileName();
  576.                softbuild = TRUE;
  577.                if (y == 1) hardbuild = TRUE;
  578.                count = 5;
  579.                }
  580.             }
  581.          break;
  582.       case OPENGADGET_UPGADGET:
  583.          if (OpenReqFileIO->NameStart)
  584.             {
  585.             OpenReqFileIO->NameStart--;
  586.             softbuild = TRUE;
  587.             }
  588.          break;
  589.       case OPENGADGET_DOWNGADGET:
  590.          if (OpenReqFileIO->NameStart + NAME_ENTRY_COUNT
  591.                < OpenReqFileIO->NameCount)
  592.             {
  593.             OpenReqFileIO->NameStart++;
  594.             softbuild = TRUE;
  595.             }
  596.          break;
  597.       case OPENGADGET_PROPGADGET:
  598.          if (OpenReqFileIO->NameCount > NAME_ENTRY_COUNT)
  599.             {
  600.             SetNameStart();
  601.             softbuild = TRUE;
  602.             }
  603.          break;
  604.       case OPENGADGET_NEXTDISK:
  605.          /* Next disk!  Wholly mackerel!  First, if no "next" then split */
  606.          if (OpenReqFileIO->VolumeCount <= 1) break;
  607.  
  608.          OpenReqFileIO->VolumeIndex++;
  609.          if (OpenReqFileIO->VolumeIndex >= OpenReqFileIO->VolumeCount)
  610.             OpenReqFileIO->VolumeIndex = 0;
  611.          CopyString(&OpenReqFileIO->DiskName[0], CurrentVolumeName());
  612.          ResetDiskText(FALSE);
  613.          ResetDrawerText(TRUE);
  614.  
  615.          /* Refresh the display so the user can see what's been done, as
  616.           * well as having the display refreshed all over again (hardbuild)
  617.           * below after the new filenames are retrieved.
  618.           */
  619.          softbuild = TRUE;
  620.          count = 5;
  621.  
  622.          /* Intentionally fall into DRAWER/DISKTEXT */
  623.  
  624.       case OPENGADGET_DRAWERTEXT:
  625.       case OPENGADGET_DISKTEXT:
  626.          ResetNameText(TRUE);
  627.          hardbuild = TRUE;
  628.          break;
  629.       default:
  630.          break;
  631.       }
  632.  
  633.    /* These are split intentionally, because setters of hardbuild might
  634.     * want a softbuild done first, to show why a hardbuild is being done!
  635.     */
  636.    if (hardbuild) SetWaitPointer(OpenReqWindow);
  637.    if (softbuild)
  638.       {
  639.       SetOpenPropPot();
  640.       StuffSelectNames(count);
  641.       }
  642.    if (hardbuild)
  643.       WarmStartFileIO(OpenReqFileIO);  /* Restart the lock etc. */
  644.  
  645.    return(returnvalue);
  646. }
  647.  
  648.  
  649.  
  650. VOID DiskInserted()
  651. /* This routine is called by the RequesterSupport code whenever a new disk
  652.  * has been inserted.  This allows the user to swap disks while the
  653.  * requester is displayed.  Unfortunately, I have no way of knowing which
  654.  * disk swapped, so I have to restart the requester more or less.
  655.  * Not too bad, but a little unpleasant.
  656.  */
  657. {
  658.    SetWaitPointer(OpenReqWindow);
  659.    SetFlag(OpenReqFileIO->Flags, DISK_HAS_CHANGED);
  660.    BuildVolumeTable(OpenReqFileIO);
  661.    CopyString(&OpenReqFileIO->DiskName[0], CurrentVolumeName());
  662.    WarmStartFileIO(OpenReqFileIO);
  663. }
  664.  
  665.  
  666.  
  667. VOID PropMouseMoves()
  668. /* This routine is called by RequesterSupport whenever the mouse moves
  669.  * while a FOLLOWMOUSE gadget is set.  The only FOLLOWMOUSE gadget is
  670.  * the prop gadget, so...
  671.  */
  672. {
  673.    /* ... if there's more names than the number of visible names,
  674.     * then reset the name start and redisplay the names.
  675.     */
  676.    if (OpenReqFileIO->NameCount > NAME_ENTRY_COUNT)
  677.       {
  678.       SetNameStart();
  679.       StuffSelectNames(2);
  680.       }
  681. }
  682.  
  683.