Annotation of mstools/samples/sdktools/dlgedit/rwdlg.c, revision 1.1.1.1

1.1       root        1: 
                      2: /******************************************************************************\
                      3: *       This is a part of the Microsoft Source Code Samples. 
                      4: *       Copyright (C) 1993 Microsoft Corporation.
                      5: *       All rights reserved. 
                      6: *       This source code is only intended as a supplement to 
                      7: *       Microsoft Development Tools and/or WinHelp documentation.
                      8: *       See these sources for detailed information regarding the 
                      9: *       Microsoft samples programs.
                     10: \******************************************************************************/
                     11: 
                     12: /****************************** Module Header *******************************
                     13: * Module Name: rwdlg.c
                     14: *
                     15: * Does the writing of .DLG files.
                     16: *
                     17: * Functions:
                     18: *    WriteDlg()
                     19: *    WriteDlgInclude()
                     20: *    WriteDialogHeader()
                     21: *    WriteDialogHeaderLanguage()
                     22: *    WriteControl()
                     23: *    WriteNameOrd()
                     24: *    WriteText()
                     25: *    WriteIDDlg()
                     26: *    GetControlKeyword()
                     27: *    WriteClass()
                     28: *    WriteStyles()
                     29: *    WriteClassStyle()
                     30: *    WriteCustomStyle()
                     31: *    WriteCoords()
                     32: *    WriteValue()
                     33: *    WriteHexWord()
                     34: *    WriteHexDWord()
                     35: *    WriteString()
                     36: *    WriteQuotedString()
                     37: *    WriteEscapedString()
                     38: *    WriteDlgChar()
                     39: *    WriteDlgFlush()
                     40: *    Tab()
                     41: *    NewLine()
                     42: *    Quote()
                     43: *    Comma()
                     44: *    Space()
                     45: *    ORSymbol()
                     46: *
                     47: * Comments:
                     48: *
                     49: ****************************************************************************/
                     50: 
                     51: #include "dlgedit.h"
                     52: #include "dlgfuncs.h"
                     53: #include "dlgextrn.h"
                     54: 
                     55: 
                     56: /*
                     57:  * Wrap lines before they go over this right margin.
                     58:  */
                     59: #define CCHRIGHTMARGIN      76
                     60: 
                     61: /*
                     62:  * Defines for the tabs and tab indent levels.
                     63:  */
                     64: #define CCHTABWIDTH         4           // Tabs are four spaces wide.
                     65: #define TABLEVELNONE        0           // No indent (at left margin).
                     66: #define TABLEVELCONTROL     1           // Indent to start of controls.
                     67: #define TABLEVELCONTROLDESC 5           // Indent to control description.
                     68: 
                     69: /*
                     70:  * Macro to set the current tab level.  The level is multiplied
                     71:  * by the tab width.
                     72:  */
                     73: #define SetTab(t)           (cTabStop = ((t)*CCHTABWIDTH))
                     74: 
                     75: /*
                     76:  * Macro that determines if the current position is the first
                     77:  * column for the current tab setting.
                     78:  */
                     79: #define AtFirstTabColumn()  ((cColumn == cTabStop) ? TRUE : FALSE)
                     80: 
                     81: STATICFN VOID WriteDlgInclude(LPTSTR pszFullDlgFile);
                     82: STATICFN PCONTROLDATA WriteDialogHeader(PRES pRes, PDIALOGBOXHEADER pdbh);
                     83: STATICFN VOID WriteDialogHeaderLanguage(WORD wLanguage);
                     84: STATICFN PCONTROLDATA WriteControl(PCONTROLDATA pcd);
                     85: STATICFN VOID WriteNameOrd(LPTSTR pszNameOrd);
                     86: STATICFN VOID WriteText(LPTSTR pszText);
                     87: STATICFN VOID WriteIDDlg(INT id, BOOL fHexOK);
                     88: STATICFN LPTSTR GetControlKeyword(INT iClass, DWORD flStyle,
                     89:     DWORD *pflStylePredef, DWORD *pflStyleDefault, BOOL *pfWriteText,
                     90:     BOOL *pfNotFound);
                     91: STATICFN VOID WriteClass(LPTSTR pszClass);
                     92: STATICFN BOOL WriteStyles(INT iClass, LPTSTR pszClass, DWORD flStyle,
                     93:     DWORD flStylePredef, DWORD flStyleDefault, PDWORD pflStyleLeft,
                     94:     BOOL fNullStyles, BOOL fCommaPrefix);
                     95: STATICFN BOOL WriteClassStyle(INT iClass, DWORD flStyle,
                     96:     DWORD flStylePredef, DWORD flStyleDefault, PDWORD pflStyleLeft,
                     97:     BOOL fPrevWritten, BOOL fNullStyles, BOOL fCommaPrefix);
                     98: STATICFN BOOL WriteCustomStyle(LPTSTR pszClass, DWORD flStyle,
                     99:     PDWORD pflStyleLeft);
                    100: STATICFN VOID WriteCoords(INT x, INT y, INT cx, INT cy);
                    101: STATICFN VOID WriteValue(INT n);
                    102: STATICFN VOID WriteHexWord(WORD w);
                    103: STATICFN VOID WriteHexDWord(DWORD dw);
                    104: STATICFN VOID WriteString(LPTSTR psz);
                    105: STATICFN VOID WriteQuotedString(LPTSTR psz);
                    106: STATICFN VOID WriteEscapedString(LPTSTR psz);
                    107: STATICFN VOID WriteDlgChar(TCHAR ch);
                    108: STATICFN VOID WriteDlgFlush(VOID);
                    109: STATICFN VOID Tab(VOID);
                    110: STATICFN VOID NewLine(VOID);
                    111: STATICFN VOID Quote(VOID);
                    112: STATICFN VOID Comma(VOID);
                    113: STATICFN VOID Space(VOID);
                    114: STATICFN VOID ORSymbol(VOID);
                    115: 
                    116: static INT cColumn;                 /* Current column in the line.      */
                    117: static INT cTabStop;                /* Current tabstop column.          */
                    118: static HANDLE hfDlg;                /* All workers write to this file.  */
                    119: static jmp_buf jbWriteDlg;          /* Capture the state for longjmp.   */
                    120: 
                    121: 
                    122: 
                    123: /************************************************************************
                    124: * WriteDlg
                    125: *
                    126: * This function writes the dialog boxes in the given resource to the
                    127: * hfWrite file in the .DLG file RC format.
                    128: *
                    129: * Arguments:
                    130: *    HANDLE - handle to the file
                    131: *    LPTSTR - pointer to the resource file name
                    132: *
                    133: ************************************************************************/
                    134: 
                    135: BOOL WriteDlg(
                    136:     HANDLE hfWrite,
                    137:     LPTSTR pszFullDlgFile)
                    138: {
                    139:     HANDLE hResLocked = NULL;
                    140:     PRES pRes = NULL;
                    141:     PRESLINK prl;
                    142:     PDIALOGBOXHEADER pdbh;
                    143:     PCONTROLDATA pcd;
                    144:     INT cItems;
                    145: 
                    146:     /*
                    147:      * Set our error trap up.  The api setjmp will return a zero at first,
                    148:      * then if a write error occurs later and longjmp is called, it
                    149:      * will return non-zero and we will return the failure up to the
                    150:      * caller.  After this point, there must be no calls to allocate
                    151:      * memory, open files, etc., unless this trap has a way to detect
                    152:      * what happened and clean it up.  See the c-runtime help file for more
                    153:      * information about setjump/longjmp.
                    154:      */
                    155:     if (_setjmp(jbWriteDlg)) {
                    156:         /*
                    157:          * If the resource is locked, unlock it.
                    158:          */
                    159:         if (hResLocked)
                    160:             GlobalUnlock(hResLocked);
                    161: 
                    162:         return FALSE;
                    163:     }
                    164: 
                    165:     /*
                    166:      * Initialize our globals.  The hfDlg global is used so that hfWrite
                    167:      * doesn't have to be passed on the stack over and over.
                    168:      */
                    169:     hfDlg = hfWrite;
                    170:     cColumn = 0;
                    171:     SetTab(TABLEVELNONE);
                    172: 
                    173:     WriteDlgInclude(pszFullDlgFile);
                    174: 
                    175:     /*
                    176:      * Process each resource in the list.
                    177:      */
                    178:     for (prl = gprlHead; prl; prl = prl->prlNext) {
                    179:         /*
                    180:          * Skip if it is not a dialog resource.
                    181:          */
                    182:         if (!prl->fDlgResource)
                    183:             continue;
                    184: 
                    185:         /*
                    186:          * Set up pointers to this dialog resource.
                    187:          */
                    188:         pRes = (PRES)GlobalLock(prl->hRes);
                    189:         hResLocked = prl->hRes;
                    190: 
                    191:         pdbh = (PDIALOGBOXHEADER)SkipResHeader(pRes);
                    192: 
                    193:         NewLine();
                    194:         pcd = WriteDialogHeader(pRes, pdbh);
                    195: 
                    196:         WriteString(ids(IDS_BEGIN));
                    197:         NewLine();
                    198: 
                    199:         /*
                    200:          * Write the controls.
                    201:          */
                    202:         cItems = (INT)pdbh->NumberOfItems;
                    203:         while (cItems--)
                    204:             pcd = WriteControl(pcd);
                    205: 
                    206:         /*
                    207:          * Finish up dialog template.
                    208:          */
                    209:         WriteString(ids(IDS_END));
                    210:         NewLine();
                    211: 
                    212:         GlobalUnlock(prl->hRes);
                    213:         hResLocked = NULL;
                    214:     }
                    215: 
                    216:     /*
                    217:      * Flush any remaining characters in the write buffer.
                    218:      */
                    219:     WriteDlgFlush();
                    220: 
                    221:     return TRUE;
                    222: }
                    223: 
                    224: 
                    225: 
                    226: /************************************************************************
                    227: * WriteDlgInclude
                    228: *
                    229: * This routine writes out the "DLGINCLUDE" lines to the .DLG file.
                    230: *
                    231: * Arguments:
                    232: *    LPTSTR - dialog file name
                    233: *
                    234: ************************************************************************/
                    235: 
                    236: STATICFN VOID WriteDlgInclude(
                    237:     LPTSTR pszFullDlgFile)
                    238: {
                    239:     if (pszIncludeFile) {
                    240:         WriteValue(ORDID_DLGINCLUDE_NAME);
                    241:         Space();
                    242:         WriteString(ids(IDS_DLGINCLUDE));
                    243:         Space();
                    244:         Quote();
                    245: 
                    246:         /*
                    247:          * If the include file is in a different directory than the resource
                    248:          * file, write the full path to it.  Otherwise, we just write the
                    249:          * include file name.
                    250:          */
                    251:         if (DifferentDirs(pszFullDlgFile, szFullIncludeFile))
                    252:             WriteEscapedString(szFullIncludeFile);
                    253:         else
                    254:             WriteEscapedString(pszIncludeFile);
                    255: 
                    256:         Quote();
                    257:         NewLine();
                    258:     }
                    259: }
                    260: 
                    261: 
                    262: 
                    263: /************************************************************************
                    264: * WriteDialogHeader
                    265: *
                    266: * Writes out the dialog header lines.
                    267: *
                    268: * Arguments:
                    269: *    PRES - pointer to the resource
                    270: *    PDIALOGBOXHEADER - pointer to the dialog box header
                    271: *
                    272: ************************************************************************/
                    273: 
                    274: STATICFN PCONTROLDATA WriteDialogHeader(
                    275:     PRES pRes,
                    276:     PDIALOGBOXHEADER pdbh)
                    277: {
                    278:     DWORD flStyle;
                    279:     DWORD flExtStyle;
                    280:     DWORD flStyleLeft;
                    281:     INT cdit;
                    282:     INT x;
                    283:     INT y;
                    284:     INT cx;
                    285:     INT cy;
                    286:     LPTSTR pszMenuName;
                    287:     LPTSTR pszClass;
                    288:     LPTSTR pszCaption;
                    289:     INT nPointSize;
                    290:     LPTSTR pszFontName;
                    291:     PCONTROLDATA pcd;
                    292:     PRES2 pRes2;
                    293:     BOOL fWritten;
                    294: 
                    295:     pRes2 = ResourcePart2(pRes);
                    296: 
                    297:     WriteNameOrd(ResourceName(pRes));
                    298:     Space();
                    299:     WriteString(ids(IDS_DIALOG));
                    300: 
                    301:     if (pRes2->MemoryFlags & MMF_PRELOAD) {
                    302:         Space();
                    303:         WriteString(ids(IDS_PRELOAD));
                    304:     }
                    305: 
                    306:     if (!(pRes2->MemoryFlags & MMF_MOVEABLE)) {
                    307:         Space();
                    308:         WriteString(ids(IDS_FIXED));
                    309:     }
                    310: 
                    311:     if (!(pRes2->MemoryFlags & MMF_PURE)) {
                    312:         Space();
                    313:         WriteString(ids(IDS_IMPURE));
                    314:     }
                    315: 
                    316:     /*
                    317:      * Parse out the dialog template.
                    318:      */
                    319:     pcd = ParseDialogBoxHeader(pdbh, &flStyle, &flExtStyle, &cdit, &x, &y,
                    320:             &cx, &cy, &pszMenuName, &pszClass, &pszCaption,
                    321:             &nPointSize, &pszFontName);
                    322: 
                    323:     Space();
                    324:     WriteCoords(x, y, cx, cy);
                    325: 
                    326:     NewLine();
                    327: 
                    328:     /*
                    329:      * Write the language.
                    330:      */
                    331:     WriteDialogHeaderLanguage(pRes2->LanguageId);
                    332: 
                    333:     /*
                    334:      * Print out the "STYLE" line for the dialog.
                    335:      */
                    336:     WriteString(ids(IDS_STYLE));
                    337:     Space();
                    338:     SetTab(TABLEVELCONTROL);
                    339:     WriteStyles(IC_DIALOG, NULL, flStyle, 0L, 0L, &flStyleLeft, TRUE, FALSE);
                    340:     SetTab(TABLEVELNONE);
                    341:     NewLine();
                    342: 
                    343:     /*
                    344:      * Print out the "EXSTYLE" line for the dialog, if necessary.
                    345:      */
                    346:     if (flExtStyle) {
                    347:         WriteString(ids(IDS_EXSTYLE));
                    348:         Space();
                    349:         SetTab(TABLEVELCONTROL);
                    350: 
                    351:         fWritten = WriteClassStyle(IC_EXSTYLE, flExtStyle, 0L, 0L,
                    352:                 &flStyleLeft, FALSE, TRUE, FALSE);
                    353: 
                    354:         /*
                    355:          * If there is anything left (styles that the dialog editor
                    356:          * does not know about) write it out as a hex constant.
                    357:          */
                    358:         if (flStyleLeft) {
                    359:             if (fWritten)
                    360:                 ORSymbol();
                    361: 
                    362:             WriteHexDWord(flStyleLeft);
                    363:         }
                    364: 
                    365:         SetTab(TABLEVELNONE);
                    366:         NewLine();
                    367:     }
                    368: 
                    369:     /*
                    370:      * If it has a caption, print it out.
                    371:      */
                    372:     if (*pszCaption) {
                    373:         WriteString(ids(IDS_CAPTION));
                    374:         Space();
                    375:         WriteText(pszCaption);
                    376:         NewLine();
                    377:     }
                    378: 
                    379:     /*
                    380:      * If it has a font specified, print it out.
                    381:      */
                    382:     if (flStyle & DS_SETFONT) {
                    383:         WriteString(ids(IDS_FONT));
                    384:         Space();
                    385: 
                    386:         WriteValue(nPointSize);
                    387:         Comma();
                    388:         WriteQuotedString(pszFontName);
                    389:         NewLine();
                    390:     }
                    391: 
                    392:     /*
                    393:      * If it has a class specified, print it out.
                    394:      */
                    395:     if (*pszClass) {
                    396:         WriteString(ids(IDS_CLASS));
                    397:         Space();
                    398:         WriteText(pszClass);
                    399:         NewLine();
                    400:     }
                    401: 
                    402:     /*
                    403:      * If it has a menu specified, print it out.
                    404:      */
                    405:     if (*pszMenuName) {
                    406:         WriteString(ids(IDS_MENU));
                    407:         Space();
                    408:         WriteNameOrd(pszMenuName);
                    409:         NewLine();
                    410:     }
                    411: 
                    412:     if (pRes2->Version) {
                    413:         WriteString(ids(IDS_VERSION));
                    414:         Space();
                    415:         WriteValue(pRes2->Version);
                    416:         NewLine();
                    417:     }
                    418: 
                    419:     if (pRes2->Characteristics) {
                    420:         WriteString(ids(IDS_CHARACTERISTICS));
                    421:         Space();
                    422:         WriteValue(pRes2->Characteristics);
                    423:         NewLine();
                    424:     }
                    425: 
                    426:     return pcd;
                    427: }
                    428: 
                    429: 
                    430: 
                    431: /************************************************************************
                    432: * WriteDialogHeaderLanguage
                    433: *
                    434: * Writes out the dialog header "LANGUAGE" line.
                    435: *
                    436: * Arguments:
                    437: *    WORD - language to write out
                    438: *
                    439: ************************************************************************/
                    440: 
                    441: STATICFN VOID WriteDialogHeaderLanguage(
                    442:     WORD wLanguage)
                    443: {
                    444:     WORD wPrimary;
                    445:     WORD wSubLang;
                    446:     INT i;
                    447:     INT j;
                    448:     INT idsLang;
                    449:     INT idsSubLang;
                    450: 
                    451:     WriteString(ids(IDS_LANGUAGE));
                    452:     Space();
                    453: 
                    454:     idsLang = 0;
                    455:     idsSubLang = 0;
                    456:     wPrimary = (WORD)PRIMARYLANGID(wLanguage);
                    457:     wSubLang = SUBLANGID(wLanguage);
                    458:     for (i = 0; i < gcLanguages; i++) {
                    459:         if (gaLangTable[i].wPrimary == wPrimary) {
                    460:             idsLang = gaLangTable[i].idsLang;
                    461: 
                    462:             for (j = 0; j < gaLangTable[i].cSubLangs; j++) {
                    463:                 if (gaLangTable[i].asl[j].wSubLang == wSubLang) {
                    464:                     idsSubLang = gaLangTable[i].asl[j].idsSubLang;
                    465:                     break;
                    466:                 }
                    467:             }
                    468: 
                    469:             break;
                    470:         }
                    471:     }
                    472: 
                    473:     if (idsLang)
                    474:         WriteString(ids(idsLang));
                    475:     else
                    476:         WriteHexWord(wPrimary);
                    477: 
                    478:     Comma();
                    479: 
                    480:     if (idsSubLang)
                    481:         WriteString(ids(idsSubLang));
                    482:     else
                    483:         WriteHexWord(wSubLang);
                    484: 
                    485:     NewLine();
                    486: }
                    487: 
                    488: 
                    489: 
                    490: /************************************************************************
                    491: * WriteControl
                    492: *
                    493: * Writes out a control line.
                    494: *
                    495: * Arguments:
                    496: *    PCONTROLDATA - pointer to the control data
                    497: *
                    498: ************************************************************************/
                    499: 
                    500: STATICFN PCONTROLDATA WriteControl(
                    501:     PCONTROLDATA pcd)
                    502: {
                    503:     INT x;
                    504:     INT y;
                    505:     INT cx;
                    506:     INT cy;
                    507:     INT id;
                    508:     DWORD flStyle;
                    509:     DWORD flExtStyle;
                    510:     LPTSTR pszClass;
                    511:     LPTSTR pszText;
                    512:     INT iClass;
                    513:     LPTSTR pszKeyword;
                    514:     BOOL fWriteText;
                    515:     BOOL fNotFound;
                    516:     DWORD flStylePredef;
                    517:     DWORD flStyleDefault;
                    518:     DWORD flStyleLeft;
                    519:     BOOL fWritten;
                    520: 
                    521:     pcd = ParseControlData(pcd, &flStyle, &flExtStyle, &x, &y, &cx, &cy,
                    522:             &id, &pszClass, &pszText);
                    523: 
                    524:     /*
                    525:      * Determine the class of the control.
                    526:      */
                    527:     iClass = GetiClass(pszClass);
                    528: 
                    529:     /*
                    530:      * Determine if there are any predefined RC keywords that we
                    531:      * can use instead of the generic "CONTROL" keyword for this
                    532:      * style of control.
                    533:      */
                    534:     pszKeyword = GetControlKeyword(iClass, flStyle, &flStylePredef,
                    535:             &flStyleDefault, &fWriteText, &fNotFound);
                    536: 
                    537:     SetTab(TABLEVELCONTROL);
                    538:     Tab();
                    539:     WriteString(pszKeyword);
                    540:     SetTab(TABLEVELCONTROLDESC);
                    541:     Tab();
                    542: 
                    543:     /*
                    544:      * Write out the text field, if this type of control has one.
                    545:      */
                    546:     if (fWriteText) {
                    547:         WriteText(pszText);
                    548:         Comma();
                    549:     }
                    550: 
                    551:     /*
                    552:      * Write out the id for the control.
                    553:      */
                    554:     WriteIDDlg(id, TRUE);
                    555: 
                    556:     /*
                    557:      * If we did not find a predefined keyword to use instead of "CONTROL",
                    558:      * we have to write out the fields in a different order, and specify
                    559:      * the class as well.
                    560:      */
                    561:     if (fNotFound) {
                    562:         WriteClass(pszClass);
                    563:         Comma();
                    564:         fWritten = WriteStyles(iClass, pszClass, flStyle, flStylePredef,
                    565:                 flStyleDefault, &flStyleLeft, fNotFound, FALSE);
                    566: 
                    567:         if (!fWritten || flStyleLeft) {
                    568:             if (fWritten)
                    569:                 ORSymbol();
                    570: 
                    571:             WriteHexWord(LOWORD(flStyleLeft));
                    572:         }
                    573: 
                    574:         Comma();
                    575:         WriteCoords(x, y, cx, cy);
                    576:     }
                    577:     else {
                    578:         Comma();
                    579:         WriteCoords(x, y, cx, cy);
                    580:         fWritten = WriteStyles(iClass, pszClass, flStyle, flStylePredef,
                    581:                 flStyleDefault, &flStyleLeft, fNotFound, TRUE);
                    582: 
                    583:         if (flStyleLeft) {
                    584:             if (fWritten)
                    585:                 ORSymbol();
                    586:             else
                    587:                 Comma();
                    588: 
                    589:             WriteHexWord(LOWORD(flStyleLeft));
                    590:             fWritten = TRUE;
                    591:         }
                    592:     }
                    593: 
                    594:     /*
                    595:      * Write out the extended styles for the control, if necessary.
                    596:      */
                    597:     if (flExtStyle) {
                    598:         /*
                    599:          * If writing a predefined keyword (not CONTROL), and there
                    600:          * were no styles written out at the end of the line, write
                    601:          * a style of zero.  RC doesn't like consecutive comma's,
                    602:          * and we need to skip the styles field to get to the
                    603:          * extended styles field.
                    604:          */
                    605:         if (!fNotFound && !fWritten) {
                    606:             Comma();
                    607:             WriteValue(0);
                    608:         }
                    609: 
                    610:         Comma();
                    611: 
                    612:         fWritten = WriteClassStyle(IC_EXSTYLE, flExtStyle, 0L, 0L,
                    613:                 &flStyleLeft, FALSE, TRUE, FALSE);
                    614: 
                    615:         /*
                    616:          * If there is anything left (styles that the dialog editor
                    617:          * does not know about) write it out as a hex constant.
                    618:          */
                    619:         if (flStyleLeft) {
                    620:             if (fWritten)
                    621:                 ORSymbol();
                    622: 
                    623:             WriteHexDWord(flStyleLeft);
                    624:         }
                    625:     }
                    626: 
                    627:     SetTab(TABLEVELNONE);
                    628:     NewLine();
                    629: 
                    630:     return pcd;
                    631: }
                    632: 
                    633: 
                    634: 
                    635: /************************************************************************
                    636: * WriteNameOrd
                    637: *
                    638: * Writes out the name/ordinal.  Handles the case where the name
                    639: * is really an ordinal instead of a string.  When it is a string,
                    640: * it will not be quoted.
                    641: *
                    642: * This routine never writes the ordinal out in hex, because the
                    643: * items that it is intended to write are not parsed properly by
                    644: * the Windows RC.EXE if they are written in hex notation.
                    645: *
                    646: * Arguments:
                    647: *   LPTSTR pszNameOrd - The name/ordinal to write.
                    648: *
                    649: ************************************************************************/
                    650: 
                    651: STATICFN VOID WriteNameOrd(
                    652:     LPTSTR pszNameOrd)
                    653: {
                    654:     if (IsOrd(pszNameOrd))
                    655:         /*
                    656:          * Write the name as a numeric ordinal.
                    657:          */
                    658:         WriteIDDlg(OrdID(pszNameOrd), FALSE);
                    659:     else
                    660:         WriteString(pszNameOrd);
                    661: }
                    662: 
                    663: 
                    664: 
                    665: /************************************************************************
                    666: * WriteText
                    667: *
                    668: * Writes out the text for a control or dialog.  This will either be
                    669: * an ordinal (icon's text field) or a quoted string.
                    670: *
                    671: * Arguments:
                    672: *    LPTSTR pszText - text to write out
                    673: *
                    674: ************************************************************************/
                    675: 
                    676: STATICFN VOID WriteText(
                    677:     LPTSTR pszText)
                    678: {
                    679:     if (IsOrd(pszText))
                    680:         /*
                    681:          * Write the text as an ID.  Hex notation is allowed.
                    682:          */
                    683:         WriteIDDlg(OrdID(pszText), TRUE);
                    684:     else
                    685:         WriteQuotedString(pszText);
                    686: }
                    687: 
                    688: 
                    689: 
                    690: /************************************************************************
                    691: * WriteIDDlg
                    692: *
                    693: * Writes out the ID.  This may be written out as either a symbol
                    694: * or a numeric.
                    695: *
                    696: * Arguments:
                    697: *    INT id - id to write out
                    698: *    BOOL fHexOK - flag specifies whether the id is a hex numeric.
                    699: *
                    700: ************************************************************************/
                    701: 
                    702: STATICFN VOID WriteIDDlg(
                    703:     INT id,
                    704:     BOOL fHexOK)
                    705: {
                    706:     TCHAR szID[CCHTEXTMAX];
                    707: 
                    708:     IDToLabel(szID, id, fHexOK);
                    709:     WriteString(szID);
                    710: }
                    711: 
                    712: 
                    713: 
                    714: /************************************************************************
                    715: * GetControlKeyword
                    716: *
                    717: * This routine does a lookup in the predefined RC keyword table
                    718: * associated with the given class for a keyword that can be used
                    719: * instead of "CONTROL".  The match is based on the style of the control
                    720: * that is passed in.  If a match is not found, it defaults all the
                    721: * returned values to use the "CONTROL" keyword.
                    722: *
                    723: * Arguments:
                    724: *   INT iClass              - The class of the control.
                    725: *   DWORD flStyle           - The style of the control.
                    726: *   DWORD *pflStylePredef   - Return for the bits of the predefined control
                    727: *                             (if found).  These can be removed later from
                    728: *                             the style flag.
                    729: *   DWORD *pflStyleDefault  - Return for the default styles.
                    730: *   BOOL *pfWriteText       - Return for the "Write Text" flag.  This will
                    731: *                             be TRUE if this control has a text field.
                    732: *   BOOL *pfNotFound        - Return for the "Not Found" flag.  This will
                    733: *                             be TRUE if no match was found and the "CONTROL"
                    734: *                             keyword was defaulted to.
                    735: *
                    736: * Returns:
                    737: *   A pointer to the control keyword to use.
                    738: *   If a match was found, *pflStylePredef is set to the bits for the match.
                    739: *       If not found, this is set to zero.
                    740: *   The default style bits for this keyword will be returned.
                    741: *   The "Write Text" flag will be set.
                    742: *   The "Not Found" flag will be set.
                    743: *
                    744: ************************************************************************/
                    745: 
                    746: STATICFN LPTSTR GetControlKeyword(
                    747:     INT iClass,
                    748:     DWORD flStyle,
                    749:     DWORD *pflStylePredef,
                    750:     DWORD *pflStyleDefault,
                    751:     BOOL *pfWriteText,
                    752:     BOOL *pfNotFound)
                    753: {
                    754:     register INT i;
                    755:     INT iMax;
                    756:     PRCKEYWORD prckwd;
                    757: 
                    758:     if (gfUseNewKeywords && iClass != IC_UNKNOWN) {
                    759:         iMax = acsd[iClass].cKeywords;
                    760:         prckwd = acsd[iClass].parckwd;
                    761: 
                    762:         /*
                    763:          * Loop through all the keywords for this class.
                    764:          */
                    765:         for (i = 0; i < iMax; i++, prckwd++) {
                    766:             /*
                    767:              * Does the style (masked) exactly match the keywords style?
                    768:              */
                    769:             if ((flStyle & prckwd->flStyleMask) == prckwd->flStyle) {
                    770:                 /*
                    771:                  * Yes.  Set the "Has Text" flag, we did find a match,
                    772:                  * put the found bits in the predefined style flag,
                    773:                  * set the default styles flag and return the found
                    774:                  * keyword.
                    775:                  */
                    776:                 *pfWriteText = prckwd->fHasText;
                    777:                 *pfNotFound = FALSE;
                    778:                 *pflStylePredef = prckwd->flStyle;
                    779:                 *pflStyleDefault = prckwd->flStyleDefault;
                    780:                 return ids(prckwd->idsKeyword);
                    781:             }
                    782:         }
                    783:     }
                    784: 
                    785:     /*
                    786:      * A match was not found.  We must write text, we didn't find a
                    787:      * match, we will be using the "CONTROL" keyword and the default
                    788:      * styles that this keyword implies is the "child" and "visible"
                    789:      * bits (rc.exe OR's these styles in implicitly).
                    790:      */
                    791:     *pfWriteText = TRUE;
                    792:     *pfNotFound = TRUE;
                    793:     *pflStylePredef = 0L;
                    794:     *pflStyleDefault = WS_VISIBLE | WS_CHILD;
                    795:     return ids(IDS_CONTROL);
                    796: }
                    797: 
                    798: 
                    799: 
                    800: /************************************************************************
                    801: * WriteClass
                    802: *
                    803: * Writes out the class for a control.
                    804: *
                    805: * Arguments:
                    806: *    LPTSTR pszClass - pointer to the class string
                    807: *
                    808: ************************************************************************/
                    809: 
                    810: STATICFN VOID WriteClass(
                    811:     LPTSTR pszClass)
                    812: {
                    813:     INT i;
                    814:     WORD idOrd;
                    815: 
                    816:     Comma();
                    817: 
                    818:     /*
                    819:      * Is this class a predefined type instead of a string?
                    820:      */
                    821:     if (IsOrd(pszClass)) {
                    822:         /*
                    823:          * Figure out which type it is and get the class string to
                    824:          * write.
                    825:          */
                    826:         idOrd = OrdID(pszClass);
                    827:         for (i = 0; i < IC_DIALOG; i++) {
                    828:             if (acsd[i].idOrd == idOrd) {
                    829:                 pszClass = ids(acsd[i].idsClass);
                    830:                 break;
                    831:             }
                    832:         }
                    833:     }
                    834: 
                    835:     WriteQuotedString(pszClass);
                    836: }
                    837: 
                    838: 
                    839: 
                    840: /************************************************************************
                    841: * WriteStyles
                    842: *
                    843: * This function writes the class and style info to the file
                    844: * for the control or dialog box in the RC format.
                    845: *
                    846: * Arguments:
                    847: *     INT iClass           = The class of the item.
                    848: *     LPTSTR pszClass      = Class name of the control.
                    849: *     DWORD flStyle        = The style of the item.
                    850: *     DWORD flStylePredef  = The styles bits implicit in the predefined
                    851: *                            keyword for this control.  This should be
                    852: *                            zero if this control doesn't have a predefined
                    853: *                            keyword for it.
                    854: *     DWORD flStyleDefault = The default styles implicit in the item.
                    855: *     PDWORD pflStyleLeft  = Where to  return any style bits that do not
                    856: *                            get written out.
                    857: *     BOOL fNullStyles     = TRUE if we should still write the style word
                    858: *                            even if the style flag is zero.
                    859: *     BOOL fCommaPrefix    = TRUE means that a comma will be written out
                    860: *                            before writing any styles.  If no styles
                    861: *                            are written, no comma will be written either.
                    862: *
                    863: * Returns:
                    864: *     TRUE => Something was written out.
                    865: *     FALSE => Nothing was written out.
                    866: *
                    867: ************************************************************************/
                    868: 
                    869: STATICFN BOOL WriteStyles(
                    870:     INT iClass,
                    871:     LPTSTR pszClass,
                    872:     DWORD flStyle,
                    873:     DWORD flStylePredef,
                    874:     DWORD flStyleDefault,
                    875:     PDWORD pflStyleLeft,
                    876:     BOOL fNullStyles,
                    877:     BOOL fCommaPrefix)
                    878: {
                    879:     DWORD flStyleLeft;
                    880:     BOOL fWritten = FALSE;
                    881: 
                    882:     /*
                    883:      * Write the control specific styles.
                    884:      */
                    885:     if (iClass == IC_CUSTOM) {
                    886:         fWritten = WriteCustomStyle(pszClass, flStyle, &flStyleLeft);
                    887:     }
                    888:     else {
                    889:         fWritten = WriteClassStyle(iClass, flStyle, flStylePredef,
                    890:                 flStyleDefault, &flStyleLeft, FALSE, fNullStyles,
                    891:                 fCommaPrefix);
                    892:     }
                    893: 
                    894:     /*
                    895:      * If we are writing styles for the dialog, remove the WS_GROUP
                    896:      * and WS_TABSTOP bits from the style before proceeding.  This is
                    897:      * because the WS_MINIMIZEBOX and WS_MAXIMIZEBOX styles use the
                    898:      * same bits, and these keywords will have already been written
                    899:      * out by the preceding WriteClassStyle call if those bits are
                    900:      * present.
                    901:      */
                    902:     if (iClass == IC_DIALOG)
                    903:         flStyle &= ~(WS_GROUP | WS_TABSTOP);
                    904: 
                    905:     /*
                    906:      * Write the window styles that are common to the different
                    907:      * controls (the high word).
                    908:      */
                    909:     fWritten |= WriteClassStyle(IC_WINDOW, flStyleLeft, flStylePredef,
                    910:             flStyleDefault, &flStyleLeft, fWritten, fNullStyles, fCommaPrefix);
                    911: 
                    912:     /*
                    913:      * Pass back any styles that were not written.
                    914:      */
                    915:     *pflStyleLeft = flStyleLeft;
                    916: 
                    917:     return fWritten;
                    918: }
                    919: 
                    920: 
                    921: 
                    922: /************************************************************************
                    923: * WriteClassStyle
                    924: *
                    925: * This function writes the class style symbols to the file.  The styles
                    926: * to write out are passed in flStyle, and the styles that are implicitly
                    927: * set by this type of control already are passed in flStyleDefault.  The
                    928: * style keywords corresponding to the bits in flStyle are written out,
                    929: * separated by " | ", and any bits in flStyleDefault that are NOT set
                    930: * are written out preceded by a "NOT" to explicitly turn them off.  This
                    931: * is used in the case of the predefined RC keywords, which often have
                    932: * styles like WS_TABSTOP or WS_VISIBLE already implicit in them.  There
                    933: * is no need to explicitly specify them, but if they are not present, we
                    934: * must NOT them out.  The parameter flStylePredef contains the style bits
                    935: * that identified the predefined control keyword itself (if any) and
                    936: * thus are removed from the style before writing anything out.
                    937: *
                    938: * Arguments:
                    939: *     INT iClass           = The class of the control. See the
                    940: *                            IC_ constants defined in dlgedit.h.
                    941: *     DWORD flStyle        = The style of control.  This nails
                    942: *                            down the exact type of control.
                    943: *     DWORD flStylePredef  = The styles bits implicit in the predefined
                    944: *                            keyword for this control.  This should be
                    945: *                            zero if this control doesn't have a predefined
                    946: *                            keyword for it.
                    947: *     DWORD flStyleDefault = The default styles that are implicit with
                    948: *                            this control.  This will only be set if this
                    949: *                            control is using a predefined RC keyword. A
                    950: *                            value of zero means that there are no default
                    951: *                            styles implicitly specified.
                    952: *     PDWORD pflStyleLeft  = Where to  return any style bits that do not
                    953: *                            get written out.
                    954: *     BOOL fPrevWritten    = TRUE means a previous style symbol has
                    955: *                            been written and to put " | " before
                    956: *                            the next symbol.
                    957: *     BOOL fNullStyles     = TRUE if we should still write the style word
                    958: *                            even if the style flag is zero.  This is used
                    959: *                            to handle the case where a predefined keyword
                    960: *                            has been written out that implies a style that
                    961: *                            also happens to be zero.  Without this flag
                    962: *                            being FALSE the style flag implicit in the
                    963: *                            keyword would be redundantly written out again.
                    964: *                            In general, if we have written out a predefined
                    965: *                            keyword this flag should be FALSE.
                    966: *     BOOL fCommaPrefix    = TRUE means that a comma will be written out
                    967: *                            before writing any styles.  This will only
                    968: *                            happen if fPrevWritten is FALSE.  If no styles
                    969: *                            are written, no comma will be written either.
                    970: *
                    971: * Returns:
                    972: *     TRUE => Something was written out.
                    973: *     FALSE => Nothing was written out.
                    974: *
                    975: ************************************************************************/
                    976: 
                    977: STATICFN BOOL WriteClassStyle(
                    978:     INT iClass,
                    979:     DWORD flStyle,
                    980:     DWORD flStylePredef,
                    981:     DWORD flStyleDefault,
                    982:     PDWORD pflStyleLeft,
                    983:     BOOL fPrevWritten,
                    984:     BOOL fNullStyles,
                    985:     BOOL fCommaPrefix)
                    986: {
                    987:     register WORD i;
                    988:     WORD iMax;
                    989:     DWORD flStyleMask;
                    990:     PCLASSSTYLE pcs;
                    991: 
                    992:     iMax = (WORD)acsd[iClass].cClassStyles;
                    993:     pcs = acsd[iClass].pacs;
                    994: 
                    995:     /*
                    996:      * Remove the bits that identified the predefined control keyword
                    997:      * from the style flag before proceeding.  For instance, if I already
                    998:      * am going to be writing out a "PUSHBUTTON", there is no reason
                    999:      * to write out the "BS_PUSHBUTTON" style.  If there is no predefined
                   1000:      * control keyword, flStylePredef will be zero and this will do
                   1001:      * nothing.
                   1002:      */
                   1003:     flStyle &= ~flStylePredef;
                   1004: 
                   1005:     /*
                   1006:      * Go through all possible flags for this style.
                   1007:      */
                   1008:     for (i = 0; i < iMax; i++, pcs++) {
                   1009:         flStyleMask = pcs->flStyleMask ? pcs->flStyleMask : pcs->flStyle;
                   1010: 
                   1011:         /*
                   1012:          * Is this styles bits set?
                   1013:          */
                   1014:         if ((flStyle & flStyleMask) == pcs->flStyle) {
                   1015:             /*
                   1016:              * Remove these bits from the styles left.  Even if
                   1017:              * we do not write them out, they are still accounted
                   1018:              * for and can be removed from the styles remaining.
                   1019:              */
                   1020:             flStyle &= ~pcs->flStyle;
                   1021: 
                   1022:             /*
                   1023:              * Skip this style if we don't want to write styles that are
                   1024:              * zero, or if the style is already implicitly specified for
                   1025:              * this control (a non-zero default style mask must be specified).
                   1026:              */
                   1027:             if ((!pcs->flStyle && !fNullStyles) ||
                   1028:                     (flStyleDefault &&
                   1029:                     (flStyleDefault & flStyleMask) == pcs->flStyle))
                   1030:                 continue;
                   1031: 
                   1032:             /*
                   1033:              * If there is a string for this style, write it out, preceded
                   1034:              * by an "|" symbol if necessary.
                   1035:              */
                   1036:             if (*ids(acsd[iClass].idsStylesStart + i)) {
                   1037:                 if (fPrevWritten) {
                   1038:                     ORSymbol();
                   1039:                 }
                   1040:                 else {
                   1041:                     if (fCommaPrefix)
                   1042:                         Comma();
                   1043: 
                   1044:                     fPrevWritten = TRUE;
                   1045:                 }
                   1046: 
                   1047:                 /*
                   1048:                  * Write the string.
                   1049:                  */
                   1050:                 WriteString(ids(acsd[iClass].idsStylesStart + i));
                   1051:             }
                   1052:         }
                   1053:         /*
                   1054:          * No the styles bit is not set.  Is it implicit in the keyword
                   1055:          * being used?  If so, we need to explicitly NOT it
                   1056:          * out in the dialog template.
                   1057:          * Note that this should not be done in the case where the style
                   1058:          * is zero.
                   1059:          */
                   1060:         else if (flStyleDefault &&
                   1061:                 (flStyleDefault & flStyleMask) == pcs->flStyle &&
                   1062:                 pcs->flStyle) {
                   1063:             if (fPrevWritten) {
                   1064:                 ORSymbol();
                   1065:             }
                   1066:             else {
                   1067:                 if (fCommaPrefix)
                   1068:                     Comma();
                   1069: 
                   1070:                 fPrevWritten = TRUE;
                   1071:             }
                   1072: 
                   1073:             WriteString(ids(IDS_NOT));
                   1074:             Space();
                   1075:             WriteString(ids(acsd[iClass].idsStylesStart + i));
                   1076:         }
                   1077:     }
                   1078: 
                   1079:     /*
                   1080:      * Pass back the style bits that were not written out.
                   1081:      */
                   1082:     *pflStyleLeft = flStyle;
                   1083: 
                   1084:     return fPrevWritten;
                   1085: }
                   1086: 
                   1087: 
                   1088: 
                   1089: /************************************************************************
                   1090: * WriteCustomStyle
                   1091: *
                   1092: * Writes our the custom control information
                   1093: *
                   1094: * Arguments:
                   1095: *    LPTSTR - class name of the control
                   1096: *    DWORD - style of the control
                   1097: *    PDWORD - styles left to be written
                   1098: *
                   1099: * Returns:
                   1100: *    TRUE if custom styles were written out; otherwise, FALSE.
                   1101: *
                   1102: ************************************************************************/
                   1103: 
                   1104: STATICFN BOOL WriteCustomStyle(
                   1105:     LPTSTR pszClass,
                   1106:     DWORD flStyle,
                   1107:     PDWORD pflStyleLeft)
                   1108: {
                   1109:     PCUSTLINK pcl;
                   1110:     LPCCSTYLEFLAG pStyleFlags;
                   1111:     DWORD flStyleMask;
                   1112:     INT i;
                   1113:     BOOL fWritten = FALSE;
                   1114: 
                   1115:     /*
                   1116:      * Search the list of installed custom controls for one
                   1117:      * that matches the class.
                   1118:      */
                   1119:     for (pcl = gpclHead;
                   1120:             pcl && lstrcmpi(pcl->pwcd->pszClass, pszClass) != 0;
                   1121:             pcl = pcl->pclNext)
                   1122:         ;
                   1123: 
                   1124:     /*
                   1125:      * Was a match found and is this control from a DLL (not emulated)?
                   1126:      */
                   1127:     if (pcl && !pcl->pwcd->fEmulated) {
                   1128:         for (i = 0, pStyleFlags = pcl->pwcd->aStyleFlags;
                   1129:                 i < pcl->pwcd->cStyleFlags;
                   1130:                 i++, pStyleFlags++) {
                   1131:             flStyleMask = pStyleFlags->flStyleMask ?
                   1132:                     pStyleFlags->flStyleMask : pStyleFlags->flStyle;
                   1133: 
                   1134:             /*
                   1135:              * Is this styles bits set?
                   1136:              */
                   1137:             if ((flStyle & flStyleMask) == pStyleFlags->flStyle) {
                   1138:                 /*
                   1139:                  * Remove these bits from the styles left.
                   1140:                  */
                   1141:                 flStyle &= ~pStyleFlags->flStyle;
                   1142: 
                   1143:                 if (fWritten)
                   1144:                     ORSymbol();
                   1145:                 else
                   1146:                     fWritten = TRUE;
                   1147: 
                   1148:                 /*
                   1149:                  * Write the string.
                   1150:                  */
                   1151:                 WriteString(pStyleFlags->pszStyle);
                   1152:             }
                   1153:         }
                   1154:     }
                   1155: 
                   1156:     /*
                   1157:      * Return the styles that remain to be written.
                   1158:      */
                   1159:     *pflStyleLeft = flStyle;
                   1160: 
                   1161:     return fWritten;
                   1162: }
                   1163: 
                   1164: 
                   1165: 
                   1166: /************************************************************************
                   1167: * WriteCoords
                   1168: *
                   1169: * This function writes the coordinates out to the file as decimal
                   1170: * ascii numbers separated by ", ".
                   1171: *
                   1172: * Arguments:
                   1173: *     INT x, y, cx, cy = The coordinates.
                   1174: *
                   1175: ************************************************************************/
                   1176: 
                   1177: STATICFN VOID WriteCoords(
                   1178:     INT x,
                   1179:     INT y,
                   1180:     INT cx,
                   1181:     INT cy)
                   1182: {
                   1183:     WriteValue(x);
                   1184:     Comma();
                   1185:     WriteValue(y);
                   1186:     Comma();
                   1187:     WriteValue(cx);
                   1188:     Comma();
                   1189:     WriteValue(cy);
                   1190: }
                   1191: 
                   1192: 
                   1193: 
                   1194: /************************************************************************
                   1195: * WriteValue
                   1196: *
                   1197: * This function writes the value of 'n' as a decimal ascii string to
                   1198: * the file.
                   1199: *
                   1200: * Arguments:
                   1201: *     INT n = The number to write.
                   1202: *
                   1203: ************************************************************************/
                   1204: 
                   1205: STATICFN VOID WriteValue(
                   1206:     INT n)
                   1207: {
                   1208:     TCHAR szNum[32];
                   1209: 
                   1210:     itoaw(n, szNum, 10);
                   1211:     WriteString(szNum);
                   1212: }
                   1213: 
                   1214: 
                   1215: 
                   1216: /************************************************************************
                   1217: * WriteHexWord
                   1218: *
                   1219: * This function writes the value of 'w' as a hex constant to the file.
                   1220: *
                   1221: * Arguments:
                   1222: *     WORD w - The word to write.
                   1223: *
                   1224: ************************************************************************/
                   1225: 
                   1226: STATICFN VOID WriteHexWord(
                   1227:     WORD w)
                   1228: {
                   1229:     TCHAR szNum[17];
                   1230: 
                   1231:     itoax(w, szNum);
                   1232:     WriteString(szNum);
                   1233: }
                   1234: 
                   1235: 
                   1236: 
                   1237: /************************************************************************
                   1238: * WriteHexDWord
                   1239: *
                   1240: * This function writes the value of 'dw' as a hex constant to the file.
                   1241: *
                   1242: * Arguments:
                   1243: *     DWORD dw - The dword to write.
                   1244: *
                   1245: ************************************************************************/
                   1246: 
                   1247: STATICFN VOID WriteHexDWord(
                   1248:     DWORD dw)
                   1249: {
                   1250:     TCHAR szNum[32];
                   1251: 
                   1252:     wsprintf(szNum, L"0x%8.8X", dw);
                   1253:     WriteString(szNum);
                   1254: }
                   1255: 
                   1256: 
                   1257: 
                   1258: /************************************************************************
                   1259: * WriteString
                   1260: *
                   1261: * This function writes the given string to the file.  If the string
                   1262: * would cause it to overflow the margin, a new line, with indenting
                   1263: * to the current tab level, is forced before writing the string.
                   1264: *
                   1265: * Arguments:
                   1266: *   LPTSTR psz = The string to write out.
                   1267: *
                   1268: ************************************************************************/
                   1269: 
                   1270: STATICFN VOID WriteString(
                   1271:     LPTSTR psz)
                   1272: {
                   1273:     register INT nLen;
                   1274: 
                   1275:     nLen = lstrlen(psz);
                   1276: 
                   1277:     if (!AtFirstTabColumn() && cColumn + nLen > CCHRIGHTMARGIN)
                   1278:         NewLine();
                   1279: 
                   1280:     while (nLen--)
                   1281:         WriteDlgChar(*psz++);
                   1282: }
                   1283: 
                   1284: 
                   1285: 
                   1286: /************************************************************************
                   1287: * WriteQuotedString
                   1288: *
                   1289: * This function writes the given string to the file.  If the string
                   1290: * would cause it to overflow the margin, a new line, with indenting
                   1291: * to the current tab level, is forced before writing the string.
                   1292: * This function will also enclose the given string in double-quotes,
                   1293: * and ensures that the string will not be broken when it is written.
                   1294: * If there are any escape characters (backslashes or quotes) in the
                   1295: * string, they will be escaped properly so that rc.exe can read them
                   1296: * properly.
                   1297: *
                   1298: * Arguments:
                   1299: *   LPTSTR psz = The string to write out.
                   1300: *
                   1301: ************************************************************************/
                   1302: 
                   1303: STATICFN VOID WriteQuotedString(
                   1304:     LPTSTR psz)
                   1305: {
                   1306:     register INT nLen;
                   1307:     LPTSTR pszT;
                   1308: 
                   1309:     /*
                   1310:      * Find the actual length of the string.  To do this, we must scan
                   1311:      * for the characters that will be escaped later.
                   1312:      */
                   1313:     nLen = lstrlen(psz);
                   1314:     pszT = psz;
                   1315:     while (*pszT) {
                   1316:         if (*pszT == CHAR_DBLQUOTE || *pszT == CHAR_BACKSLASH)
                   1317:             nLen++;
                   1318: 
                   1319:         pszT++;
                   1320:     }
                   1321: 
                   1322:     /*
                   1323:      * Start a new line if necessary.  Add 2 for the quotes.
                   1324:      */
                   1325:     if (!AtFirstTabColumn() && cColumn + nLen + 2 > CCHRIGHTMARGIN)
                   1326:         NewLine();
                   1327: 
                   1328:     Quote();
                   1329:     WriteEscapedString(psz);
                   1330:     Quote();
                   1331: }
                   1332: 
                   1333: 
                   1334: 
                   1335: /************************************************************************
                   1336: * WriteEscapedString
                   1337: *
                   1338: * This function writes the given string to the file.  It is different
                   1339: * from WriteString in that it will add a '\' in front of other
                   1340: * backslashes and a second double quote in front of double quotes.
                   1341: * This is necessary when writing out a string which will be surrounded
                   1342: * by quotes, such as the Text fields in the .DLG file.
                   1343: *
                   1344: * Arguments:
                   1345: *   LPTSTR psz = The string to write out.
                   1346: *
                   1347: ************************************************************************/
                   1348: 
                   1349: STATICFN VOID WriteEscapedString(
                   1350:     LPTSTR psz)
                   1351: {
                   1352:     while (*psz) {
                   1353:         if (*psz == CHAR_DBLQUOTE)
                   1354:             WriteDlgChar(CHAR_DBLQUOTE);
                   1355:         else if (*psz == CHAR_BACKSLASH)
                   1356:             WriteDlgChar(CHAR_BACKSLASH);
                   1357: 
                   1358:         WriteDlgChar(*psz++);
                   1359:     }
                   1360: }
                   1361: 
                   1362: 
                   1363: 
                   1364: /************************************************************************
                   1365: * WriteDlgChar
                   1366: *
                   1367: * Low level function to do an actual character write to the file.
                   1368: * Some buffering is done then _lwrite is called.
                   1369: *
                   1370: * Because it is buffered, before closing the file any remaining
                   1371: * characters in the buffer must be flushed to disk using WriteDlgFlush.
                   1372: *
                   1373: * If an error occurs on the write, Throw will be called to jump back
                   1374: * up to WriteDlg and return the failure to the caller.
                   1375: *
                   1376: * The globals gachWriteBuffer and cbWritePos are updated by this routine.
                   1377: *
                   1378: * Arguments:
                   1379: *     TCHAR ch - The character to write.
                   1380: *
                   1381: * Returns:
                   1382: *   If an error occurs on the _lwrite, the execution will be thrown
                   1383: *   back to the WriteDlg function.  Otherwise, nothing is returned.
                   1384: *
                   1385: ************************************************************************/
                   1386: 
                   1387: STATICFN VOID WriteDlgChar(
                   1388:     TCHAR ch)
                   1389: {
                   1390:     INT cbWritten;
                   1391: 
                   1392:     gachWriteBuffer[cbWritePos++] = ch;
                   1393: 
                   1394:     /*
                   1395:      * Is the buffer full?
                   1396:      */
                   1397:     if (cbWritePos == CCHFILEBUFFER) {
                   1398:         CHAR abWriteBuffer[CCHFILEBUFFER];
                   1399:         BOOL fDefCharUsed;
                   1400: 
                   1401:         WideCharToMultiByte(CP_ACP, 0, gachWriteBuffer, CCHFILEBUFFER,
                   1402:                 abWriteBuffer, CCHFILEBUFFER, NULL, &fDefCharUsed);
                   1403: 
                   1404:         cbWritten = (INT)_lwrite((HFILE)hfDlg, abWriteBuffer, cbWritePos);
                   1405:         if (cbWritten != cbWritePos)
                   1406:             longjmp(jbWriteDlg, 1);
                   1407: 
                   1408:         cbWritePos = 0;
                   1409:     }
                   1410: 
                   1411:     /*
                   1412:      * Update the current column counter.
                   1413:      */
                   1414:     if (ch == CHAR_RETURN || ch == CHAR_NEWLINE) {
                   1415:         /*
                   1416:          * Carriage return or newline resets column position to 0.
                   1417:          */
                   1418:         cColumn = 0;
                   1419:     }
                   1420:     else {
                   1421:         cColumn++;
                   1422:     }
                   1423: }
                   1424: 
                   1425: 
                   1426: 
                   1427: /************************************************************************
                   1428: * WriteDlgFlush
                   1429: *
                   1430: * This routine flushes the write buffer.  This must be done before
                   1431: * the file is closed or data can be lost.
                   1432: *
                   1433: * The global cbWritePos is updated by this routine.
                   1434: *
                   1435: * Returns:
                   1436: *   If an error occurs on the _lwrite, the execution will be thrown
                   1437: *   back to the WriteDlg function.  Otherwise, nothing is returned.
                   1438: *
                   1439: ************************************************************************/
                   1440: 
                   1441: STATICFN VOID WriteDlgFlush(VOID)
                   1442: {
                   1443:     INT cbWritten;
                   1444: 
                   1445:     /*
                   1446:      * Are any bytes remaining in the buffer?
                   1447:      */
                   1448:     if (cbWritePos) {
                   1449:         CHAR abWriteBuffer[CCHFILEBUFFER];
                   1450:         BOOL fDefCharUsed;
                   1451: 
                   1452:         WideCharToMultiByte(CP_ACP, 0, gachWriteBuffer, cbWritePos,
                   1453:                 abWriteBuffer, CCHFILEBUFFER, NULL, &fDefCharUsed);
                   1454: 
                   1455:         cbWritten = (INT)_lwrite((HFILE)hfDlg, abWriteBuffer, cbWritePos);
                   1456:         if (cbWritten != cbWritePos)
                   1457:             longjmp(jbWriteDlg, 1);
                   1458: 
                   1459:         cbWritePos = 0;
                   1460:     }
                   1461: }
                   1462: 
                   1463: 
                   1464: 
                   1465: /****************************************************************************
                   1466: * Tab
                   1467: *
                   1468: * Writes spaces up to the current tab level setting.
                   1469: *
                   1470: ****************************************************************************/
                   1471: 
                   1472: STATICFN VOID Tab(VOID)
                   1473: {
                   1474:     while (cColumn < cTabStop)
                   1475:         WriteDlgChar(CHAR_SPACE);
                   1476: }
                   1477: 
                   1478: 
                   1479: 
                   1480: /****************************************************************************
                   1481: * NewLine
                   1482: *
                   1483: * Begins a new line by writing a carriage return and linefeed.  Also
                   1484: * indents the following line up to the current tab level.
                   1485: *
                   1486: ****************************************************************************/
                   1487: 
                   1488: STATICFN VOID NewLine(VOID)
                   1489: {
                   1490:     WriteDlgChar(CHAR_RETURN);
                   1491:     WriteDlgChar(CHAR_NEWLINE);
                   1492:     Tab();
                   1493: }
                   1494: 
                   1495: 
                   1496: 
                   1497: /****************************************************************************
                   1498: * Quote
                   1499: *
                   1500: * Writes a double quote.
                   1501: *
                   1502: ****************************************************************************/
                   1503: 
                   1504: STATICFN VOID Quote(VOID)
                   1505: {
                   1506:     WriteDlgChar(CHAR_DBLQUOTE);
                   1507: }
                   1508: 
                   1509: 
                   1510: 
                   1511: /****************************************************************************
                   1512: * Comma
                   1513: *
                   1514: * Writes a comma then a space.
                   1515: *
                   1516: ****************************************************************************/
                   1517: 
                   1518: STATICFN VOID Comma(VOID)
                   1519: {
                   1520:     WriteDlgChar(CHAR_COMMA);
                   1521:     WriteDlgChar(CHAR_SPACE);
                   1522: }
                   1523: 
                   1524: 
                   1525: 
                   1526: /****************************************************************************
                   1527: * Space
                   1528: *
                   1529: * Writes a space.
                   1530: *
                   1531: ****************************************************************************/
                   1532: 
                   1533: STATICFN VOID Space(VOID)
                   1534: {
                   1535:     WriteDlgChar(CHAR_SPACE);
                   1536: }
                   1537: 
                   1538: 
                   1539: 
                   1540: /****************************************************************************
                   1541: * ORSymbol
                   1542: *
                   1543: * Writes " | ".
                   1544: *
                   1545: ****************************************************************************/
                   1546: 
                   1547: STATICFN VOID ORSymbol(VOID)
                   1548: {
                   1549:     WriteDlgChar(CHAR_SPACE);
                   1550:     WriteDlgChar(CHAR_ORSYMBOL);
                   1551:     WriteDlgChar(CHAR_SPACE);
                   1552: }

unix.superglobalmegacorp.com

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