Annotation of os232sdk/toolkt20/c/samples/nead/neadfile.c, revision 1.1.1.1

1.1       root        1: /*************************************************************
                      2: 
                      3:  This module contains subroutines for nead.c that specifically
                      4:  deal with the Open file interface.  Most of the routines were
                      5:  taken from Charles Petzold's book "Programming the OS/2
                      6:  Presentation Manager" and were slightly modified.
                      7: 
                      8:  Procedures in this file:
                      9:    OpenFile()          Asks user for new file name and opens it
                     10:    OpenFileProc()      Dialog proc that prompts user for file name
                     11:    FillDirListBox()    Fills the directory list box
                     12:    FillFileListBox()   Fills the file list box
                     13: 
                     14: **************************************************************/
                     15: #include "nead.h"
                     16: 
                     17: /************ External GLOBALS *******************************/
                     18: 
                     19: extern CHAR szFileName[CCHMAXPATH];
                     20: extern CHAR szEAName[MAXEANAME+1];
                     21: extern USHORT usRetEAType;
                     22: extern BOOL FILE_ISOPEN;
                     23: extern BOOL FILE_CHANGED;
                     24: extern BOOL COMMAND_LINE_FILE;
                     25: extern CHAR *pAlloc,*szEditBuf,*szAscii,*szScratch;
                     26: extern HOLDFEA *pHoldFEA;
                     27: extern DELETELIST *pDelList;
                     28: extern EADATA ConvTable[EATABLESIZE];
                     29: 
                     30: /*************************************************************/
                     31: 
                     32: 
                     33: /*
                     34:  * Function name: OpenFile()
                     35:  *
                     36:  * Parameters:  hwnd which is the current window handle.
                     37:  *              usMode which will attempt to load the file from the command
                     38:  *              line iff usMode == ARGFILE which is set in main().  Otherwise,
                     39:  *              the selector box is brought up for the user to select from.
                     40:  *
                     41:  * Returns: TRUE iff a file is open upon exit.
                     42:  *
                     43:  * Purpose: This routine handles opening a new file.  It will also query the
                     44:  *          user for the disposition of the current file if it has been
                     45:  *          modified before loading the new file.
                     46:  *
                     47:  * Usage/Warnings:  Routine should be bullet proof as it does its own
                     48:  *                  error checking.  It assumes that hwnd points to the
                     49:  *                  correct window with the name listbox in it.
                     50:  *
                     51:  * Calls: WriteEAs(), Free_FEAList()
                     52:  */
                     53: 
                     54: BOOL OpenFile(HWND hwnd,USHORT usMode)
                     55: {
                     56:    CHAR szOldFile[CCHMAXPATH];
                     57:    USHORT usRet;
                     58: 
                     59:    strcpy(szOldFile,szFileName);  /* Save name of the currently open file */
                     60: 
                     61:    if(usMode != ARGFILE)          /* It isn't the command line file */
                     62:    {
                     63:       if(!WinDlgBox(HWND_DESKTOP, /* Get the file name from the user */
                     64:                     hwnd,
                     65:                     OpenFileProc,
                     66:                     NULL,
                     67:                     IDD_OPENBOX,
                     68:                     NULL))
                     69:       {
                     70:          strcpy(szFileName,szOldFile); /* They canceled, restore old file */
                     71:          return(FILE_ISOPEN);
                     72:       }
                     73:    }
                     74: 
                     75:    if(FILE_CHANGED) /* Give them a chance to save modifications */
                     76:    {
                     77:       usRet=WinMessageBox(HWND_DESKTOP,hwnd,
                     78:                           "The current file has been changed.  Do you \
                     79: wish to save the changes before proceeding?",
                     80:                           "Warning",NULL,MB_YESNOCANCEL | MB_ICONQUESTION);
                     81:       switch(usRet)
                     82:       {
                     83:          case MBID_YES:
                     84:             WriteEAs();
                     85:             break;
                     86:          case MBID_CANCEL:
                     87:             return FILE_ISOPEN;
                     88:       }
                     89:    }
                     90: 
                     91:    if(FILE_ISOPEN) /* Free up everything associated with the current file */
                     92:    {
                     93:       Free_FEAList(pHoldFEA,pDelList);
                     94:       FILE_ISOPEN = FALSE;
                     95:    }
                     96: 
                     97:    if(QueryEAs(szFileName)) /* We were successful */
                     98:    {
                     99:       HOLDFEA *pFEA=pHoldFEA;
                    100: 
                    101:       FILE_ISOPEN = TRUE;
                    102:       FILE_CHANGED = FALSE;
                    103: 
                    104:       WinSendDlgItemMsg(hwnd, IDD_LBOX, LM_DELETEALL,0L,0L); /* Fill L-box */
                    105: 
                    106:       while(pFEA)
                    107:       {
                    108:          WinSendDlgItemMsg(hwnd, IDD_LBOX, LM_INSERTITEM,
                    109:                            MPFROM2SHORT(LIT_END,0),
                    110:                            MPFROMP(pFEA->szName));
                    111:          pFEA = pFEA->next;
                    112:       }
                    113:    }
                    114:    else /* We couldn't query the EAs */
                    115:    {
                    116:       *szFileName = '\000';
                    117:       WinSetDlgItemText(hwnd,IDD_FNAME,szFileName);
                    118:       return(FILE_ISOPEN = FALSE);
                    119:    }
                    120:    WinSetDlgItemText(hwnd,IDD_FNAME,szFileName);
                    121:    pDelList = NULL;
                    122:    return(TRUE);
                    123: }
                    124: 
                    125: 
                    126: /*
                    127:  * Function name: OpenFileProc()
                    128:  *
                    129:  * Parameters:  hwnd, msg, mp1, mp2.  Standard PM Dialog Proc params.
                    130:  *              Expects no user pointer.
                    131:  *
                    132:  * Returns: TRUE if user selects OK, FALSE if Cancel is selected.
                    133:  *
                    134:  * Purpose: This proc handles the user interface to select a file name.
                    135:  *          Some elementary checks are done to make sure the filename is
                    136:  *          valid.
                    137:  *
                    138:  * Usage/Warnings:  The interface is NOT foolproof as it is possible to
                    139:  *                  continue with a non-existant file name.  Also, users
                    140:  *                  are not currently allowed to view/edit the EAs attached
                    141:  *                  to a directory.
                    142:  *
                    143:  * Calls: FillDirListBox(), FillFileListBox(), ParseFileName()
                    144:  */
                    145: 
                    146: MRESULT EXPENTRY OpenFileProc(HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2)
                    147: {
                    148:    static CHAR szCurrentPath[CCHMAXPATH]={'.', '\\', '*', '\000'},
                    149:                szBuffer[CCHMAXPATH];
                    150:    CHAR        szParsedPath[CCHMAXPATH];
                    151:    SHORT       sSelect;
                    152: 
                    153:    switch(msg)
                    154:    {
                    155:       case WM_INITDLG:
                    156:          FillDirListBox(hwnd,szCurrentPath);
                    157:          FillFileListBox(hwnd);
                    158:          WinSendDlgItemMsg(hwnd, IDD_FILEEDIT,EM_SETTEXTLIMIT,
                    159:                                  MPFROM2SHORT(CCHMAXPATH,0),NULL);
                    160:          return 0L;
                    161: 
                    162:       case WM_CONTROL:
                    163:          if(SHORT1FROMMP(mp1) == IDD_DIRLIST ||  /* An lbox item is selected */
                    164:             SHORT1FROMMP(mp1) == IDD_FILELIST)
                    165:          {
                    166:             sSelect = (USHORT) WinSendDlgItemMsg(hwnd, /* Get item->szBuffer */
                    167:                                SHORT1FROMMP(mp1),
                    168:                                LM_QUERYSELECTION, 0L, 0L);
                    169: 
                    170:             WinSendDlgItemMsg(hwnd, SHORT1FROMMP(mp1),
                    171:                               LM_QUERYITEMTEXT,
                    172:                               MPFROM2SHORT(sSelect, sizeof(szBuffer)),
                    173:                               MPFROMP(szBuffer));
                    174:          }
                    175: 
                    176:          switch(SHORT1FROMMP(mp1))
                    177:          {
                    178:             case IDD_DIRLIST:              /* Item was in the directory lbox */
                    179:                switch(SHORT2FROMMP(mp1))
                    180:                {
                    181:                   case LN_ENTER:           /* Go to the select drive/dir */
                    182:                      if(*szBuffer == ' ')
                    183:                         DosSelectDisk(*(szBuffer+1) - '@');
                    184:                      else
                    185:                         DosChDir(szBuffer);
                    186: 
                    187:                      FillDirListBox(hwnd, szCurrentPath);
                    188:                      FillFileListBox(hwnd);
                    189: 
                    190:                      WinSetDlgItemText(hwnd, IDD_FILEEDIT, "");
                    191:                      return 0L;
                    192:                }
                    193:                break;
                    194: 
                    195:             case IDD_FILELIST:             /* Item was in the file lbox */
                    196:                switch(SHORT2FROMMP(mp1))
                    197:                {
                    198:                   case LN_SELECT:          /* Copy name to entry field  */
                    199:                      WinSetDlgItemText(hwnd, IDD_FILEEDIT, szBuffer);
                    200:                      return 0L;
                    201: 
                    202:                   case LN_ENTER:           /* Try to query the file */
                    203:                      if(ParseFileName(szFileName, szBuffer) != FILE_VALID)
                    204:                         return 0; /* Some error, don't finish */
                    205:                      WinDismissDlg(hwnd, TRUE);
                    206:                      return 0L;
                    207:                }
                    208:                break;
                    209:          }
                    210:          break;
                    211: 
                    212:       case WM_COMMAND:
                    213:          switch(LOUSHORT(mp1))
                    214:          {
                    215:             case DID_OK:            /* Try to query file in the entry field */
                    216:                WinQueryDlgItemText(hwnd, IDD_FILEEDIT,
                    217:                                    sizeof(szBuffer), szBuffer);
                    218: 
                    219:                switch(ParseFileName(szParsedPath, szBuffer))
                    220:                {
                    221:                   case FILE_INVALID:    /* Can't open the file */
                    222:                      WinAlarm(HWND_DESKTOP, WA_ERROR);
                    223:                      FillDirListBox(hwnd, szCurrentPath);
                    224:                      FillFileListBox(hwnd);
                    225:                      return 0L;
                    226: 
                    227:                   case FILE_PATH:    /* It was an incomplete path name */
                    228:                      strcpy(szCurrentPath,szBuffer);
                    229:                      FillDirListBox(hwnd, szCurrentPath);
                    230:                      FillFileListBox(hwnd);
                    231:                      WinSetDlgItemText(hwnd, IDD_FILEEDIT, "");
                    232:                      return 0L;
                    233: 
                    234:                   case FILE_VALID:    /* It was valid */
                    235:                      strcpy(szFileName, szParsedPath);
                    236:                      WinDismissDlg(hwnd, TRUE);
                    237:                      return 0L;
                    238:                }
                    239:                break;
                    240: 
                    241:             case DID_CANCEL:
                    242:                WinDismissDlg(hwnd, FALSE);
                    243:                return 0L;
                    244:          }
                    245:          break;
                    246:    }
                    247:    return WinDefDlgProc(hwnd, msg, mp1, mp2);
                    248: }
                    249: 
                    250: 
                    251: /*
                    252:  * Function name: FillDirListBox()
                    253:  *
                    254:  * Parameters:  hwnd points to the current window handle
                    255:  *              pcCurrentPath points to a buffer which will be filled in
                    256:  *              with the current path.
                    257:  *
                    258:  * Returns: VOID
                    259:  *
                    260:  * Purpose: This routine is called by OpenFileProc to fill in the directory
                    261:  *          list box
                    262:  *
                    263:  * Usage/Warnings:  Adequete error checking is NOT done on the return
                    264:  *                  values of the system calls.  Also, it is remotely
                    265:  *                  possible that the calls to add to the list box could fail.
                    266:  *
                    267:  * Calls:
                    268:  */
                    269: 
                    270: VOID FillDirListBox(HWND hwnd, CHAR *pcCurrentPath)
                    271: {
                    272:    static CHAR szDrive [] = "  :";
                    273:    FILEFINDBUF findbuf;
                    274:    HDIR        hDir = 1;
                    275:    SHORT       sDrive;
                    276:    
                    277:    ULONG       ulCurPathLen, ulDriveMap, ulSearchCount = 1, ulDriveNum;
                    278: 
                    279:    DosQCurDisk(&ulDriveNum, &ulDriveMap);
                    280:    *pcCurrentPath     = (CHAR) ulDriveNum + '@';
                    281:    *(pcCurrentPath+1) = ':';
                    282:    *(pcCurrentPath+2) = '\\';
                    283:    ulCurPathLen = CCHMAXPATH;
                    284:    DosQCurDir(0L, pcCurrentPath + 3, &ulCurPathLen);
                    285: 
                    286:    WinSetDlgItemText(hwnd, IDD_PATH, pcCurrentPath);
                    287:    WinSendDlgItemMsg(hwnd, IDD_DIRLIST, LM_DELETEALL, NULL, NULL);
                    288: 
                    289:    for(sDrive = ('A'-'A'); sDrive <= ('Z'-'A'); sDrive++)
                    290:    {
                    291:       if(ulDriveMap & (1L << sDrive))
                    292:       {
                    293:          *(szDrive+1) = (CHAR) sDrive + 'A';
                    294: 
                    295:          WinSendDlgItemMsg(hwnd, IDD_DIRLIST, LM_INSERTITEM,
                    296:                            MPFROM2SHORT(LIT_END, 0),
                    297:                            MPFROMP(szDrive));
                    298:       }
                    299:    }
                    300:    DosFindFirst("*", &hDir, FILE_DIRECTORY | FILE_ALL, &findbuf,
                    301:                 sizeof(findbuf), &ulSearchCount, FIL_STANDARD);
                    302:    while(ulSearchCount)
                    303:    {
                    304:       if((findbuf.attrFile & FILE_DIRECTORY) &&
                    305:          (findbuf.achName[0] != '.' || findbuf.achName[1]))
                    306: 
                    307:          WinSendDlgItemMsg(hwnd, IDD_DIRLIST, LM_INSERTITEM,
                    308:                            MPFROM2SHORT(LIT_SORTASCENDING, 0),
                    309:                            MPFROMP(findbuf.achName));
                    310: 
                    311:       if(DosFindNext(hDir, &findbuf, sizeof(findbuf), &ulSearchCount))
                    312:          break;
                    313:    }
                    314: }
                    315: 
                    316: 
                    317: /* This routine is called by OpenFileProc to fill the file list box */
                    318: 
                    319: /*
                    320:  * Function name: FillFileListBox()
                    321:  *
                    322:  * Parameters:  hwnd points to the current window handle
                    323:  *
                    324:  * Returns: VOID
                    325:  *
                    326:  * Purpose: This routine is called by OpenFileProc to fill in the file
                    327:  *          list box with files in the current directory.
                    328:  *
                    329:  * Usage/Warnings:  Adequete error checking is NOT done on the return
                    330:  *                  values of the system calls.  Also, it is remotely
                    331:  *                  possible that the calls to add to the list box could fail.
                    332:  *
                    333:  * Calls:
                    334:  */
                    335: 
                    336: VOID FillFileListBox(HWND hwnd)
                    337: {
                    338:    FILEFINDBUF findbuf;
                    339:    HDIR        hDir = 1;
                    340:    ULONG      ulSearchCount = 1; /* Read 1 entry at a time */
                    341: 
                    342:    WinSendDlgItemMsg(hwnd, IDD_FILELIST, LM_DELETEALL, NULL, NULL);
                    343: 
                    344:    DosFindFirst("*", &hDir, FILE_ALL, &findbuf, sizeof(findbuf),
                    345:                        &ulSearchCount, FIL_STANDARD);
                    346:    while(ulSearchCount)
                    347:    {
                    348:       WinSendDlgItemMsg(hwnd, IDD_FILELIST, LM_INSERTITEM,
                    349:                         MPFROM2SHORT(LIT_SORTASCENDING, 0),
                    350:                         MPFROMP(findbuf.achName));
                    351: 
                    352:       if(DosFindNext(hDir, &findbuf, sizeof(findbuf), &ulSearchCount))
                    353:          break;
                    354:    }
                    355: }
                    356: 
                    357: 
                    358: /*
                    359:  * Function name: ParseFileName()
                    360:  *
                    361:  * Parameters:  pcOut points to a buffer for the return file specification.
                    362:  *              pcIn  points to the buffer containing the raw input spec.
                    363:  *
                    364:  * Returns: FILE_INVALID if pcIn had invalid drive or no directory
                    365:  *          FILE_PATH    if pcIn was empty or had just a path/no file name.
                    366:  *          FILE_VALID   if pcIn point to good file.
                    367:  *
                    368:  * Purpose: This routine changes drive and directory as per pcIn string.
                    369:  *
                    370:  * Usage/Warnings:  Note that pcOut is only valid if FILE_VALID is returned.
                    371:  *                  in place of strupr(), a codepage should be fetched and
                    372:  *                  DosCaseMap() should be used to allow for extended chars.
                    373:  *                  This routine could use some cleanup work.
                    374:  *
                    375:  * Calls:
                    376:  */
                    377: 
                    378: SHORT ParseFileName(CHAR *pcOut, CHAR *pcIn)
                    379: {
                    380:    CHAR   *pcLastSlash, *pcFileOnly ;
                    381:    ULONG  ulDriveMap, ulDirLen = CCHMAXPATH, ulDriveNum;
                    382: 
                    383:    strupr(pcIn);  /* Does NOT handle extended chars, should use DosCaseMap */
                    384: 
                    385:    if(*pcIn == '\000')  /* If string is empty, return FILE_PATH */
                    386: 
                    387:       return FILE_PATH;
                    388: 
                    389:    /* Get drive from input string or use current drive */
                    390: 
                    391:    if(*(pcIn+1) == ':') /* Yup, they specified a drive */
                    392:    {
                    393:       if(DosSelectDisk(*pcIn - '@')) /* Change to selected drive */
                    394:          return FILE_INVALID;
                    395:       pcIn += 2;
                    396:    }
                    397:    DosQCurDisk(&ulDriveNum, &ulDriveMap); /* Get current drive */
                    398: 
                    399:    *pcOut++ = (CHAR) ulDriveNum + '@'; /* Build drive letter */
                    400:    *pcOut++ = ':';
                    401:    *pcOut++ = '\\';
                    402: 
                    403:    if(*pcIn == '\000') /* If rest of the string is empty, return FILE_PATH */
                    404:       return FILE_PATH;
                    405: 
                    406:    /* Search for the last backslash.  If none, it could be a directory. */
                    407: 
                    408:    if(!(pcLastSlash = strrchr(pcIn, '\\'))) /* No slashes? */
                    409:    {
                    410:       if(!DosChDir(pcIn))
                    411:          return FILE_PATH;            /* It was a directory */
                    412: 
                    413:       DosQCurDir(0L, pcOut, &ulDirLen); /* Get current dir & attach input fn */
                    414: 
                    415:       if(*(pcOut+strlen(pcOut)-1) != '\\')
                    416:          strcat(pcOut++, "\\");
                    417: 
                    418:       strcat(pcOut, pcIn);
                    419:       return FILE_VALID;
                    420:    }
                    421: 
                    422:    /* If the only backslash is at the beginning, change to root */
                    423: 
                    424:    if(pcIn == pcLastSlash)
                    425:    {
                    426:       DosChDir("\\");
                    427: 
                    428:       if(*(pcIn+1) == '\000')
                    429:          return FILE_PATH;
                    430: 
                    431:       strcpy(pcOut, pcIn+1);
                    432:       return FILE_VALID;
                    433:    }
                    434: 
                    435:    /* Attempt to change directory -- Get current dir if OK */
                    436: 
                    437:    *pcLastSlash = NULL;
                    438: 
                    439:    if(DosChDir(pcIn))
                    440:       return FILE_INVALID;
                    441: 
                    442:    DosQCurDir(0L, pcOut, &ulDirLen);
                    443: 
                    444:    /* Append input filename if any */
                    445: 
                    446:    pcFileOnly = pcLastSlash+1;
                    447: 
                    448:    if(*pcFileOnly == '\000')
                    449:       return FILE_PATH;
                    450: 
                    451:    if(*(pcOut+strlen(pcOut)-1) != '\\')
                    452:       strcat(pcOut++, "\\");
                    453: 
                    454:    strcat(pcOut, pcFileOnly);
                    455:    return FILE_VALID;
                    456: }
                    457: 

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.