⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 complist.c

📁 <Win2k系统编程>源码.次数为国人自编,内容丰富,还是不错的.
💻 C
📖 第 1 页 / 共 3 页
字号:


/****************************** Module Header *******************************
* Module Name: COMPLIST.C
*
* Supports a list of compitems, where each compitem represents
* a pair of matching files, or an unmatched file.
*
* Functions:
*
* complist_filedialog()
* complist_dirdialog()
* complist_args()
* complist_getitems()
* complist_delete()
* complist_savelist()
* complist_copyfiles()
* complist_dodlg_savelist()
* complist_dodlg_copyfiles()
* complist_match()
* complist_new()
* complist_dodlg_dir()
*
* Comments:
*
* We build lists of filenames from two pathnames (using the
* scandir module) and then traverse the two lists comparing names.
* Where the names match, we create a CompItem from the matching
* names. Where there is an unmatched name, we create a compitem for it.
*
* We may also be asked to create a complist for two individual files:
* here we create a single compitem for them as a matched pair even if
* the names don't match.
*
****************************************************************************/

#include <windows.h>
#include <stdlib.h>
#include <string.h>
#include <dos.h>
#include <direct.h>

#include "gutils.h"
#include "state.h"
#include "windiff.h"
#include "wdiffrc.h"
#include "list.h"
#include "line.h"
#include "scandir.h"
#include "file.h"
#include "section.h"
#include "compitem.h"
#include "complist.h"
#include "view.h"


extern BOOL bAbort;             /* defined in windiff.c  Read only here */

/*
 * The COMPLIST handle is typedef-ed to be a pointer to one
 * of these struct complist
 */
struct complist {
        DIRLIST left;           /* left list of files */
        DIRLIST right;          /* right list of files */
        LIST items;             /* list of COMPITEMs */
};

/* ---- module-wide data -------------------------------------*/

/* data for communicating between the SaveList dlg and complist_savelist() */

char dlg_file[256];                /* filename to save to */

/* checkbox options */
BOOL dlg_identical, dlg_differ, dlg_left, dlg_right;
BOOL dlg_recursive = FALSE;

/* data for Directory and SaveList */
char dialog_leftname[256];
char dialog_rightname[256];

/*
 * data used by dodlg_copyfiles
 */
UINT dlg_options;
char dlg_root[256];

/*------------------------timing for performance measurements-----------------*/

static DWORD TickCount;         /* time operation started, then time taken*/


int FAR PASCAL complist_dodlg_savelist(HWND hDlg, UINT message,
        UINT wParam, long lParam);
int FAR PASCAL complist_dodlg_copyfiles(HWND hDlg, UINT message,
        UINT wParam, long lParam);
BOOL complist_match(COMPLIST cl, VIEW view, BOOL fDeep, BOOL fExact);
COMPLIST complist_new(void);
int FAR PASCAL complist_dodlg_dir(HWND hDlg, unsigned message,
        WORD wParam, LONG lParam);



/***************************************************************************
 * Function: complist_filedialog
 *
 * Purpose:
 *
 * Builds a complist by putting up two dialogs to allow the user to
 * select two files. This will build a Complist with one CompItem (even
 * if the names don't match).
 *
 ***************************************************************************/
COMPLIST
complist_filedialog(VIEW view)
{
        COMPLIST cl;
        OFSTRUCT os1, os2;
        char fname[256], FileExt[256], FileOpenSpec[256];

        /* ask for the filenames */
        lstrcpy(FileExt, ".c");
        lstrcpy(FileOpenSpec, "*.*");
        lstrcpy(fname,"");

        if (!complist_open(LoadRcString(IDS_SELECT_FIRST_FILE), FileExt, FileOpenSpec,
                        &os1, fname) )
                return(NULL);

        lstrcpy(FileExt, ".c");
        lstrcpy(FileOpenSpec, "*.*");
        lstrcpy(fname,"");

        if (!complist_open(LoadRcString(IDS_SELECT_SECOND_FILE), FileExt, FileOpenSpec,
                        &os2, fname) )
                return(NULL);

        /* alloc a new structure */
        cl = complist_new();

        cl->left = dir_buildlist(os1.szPathName, TRUE);
        cl->right = dir_buildlist(os2.szPathName, TRUE);


        /* register with the view (must be done after the list is non-null) */
        view_setcomplist(view, cl);

        complist_match(cl, view, FALSE, TRUE);

        return(cl);
}/* complist_filedialog */

/***************************************************************************
 * Function: complist_dirdialog
 *
 * Purpose:
 *
 * Builds a new complist by querying the user for two directory
 * names and scanning those in parallel.
 *
 * Names that match in the same directory will be paired - unmatched
 * names will go in a compitem on their own.
 *
 ***************************************************************************/
COMPLIST
complist_dirdialog(VIEW view)
{
        DLGPROC lpProc;
        BOOL fOK;

        /* put up a dialog for the two pathnames */
        lpProc = (DLGPROC)MakeProcInstance((WNDPROC)complist_dodlg_dir, hInst);
        windiff_UI(TRUE);
        fOK = DialogBox(hInst, "Directory", hwndClient, lpProc);
        windiff_UI(FALSE);
        FreeProcInstance(lpProc);

        if (!fOK) {
                return(NULL);
        }

        return complist_args( dialog_leftname, dialog_rightname
                            , view, dlg_recursive);
} /* complist_dirdialog */


/***************************************************************************
 * Function: complist_args
 *
 * Purpose:
 *
 * Given two pathname strings, scan the directories and traverse them
 * in parallel comparing matching names.
 *
 ***************************************************************************/
COMPLIST
complist_args(LPSTR p1, LPSTR p2, VIEW view, BOOL fDeep)
{
        COMPLIST cl;
        char msg[256];


        /* alloc a new complist */
        cl = complist_new();

        cl->left = dir_buildlist(p1, TRUE);
        /* check that we could find the paths, and report if not */
        if (cl->left == NULL) {
                wsprintf((LPTSTR)msg, LoadRcString(IDS_COULDNT_FIND), p1);
                MessageBox(NULL, msg, NULL, MB_OK | MB_ICONSTOP);
                return(NULL);
        }

        cl->right = dir_buildlist(p2, TRUE);
        if (cl->right == NULL) {
                wsprintf((LPTSTR)msg, LoadRcString(IDS_COULDNT_FIND), p2);
                MessageBox(NULL, msg, NULL, MB_OK | MB_ICONSTOP);
                return(NULL);
        }

        /* register with the view (must be done after building lists) */
        view_setcomplist(view, cl);

        complist_match(cl, view, fDeep, TRUE);

        return(cl);
} /* complist_args */

/***************************************************************************
 * Function: complist_getitems
 *
 * Purpose:
 *
 * Gets the handle to the list of COMPITEMs. The list continues to be
 * owned by the COMPLIST, so don't delete except by calling complist_delete.
 *
 ***************************************************************************/
LIST
complist_getitems(COMPLIST cl)
{
        if (cl == NULL) {
                return(NULL);
        }

        return(cl->items);
}

/***************************************************************************
 * Function: complist_delete
 *
 * Purpose:
 *
 * Deletes a complist and all associated CompItems and DIRLISTs. Note this
 * does not delete any VIEW - the VIEW owns the COMPLIST and not the other
 * way around.
 *
 **************************************************************************/
void
complist_delete(COMPLIST cl)
{
        COMPITEM item;

        if (cl == NULL) {
                return;
        }

        /* delete the two directory scan lists */
        dir_delete(cl->left);
        dir_delete(cl->right);

        /* delete the compitems in the list */
        List_TRAVERSE(cl->items, item) {
                        compitem_delete(item);
        }

        /* delete the list itself */
        List_Destroy(&cl->items);

        gmem_free(hHeap, (LPSTR) cl, sizeof(struct complist));

}

/***************************************************************************
 * Function: complist_savelist
 *
 * Purpose:
 *
 * Writes out to a text file the list of compitems as relative filenames
 * one per line.
 *
 * If savename is non-null, use this as the filename for output; otherwise,
 * query the user via a dialog for the filename and include options.
 *
 **************************************************************************/
void
complist_savelist(COMPLIST cl, LPSTR savename, UINT options)
{
        DLGPROC lpProc;
        static BOOL done_init = FALSE;
        BOOL bOK;
        int fh, state;
        OFSTRUCT os;
        char msg[256];
        HCURSOR hcurs;
        COMPITEM ci;
        LPSTR pstr, lhead, rhead;
        int nFiles = 0;

        if (!done_init) {
                /* init the options once round - but keep the same options
                 * for the rest of the session.
                 */

                /* first init default options */
                dlg_identical = FALSE;
                dlg_differ = TRUE;
                dlg_left = TRUE;
                dlg_right = FALSE;

                dlg_file[0] = '\0';

                done_init = TRUE;
        }

        if (cl == NULL) {
                return;
        }

        if (savename == NULL) {

                /* store the left and right rootnames so that dodlg_savelist
                 * can display them in the dialog.
                 */
                pstr = dir_getroot_list(cl->left);
                lstrcpy(dialog_leftname, pstr);
                dir_freeroot_list(cl->left, pstr);

                pstr = dir_getroot_list(cl->right);
                lstrcpy(dialog_rightname, pstr);
                dir_freeroot_list(cl->right, pstr);

                lpProc = (DLGPROC)MakeProcInstance((WNDPROC)complist_dodlg_savelist, hInst);
                windiff_UI(TRUE);
                bOK = DialogBox(hInst, "SaveList", hwndClient, lpProc);
                windiff_UI(FALSE);
                FreeProcInstance(lpProc);

                if (!bOK) {
                        /* user cancelled from dialog box */
                        return;
                }
                savename = dlg_file;

        } else {
                dlg_identical = (options & INCLUDE_SAME);
                dlg_differ = (options & INCLUDE_DIFFER);
                dlg_left = (options & INCLUDE_LEFTONLY);
                dlg_right = (options & INCLUDE_RIGHTONLY);
        }


        /* try to open the file */
        fh = OpenFile(savename, &os, OF_CREATE|OF_READWRITE|OF_SHARE_DENY_WRITE);
        if (fh < 0) {
                wsprintf((LPTSTR)msg, LoadRcString(IDS_CANT_OPEN), savename);
                windiff_UI(TRUE);
                MessageBox(NULL, msg, "Windiff", MB_ICONSTOP|MB_OK);
                windiff_UI(FALSE);
                return;
        }

        hcurs = SetCursor(LoadCursor(NULL, IDC_WAIT));

        /* write out the header line */
        lhead = dir_getroot_list(cl->left);
        rhead = dir_getroot_list(cl->right);
{
        TCHAR szBuf1[20],szBuf2[20],szBuf3[20],szBuf4[20];
        lstrcpy(szBuf1,(LPSTR)(dlg_identical ? LoadRcString(IDS_IDENTICAL_COMMA) : ""));
        lstrcpy(szBuf2,(LPSTR)(dlg_left ? LoadRcString(IDS_LEFT_ONLY_COMMA) : ""));
        lstrcpy(szBuf3,(LPSTR)(dlg_right ? LoadRcString(IDS_RIGHT_ONLY_COMMA) : ""));
        lstrcpy(szBuf4,(LPSTR)(dlg_differ ? LoadRcString(IDS_DIFFERING) : ""));
        wsprintf(msg, LoadRcString(IDS_HEADER_LINE_STR),
                lhead, rhead, szBuf1, szBuf2, szBuf3, szBuf4);
}
        _lwrite(fh, msg, lstrlen(msg));
        dir_freeroot_list(cl->left, lhead);
        dir_freeroot_list(cl->right, rhead);


        /* traverse the list of compitems looking for the
         * ones we are supposed to include
         */
        List_TRAVERSE(cl->items, ci) {

                /* check if files of this type are to be listed */
                state = compitem_getstate(ci);

                if ((state == STATE_SAME) && (!dlg_identical)) {
                        continue;
                } else if ((state == STATE_DIFFER) && (!dlg_differ)) {
                        continue;
                } else if ((state == STATE_FILELEFTONLY) && (!dlg_left)) {

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -