source: trunk/dll/comp.c@ 775

Last change on this file since 775 was 775, checked in by Gregg Young, 18 years ago

Minor clean up add comments re recent changes

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 74.2 KB
Line 
1
2/***********************************************************************
3
4 $Id: comp.c 775 2007-08-11 21:07:07Z gyoung $
5
6 Compare directories
7
8 Copyright (c) 1993-02 M. Kimes
9 Copyright (c) 2003, 2007 Steven H. Levine
10
11 16 Oct 02 MK Baseline
12 04 Nov 03 SHL Force window refresh after subdir toggle
13 01 Aug 04 SHL Rework lstrip/rstrip usage
14 24 May 05 SHL Rework Win_Error usage
15 24 May 05 SHL Rework for CNRITEM.szSubject
16 25 May 05 SHL Rework with ULONGLONG
17 06 Jun 05 SHL Drop unused
18 12 Jul 06 SHL Renames and comments
19 13 Jul 06 SHL Use Runtime_Error
20 26 Jul 06 SHL Drop unreachable CN_... code
21 29 Jul 06 SHL Use xfgets_bstripcr
22 15 Aug 06 SHL Turn off hide not selected on dir change
23 19 Oct 06 SHL Correct . and .. detect
24 03 Nov 06 SHL Count thread usage
25 22 Mar 07 GKY Use QWL_USER
26 29 Jul 07 SHL Use Win_Error to report container errors
27 01 Aug 07 SHL Rework to sync with CNRITEM mods
28 01 Aug 07 SHL Rework to remove vast amount of duplicate code
29 03 Aug 07 GKY Enlarged and made setable everywhere Findbuf (speed file loading)
30 06 Aug 07 SHL Move BldFullPathName here to be near primary caller
31 07 Aug 07 SHL COMP_COLLECT: Avoid collecting empty entries when nothing selected
32 06 Aug 07 GKY Reduce DosSleep times (ticket 148)
33
34
35***********************************************************************/
36
37#define INCL_DOS
38#define INCL_WIN
39#define INCL_GPI
40#define INCL_LONGLONG
41#include <os2.h>
42
43#include <stdio.h>
44#include <stdlib.h>
45#include <string.h>
46#include <ctype.h>
47#include <share.h>
48#include <io.h>
49#include <process.h> // _beginthread
50
51#include "fm3dll.h"
52#include "fm3dlg.h"
53#include "fm3str.h"
54
55#pragma alloc_text(COMPAREDIR,FillCnrsThread,FillDirList,CompNames,BldFullPathName)
56#pragma alloc_text(COMPAREDIR1,CompareDlgProc)
57#pragma alloc_text(COMPAREDIR2,SelectCnrsThread,ActionCnrThread)
58#pragma alloc_text(COMPAREFILE,CFileDlgProc,CompareFilesThread)
59#pragma alloc_text(SNAPSHOT,SnapShot,StartSnap)
60
61typedef struct
62{
63 CHAR filename[CCHMAXPATH];
64 CHAR dirname[CCHMAXPATH];
65 BOOL recurse;
66}
67SNAPSTUFF;
68
69static PSZ pszSrcFile = __FILE__;
70
71/**
72 * Build full path name in callers buffer given directory
73 * name and filename
74 * @param pszPathName points to drive/directory if not NULL
75 * @returns pointer to full path name in caller's buffer
76 * @note OK for pszFullPathName and pszPathName to point to same buffer
77 *
78 */
79
80PSZ BldFullPathName(PSZ pszFullPathName, PSZ pszPathName, PSZ pszFileName)
81{
82 UINT c = pszPathName ? strlen(pszPathName) : 0;
83 if (c > 0) {
84 memcpy(pszFullPathName, pszPathName, c);
85 if (pszFullPathName[c - 1] != '\\')
86 pszFullPathName[c++] = '\\';
87 }
88 strcpy(pszFullPathName + c, pszFileName);
89 return pszFullPathName;
90}
91
92//=== SnapShot() Write directory tree to file and recurse if requested ===
93
94static VOID SnapShot(char *path, FILE * fp, BOOL recurse)
95{
96 FILEFINDBUF4 *fb;
97 char *mask, *enddir;
98 HDIR hdir = HDIR_CREATE;
99 ULONG nm = 1;
100
101 fb = xmalloc(sizeof(FILEFINDBUF4), pszSrcFile, __LINE__);
102 if (fb) {
103 mask = xmalloc(CCHMAXPATH, pszSrcFile, __LINE__);
104 if (mask) {
105 sprintf(mask,
106 "%s%s*",
107 path, (path[strlen(path) - 1] != '\\') ? "\\" : NullStr);
108 enddir = strrchr(mask, '\\');
109 enddir++;
110 if (!DosFindFirst(mask,
111 &hdir,
112 FILE_NORMAL | FILE_DIRECTORY |
113 FILE_ARCHIVED | FILE_READONLY | FILE_HIDDEN |
114 FILE_SYSTEM,
115 fb, sizeof(FILEFINDBUF4), &nm, FIL_QUERYEASIZE)) {
116 do {
117 strcpy(enddir, fb->achName);
118 if (!(fb->attrFile & FILE_DIRECTORY))
119 fprintf(fp,
120 "\"%s\",%u,%lu,%04u/%02u/%02u,%02u:%02u:%02u,%lu,%lu,N\n",
121 mask,
122 enddir - mask,
123 fb->cbFile,
124 (fb->fdateLastWrite.year + 1980),
125 fb->fdateLastWrite.month,
126 fb->fdateLastWrite.day,
127 fb->ftimeLastWrite.hours,
128 fb->ftimeLastWrite.minutes,
129 fb->ftimeLastWrite.twosecs,
130 fb->attrFile, (fb->cbList > 4) ? (fb->cbList / 2) : 0);
131 // Skip . and ..
132 else if (recurse &&
133 (fb->achName[0] != '.' ||
134 (fb->achName[1] &&
135 (fb->achName[1] != '.' || fb->achName[2])))) {
136 SnapShot(mask, fp, recurse);
137 }
138 nm = 1;
139 } while (!DosFindNext(hdir, fb, sizeof(FILEFINDBUF4), &nm));
140 DosFindClose(hdir);
141 }
142 free(mask);
143 }
144 free(fb);
145 }
146}
147
148//=== StartSnap() Write directory tree to snapshot file ===
149
150static VOID StartSnap(VOID * dummy)
151{
152 SNAPSTUFF *sf = (SNAPSTUFF *) dummy;
153 FILE *fp;
154 CHAR *p;
155
156 if (sf) {
157 if (*sf->dirname && *sf->filename) {
158 priority_normal();
159 p = sf->dirname;
160 while (*p) {
161 if (*p == '/')
162 *p = '\\';
163 p++;
164 }
165 if (*(p - 1) != '\\') {
166 *p = '\\';
167 p++;
168 }
169 fp = xfopen(sf->filename, "w", pszSrcFile, __LINE__);
170 if (fp) {
171 fprintf(fp, "\"%s\"\n", sf->dirname);
172 SnapShot(sf->dirname, fp, sf->recurse);
173 fclose(fp);
174 }
175 }
176 free(sf);
177 }
178}
179
180//=== CompareFilesThread() Compare files and update container select flags ===
181
182static VOID CompareFilesThread(VOID * args)
183{
184 FCOMPARE fc;
185 HAB hab2;
186 HMQ hmq2;
187 FILE *fp1, *fp2;
188 ULONG len1, len2, offset = 0L;
189 LONG numread1, numread2;
190 CHAR s[1024], ss[1024], *p1, *p2;
191
192 if (args) {
193 fc = *(FCOMPARE *) args;
194 hab2 = WinInitialize(0);
195 if (hab2) {
196 hmq2 = WinCreateMsgQueue(hab2, 0);
197 if (hmq2) {
198 WinCancelShutdown(hmq2, TRUE);
199 IncrThreadUsage();
200 if (!IsFile(fc.file1) || IsRoot(fc.file1)) {
201 p1 = strrchr(fc.file2, '\\');
202 if (p1) {
203 if (fc.file1[strlen(fc.file1) - 1] == '\\')
204 p1++;
205 strcat(fc.file1, p1);
206 }
207 }
208 else if (!IsFile(fc.file2) || IsRoot(fc.file2)) {
209 p1 = strrchr(fc.file1, '\\');
210 if (p1) {
211 if (fc.file2[strlen(fc.file2) - 1] == '\\')
212 p1++;
213 strcat(fc.file2, p1);
214 }
215 }
216 sprintf(s, GetPString(IDS_COMPCOMPARETEXT), fc.file1);
217 AddToListboxBottom(fc.hwndList, s);
218 sprintf(s, GetPString(IDS_COMPTOTEXT), fc.file2);
219 AddToListboxBottom(fc.hwndList, s);
220 fp1 = _fsopen(fc.file1, "rb", SH_DENYNO);
221 if (!fp1) {
222 sprintf(s, GetPString(IDS_COMPCANTOPENTEXT), fc.file1);
223 AddToListboxBottom(fc.hwndList, s);
224 WinSetWindowText(fc.hwndHelp, GetPString(IDS_ERRORTEXT));
225 }
226 else {
227 fp2 = _fsopen(fc.file2, "rb", SH_DENYNO);
228 if (!fp2) {
229 sprintf(s, GetPString(IDS_COMPCANTOPENTEXT), fc.file2);
230 AddToListboxBottom(fc.hwndList, s);
231 WinSetWindowText(fc.hwndHelp, GetPString(IDS_ERRORTEXT));
232 }
233 else {
234 len1 = filelength(fileno(fp1));
235 len2 = filelength(fileno(fp2));
236 if (len1 != len2) {
237 strcpy(s, GetPString(IDS_COMPDIFSIZESTEXT));
238 AddToListboxBottom(fc.hwndList, s);
239 sprintf(s, GetPString(IDS_COMPVSBYTESTEXT), len1, len2);
240 AddToListboxBottom(fc.hwndList, s);
241 WinSetWindowText(fc.hwndHelp,
242 GetPString(IDS_COMPDONTMATCHTEXT));
243 }
244 else {
245 WinSetWindowText(fc.hwndHelp,
246 GetPString(IDS_COMPCOMPARINGTEXT));
247 while (WinIsWindow(hab2, fc.hwndList)) {
248 numread1 = fread(s, 1, 1024, fp1);
249 numread2 = fread(ss, 1, 1024, fp2);
250 if (numread1 != numread2 || feof(fp1) != feof(fp2)) {
251 sprintf(s, GetPString(IDS_COMPREADERRORTEXT),
252 offset, offset);
253 AddToListboxBottom(fc.hwndList, s);
254 WinSetWindowText(fc.hwndHelp, GetPString(IDS_ERRORTEXT));
255 break;
256 }
257 else if (!numread1 && feof(fp1) && feof(fp2)) {
258 AddToListboxBottom(fc.hwndList,
259 GetPString(IDS_COMPFILESMATCHTEXT));
260 if (!stricmp(fc.file1, fc.file2))
261 AddToListboxBottom(fc.hwndList,
262 GetPString(IDS_COMPWONDERWHYTEXT));
263 WinSetWindowText(fc.hwndHelp,
264 GetPString(IDS_COMPCOMPLETETEXT));
265 break;
266 }
267 else if (numread1 <= 0 || numread2 <= 0) {
268 if (offset == len1)
269 break;
270 else {
271 sprintf(s, GetPString(IDS_COMPMATCHREADERRORTEXT),
272 offset, offset);
273 WinSetWindowText(fc.hwndHelp,
274 GetPString(IDS_COMPODDERRORTEXT));
275 AddToListboxBottom(fc.hwndList, s);
276 break;
277 }
278 }
279 else if (memcmp(s, ss, numread1)) {
280 p1 = s;
281 p2 = ss;
282 while (p1 < s + numread1) {
283 if (*p1 != *p2) {
284 sprintf(s, GetPString(IDS_COMPMISMATCHERRORTEXT),
285 offset + (p1 - s), offset + (p1 - s));
286 AddToListboxBottom(fc.hwndList, s);
287 WinSetWindowText(fc.hwndHelp,
288 GetPString(IDS_COMPDONTMATCHTEXT));
289 break;
290 }
291 p1++;
292 p2++;
293 }
294 break;
295 }
296 offset += numread1;
297 }
298 }
299 fclose(fp2);
300 }
301 fclose(fp1);
302 }
303 DecrThreadUsage();
304 WinDestroyMsgQueue(hmq2);
305 }
306 WinTerminate(hab2);
307 }
308 }
309}
310
311//=== CFileDlgProc() Select directories to compare dialog procedure ===
312
313MRESULT EXPENTRY CFileDlgProc(HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2)
314{
315 FCOMPARE *fc;
316
317 switch (msg) {
318 case WM_INITDLG:
319 if (!mp2)
320 WinDismissDlg(hwnd, 0);
321 else {
322 WinSetWindowPtr(hwnd, QWL_USER, mp2);
323 fc = (FCOMPARE *) mp2;
324 fc->hwndReport = hwnd;
325 fc->hwndList = WinWindowFromID(hwnd, FCMP_LISTBOX);
326 fc->hwndHelp = WinWindowFromID(hwnd, FCMP_HELP);
327 if (!*fc->file1 || !fc->file2) {
328 WinDismissDlg(hwnd, 0);
329 break;
330 }
331 MakeFullName(fc->file1);
332 MakeFullName(fc->file2);
333 if (!stricmp(fc->file1, fc->file2)) {
334 saymsg(MB_CANCEL, hwnd,
335 GetPString(IDS_COMPSILLYALERTTEXT),
336 GetPString(IDS_COMPTOITSELFTEXT));
337 WinDismissDlg(hwnd, 0);
338 break;
339 }
340 if (_beginthread(CompareFilesThread, NULL, 65536, (PVOID) fc) == -1) {
341 Runtime_Error(pszSrcFile, __LINE__,
342 GetPString(IDS_COULDNTSTARTTHREADTEXT));
343 WinDismissDlg(hwnd, 0);
344 }
345 }
346 break;
347
348 case WM_ADJUSTWINDOWPOS:
349 PostMsg(hwnd, UM_SETDIR, MPVOID, MPVOID);
350 break;
351
352 case UM_SETDIR:
353 PaintRecessedWindow(WinWindowFromID(hwnd, FCMP_HELP),
354 (HPS) 0, FALSE, TRUE);
355 return 0;
356
357 case WM_COMMAND:
358 switch (SHORT1FROMMP(mp1)) {
359 case DID_OK:
360 WinDismissDlg(hwnd, 0);
361 break;
362 case DID_CANCEL:
363 WinDismissDlg(hwnd, 1);
364 break;
365 }
366 return 0;
367
368 case WM_DESTROY:
369 DosSleep(50);//05 Aug 07 GKY 100
370 break;
371 }
372 return WinDefDlgProc(hwnd, msg, mp1, mp2);
373}
374
375//=== ActionCnrThread() Do requested action on container contents ===
376
377static VOID ActionCnrThread(VOID *args)
378{
379 COMPARE *cmp = (COMPARE *)args;
380 HAB hab;
381 HMQ hmq;
382 HWND hwndCnrS, hwndCnrD;
383 PCNRITEM pci, pciD, pciNextS, pciNextD;
384 CHAR szNewName[CCHMAXPATH], szDirName[CCHMAXPATH], *p;
385 APIRET rc;
386
387 if (!cmp) {
388 Runtime_Error2(pszSrcFile, __LINE__, IDS_NODATATEXT);
389 return;
390 }
391
392 DosError(FERR_DISABLEHARDERR);
393
394 hab = WinInitialize(0);
395 if (hab) {
396 hmq = WinCreateMsgQueue(hab, 0);
397 if (hmq) {
398 WinCancelShutdown(hmq, TRUE);
399 IncrThreadUsage();
400 priority_normal();
401 switch (cmp->action) {
402 case COMP_DELETELEFT:
403 hwndCnrS = WinWindowFromID(cmp->hwnd, COMP_LEFTDIR);
404 hwndCnrD = WinWindowFromID(cmp->hwnd, COMP_RIGHTDIR);
405 cmp->action = IDM_DELETE;
406 break;
407 case COMP_DELETERIGHT:
408 hwndCnrS = WinWindowFromID(cmp->hwnd, COMP_RIGHTDIR);
409 hwndCnrD = WinWindowFromID(cmp->hwnd, COMP_LEFTDIR);
410 cmp->action = IDM_DELETE;
411 break;
412 case COMP_MOVELEFT:
413 cmp->action = IDM_MOVE;
414 hwndCnrS = WinWindowFromID(cmp->hwnd, COMP_LEFTDIR);
415 hwndCnrD = WinWindowFromID(cmp->hwnd, COMP_RIGHTDIR);
416 break;
417 case COMP_MOVERIGHT:
418 cmp->action = IDM_MOVE;
419 hwndCnrS = WinWindowFromID(cmp->hwnd, COMP_RIGHTDIR);
420 hwndCnrD = WinWindowFromID(cmp->hwnd, COMP_LEFTDIR);
421 break;
422 case COMP_COPYLEFT:
423 cmp->action = IDM_COPY;
424 hwndCnrS = WinWindowFromID(cmp->hwnd, COMP_LEFTDIR);
425 hwndCnrD = WinWindowFromID(cmp->hwnd, COMP_RIGHTDIR);
426 break;
427 case COMP_COPYRIGHT:
428 cmp->action = IDM_COPY;
429 hwndCnrS = WinWindowFromID(cmp->hwnd, COMP_RIGHTDIR);
430 hwndCnrD = WinWindowFromID(cmp->hwnd, COMP_LEFTDIR);
431 break;
432 default:
433 Runtime_Error(pszSrcFile, __LINE__, "bad case %u", cmp->action);
434 goto Abort;
435 }
436
437 pci = WinSendMsg(hwndCnrS, CM_QUERYRECORD, MPVOID,
438 MPFROM2SHORT(CMA_FIRST, CMA_ITEMORDER));
439 pciD = WinSendMsg(hwndCnrD, CM_QUERYRECORD, MPVOID,
440 MPFROM2SHORT(CMA_FIRST, CMA_ITEMORDER));
441
442 while (pci && (INT)pci != -1 && pciD && (INT)pciD != -1) {
443
444 pciNextS = WinSendMsg(hwndCnrS, CM_QUERYRECORD, MPFROMP(pci),
445 MPFROM2SHORT(CMA_NEXT, CMA_ITEMORDER));
446 pciNextD = WinSendMsg(hwndCnrD, CM_QUERYRECORD, MPFROMP(pciD),
447 MPFROM2SHORT(CMA_NEXT, CMA_ITEMORDER));
448
449 if (*pci->pszFileName && pci->rc.flRecordAttr & CRA_SELECTED) {
450
451 // Source name not blank
452 switch (cmp->action) {
453 case IDM_DELETE:
454 if (!unlinkf("%s", pci->pszFileName)) {
455 WinSendMsg(hwndCnrS, CM_SETRECORDEMPHASIS, MPFROMP(pci),
456 MPFROM2SHORT(FALSE, CRA_SELECTED));
457
458 if (!*pciD->pszFileName) {
459 // Other side is blank - remove from both sides
460 RemoveCnrItems(hwndCnrS, pci, 1, CMA_FREE | CMA_INVALIDATE);
461 if (pciD->rc.flRecordAttr & CRA_SELECTED)
462 WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciD),
463 MPFROM2SHORT(FALSE, CRA_SELECTED));
464 RemoveCnrItems(hwndCnrD, pciD, 1, CMA_FREE | CMA_INVALIDATE);
465 }
466 else {
467 // Other side is not blank - update just this side
468 FreeCnrItemData(pci);
469 pci->pszDisplayName = pci->pszFileName;
470 pci->rc.pszIcon = pci->pszFileName;
471 pci->flags = 0;
472 WinSendMsg(hwndCnrS, CM_INVALIDATERECORD, MPFROMP(&pci),
473 MPFROM2SHORT(1, CMA_ERASE | CMA_TEXTCHANGED));
474 }
475 if (hwndCnrS == WinWindowFromID(cmp->hwnd, COMP_LEFTDIR))
476 cmp->cmp->totalleft--;
477 else
478 cmp->cmp->totalright--;
479 DosSleep(1);
480 }
481 break;
482
483 case IDM_MOVE:
484 if (hwndCnrS == WinWindowFromID(cmp->hwnd, COMP_RIGHTDIR))
485 BldFullPathName(szNewName, cmp->leftdir, pci->pszDisplayName);
486 //sprintf(szNewName, "%s%s%s",
487 // cmp->leftdir,
488 // cmp->leftdir[strlen(cmp->leftdir) - 1] == '\\' ?
489 // NullStr : "\\",
490 // pci->pszDisplayName);
491 else
492 BldFullPathName(szNewName, cmp->rightdir, pci->pszDisplayName);
493 //sprintf(szNewName, "%s%s%s",
494 // cmp->rightdir,
495 // cmp->rightdir[strlen(cmp->rightdir) - 1] == '\\' ?
496 // NullStr : "\\",
497 // pci->pszDisplayName);
498 // Make directory if required
499 strcpy(szDirName, szNewName);
500 p = strrchr(szDirName, '\\');
501 if (p) {
502 if (p > szDirName + 2)
503 p++;
504 *p = 0;
505 if (IsFile(szDirName) == -1)
506 MassMkdir(hwndMain, szDirName);
507 }
508 rc = docopyf(MOVE, pci->pszFileName, "%s", szNewName);
509 if (!rc && stricmp(pci->pszFileName, szNewName)) {
510 WinSendMsg(hwndCnrS, CM_SETRECORDEMPHASIS, MPFROMP(pci),
511 MPFROM2SHORT(FALSE, CRA_SELECTED));
512 if (pciD->rc.flRecordAttr & CRA_SELECTED)
513 WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciD),
514 MPFROM2SHORT(FALSE, CRA_SELECTED));
515 FreeCnrItemData(pciD);
516 pciD->pszFileName = xstrdup(szNewName, pszSrcFile, __LINE__);
517 if (hwndCnrS == WinWindowFromID(cmp->hwnd, COMP_RIGHTDIR)) {
518 pciD->pszDisplayName = pciD->pszFileName + strlen(cmp->leftdir);
519 if (cmp->leftdir[strlen(cmp->leftdir) - 1] != '\\')
520 pciD->pszDisplayName++;
521 }
522 else {
523 pciD->pszDisplayName = pciD->pszFileName + strlen(cmp->rightdir);
524 if (cmp->rightdir[strlen(cmp->rightdir) - 1] != '\\')
525 pciD->pszDisplayName++;
526 }
527 // 02 Aug 07 SHL fixme to know if LongName transfer is correct?
528 pciD->pszLongName = pci->pszLongName;
529 if (pciD->pszSubject != NullStr) {
530 xfree(pciD->pszSubject);
531 pciD->pszSubject = NullStr;
532 }
533 pciD->attrFile = pci->attrFile;
534 pciD->pszDispAttr = pci->pszDispAttr;
535 pciD->flags = 0; // Just on one side
536 pciD->date = pci->date;
537 pciD->time = pci->time;
538 pciD->ladate = pci->ladate;
539 pciD->latime = pci->latime;
540 pciD->crdate = pci->crdate;
541 pciD->crtime = pci->crtime;
542 pciD->cbFile = pci->cbFile;
543 pciD->easize = pci->easize;
544
545 if (pci->pszFileName != NullStr) {
546 xfree(pci->pszFileName);
547 pci->pszFileName = NullStr;
548 pci->pszDisplayName = pci->pszFileName;
549 pci->rc.pszIcon = pci->pszFileName;
550 }
551 if (pci->pszSubject != NullStr) {
552 xfree(pci->pszSubject);
553 pci->pszSubject = NullStr;
554 }
555 pci->flags = 0;
556
557 WinSendMsg(hwndCnrS, CM_INVALIDATERECORD, MPFROMP(&pci),
558 MPFROM2SHORT(1, CMA_ERASE | CMA_TEXTCHANGED));
559 WinSendMsg(hwndCnrD, CM_INVALIDATERECORD, MPFROMP(&pciD),
560 MPFROM2SHORT(1, CMA_ERASE | CMA_TEXTCHANGED));
561 }
562 else if (rc) {
563 rc = Dos_Error(MB_ENTERCANCEL,
564 rc,
565 HWND_DESKTOP,
566 pszSrcFile,
567 __LINE__,
568 GetPString(IDS_COMPMOVEFAILEDTEXT),
569 pci->pszFileName, szNewName);
570 if (rc == MBID_CANCEL) // Cause loop to break
571 pciNextS = NULL;
572 }
573 break;
574
575 case IDM_COPY:
576 if (hwndCnrS == WinWindowFromID(cmp->hwnd, COMP_RIGHTDIR))
577 BldFullPathName(szNewName, cmp->leftdir, pci->pszDisplayName);
578 //sprintf(szNewName, "%s%s%s",
579 // cmp->leftdir,
580 // cmp->leftdir[strlen(cmp->leftdir) - 1] == '\\' ?
581 // NullStr : "\\",
582 // pci->pszDisplayName);
583 else
584 BldFullPathName(szNewName, cmp->rightdir, pci->pszDisplayName);
585 //sprintf(szNewName, "%s%s%s",
586 // cmp->rightdir,
587 // cmp->rightdir[strlen(cmp->rightdir) - 1] == '\\' ?
588 // NullStr : "\\",
589 // pci->pszDisplayName);
590 // Make directory if required
591 strcpy(szDirName, szNewName);
592 p = strrchr(szDirName, '\\');
593 if (p) {
594 if (p > szDirName + 2)
595 p++;
596 *p = 0;
597 if (IsFile(szDirName) == -1)
598 MassMkdir(hwndMain, szDirName);
599 }
600 rc = docopyf(COPY, pci->pszFileName, "%s", szNewName);
601 if (rc) {
602 rc = Dos_Error(MB_ENTERCANCEL,
603 rc,
604 HWND_DESKTOP,
605 pszSrcFile,
606 __LINE__,
607 GetPString(IDS_COMPCOPYFAILEDTEXT),
608 pci->pszFileName, szNewName);
609 if (rc == MBID_CANCEL)
610 pciNextS = NULL; // Cause loop to break
611 }
612 else {
613 WinSendMsg(hwndCnrS, CM_SETRECORDEMPHASIS, MPFROMP(pci),
614 MPFROM2SHORT(FALSE, CRA_SELECTED));
615 if (pciD->rc.flRecordAttr & CRA_SELECTED)
616 WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciD),
617 MPFROM2SHORT(FALSE, CRA_SELECTED));
618 FreeCnrItemData(pciD);
619 pciD->pszFileName = xstrdup(szNewName, pszSrcFile, __LINE__);
620 if (hwndCnrS == WinWindowFromID(cmp->hwnd, COMP_RIGHTDIR)) {
621 pciD->pszDisplayName = pciD->pszFileName + strlen(cmp->leftdir);
622 if (cmp->leftdir[strlen(cmp->leftdir) - 1] != '\\')
623 pciD->pszDisplayName++;
624 }
625 else {
626 pciD->pszDisplayName = pciD->pszFileName + strlen(cmp->rightdir);
627 if (cmp->rightdir[strlen(cmp->rightdir) - 1] != '\\')
628 pciD->pszDisplayName++;
629 }
630 pciD->attrFile = pci->attrFile;
631 pciD->pszDispAttr = pci->pszDispAttr;
632 pciD->flags = CNRITEM_EXISTS; // Now on both sides
633 pciD->date = pci->date;
634 pciD->time = pci->time;
635 pciD->ladate = pci->ladate;
636 pciD->latime = pci->latime;
637 pciD->crdate = pci->crdate;
638 pciD->crtime = pci->crtime;
639 pciD->cbFile = pci->cbFile;
640 pciD->easize = pci->easize;
641
642 // Forget status until we regenerate it
643 if (pci->pszSubject != NullStr) {
644 xfree(pci->pszSubject);
645 pci->pszSubject = NullStr;
646 }
647 pci->flags = CNRITEM_EXISTS;
648
649 WinSendMsg(hwndCnrS, CM_INVALIDATERECORD, MPFROMP(&pci),
650 MPFROM2SHORT(1, CMA_ERASE | CMA_TEXTCHANGED));
651 WinSendMsg(hwndCnrD, CM_INVALIDATERECORD, MPFROMP(&pciD),
652 MPFROM2SHORT(1, CMA_ERASE | CMA_TEXTCHANGED));
653 }
654 break;
655
656 default:
657 break;
658 } // switch
659
660 } // if have name
661
662 pci = pciNextS;
663 pciD = pciNextD;
664
665 } // while
666 Abort:
667 WinDestroyMsgQueue(hmq);
668 }
669 DecrThreadUsage();
670 WinTerminate(hab);
671 }
672 PostMsg(cmp->hwnd, UM_CONTAINER_FILLED, MPFROMLONG(1L), MPVOID);
673 PostMsg(cmp->hwnd, WM_COMMAND, MPFROM2SHORT(IDM_DESELECTALL, 0), MPVOID);
674 free(cmp);
675}
676
677//=== SelectCnrsThread() Update container selection flags thread ===
678
679static VOID SelectCnrsThread(VOID * args)
680{
681 COMPARE *cmp = (COMPARE *) args;
682 HAB hab;
683 HMQ hmq;
684
685 if (!cmp)
686 return;
687
688 DosError(FERR_DISABLEHARDERR);
689
690 hab = WinInitialize(0);
691 if (hab) {
692 hmq = WinCreateMsgQueue(hab, 0);
693 if (hmq) {
694 WinCancelShutdown(hmq, TRUE);
695 IncrThreadUsage();
696 priority_normal();
697 switch (cmp->action) {
698 case IDM_INVERT:
699 InvertAll(WinWindowFromID(cmp->hwnd, COMP_LEFTDIR));
700 InvertAll(WinWindowFromID(cmp->hwnd, COMP_RIGHTDIR));
701 break;
702
703 case IDM_DESELECTALL:
704 Deselect(WinWindowFromID(cmp->hwnd, COMP_LEFTDIR));
705 Deselect(WinWindowFromID(cmp->hwnd, COMP_RIGHTDIR));
706 break;
707
708 default:
709 SpecialSelect(WinWindowFromID(cmp->hwnd, COMP_LEFTDIR),
710 WinWindowFromID(cmp->hwnd, COMP_RIGHTDIR),
711 cmp->action, cmp->reset);
712 break;
713 }
714 if (!PostMsg(cmp->hwnd, UM_CONTAINER_FILLED, MPFROMLONG(1L), MPVOID))
715 WinSendMsg(cmp->hwnd, UM_CONTAINER_FILLED, MPFROMLONG(1L), MPVOID);
716 WinDestroyMsgQueue(hmq);
717 }
718 DecrThreadUsage();
719 WinTerminate(hab);
720 }
721 free(cmp);
722}
723
724/**
725 * Build FILELIST given pathname
726 */
727
728static VOID FillDirList(CHAR *str, INT skiplen, BOOL recurse,
729 FILELIST ***list, INT *numfiles, INT *numalloc)
730{
731
732 BYTE *fb;
733 CHAR *enddir;
734 ULONG x;
735 CHAR *maskstr;
736 FILEFINDBUF4 *ffb4, *pffb;
737 HDIR hDir;
738 ULONG nm, fl = 0, ulM = FilesToGet;
739 APIRET rc;
740
741 if (!str || !*str) {
742 Runtime_Error2(pszSrcFile, __LINE__, IDS_NODATATEXT);
743 return;
744 }
745
746 //if (!recurse)
747 // ulM = FilesToGet;
748 maskstr = xmalloc(CCHMAXPATH, pszSrcFile, __LINE__);
749 if (!maskstr)
750 return;
751 ffb4 = xmalloc(sizeof(FILEFINDBUF4) * ulM, pszSrcFile, __LINE__);
752 if (!ffb4) {
753 free(maskstr);
754 return;
755 }
756 x = strlen(str);
757 memcpy(maskstr, str, x + 1);
758 enddir = maskstr + x;
759 if (*(enddir - 1) != '\\') {
760 *enddir = '\\';
761 enddir++;
762 *enddir = 0;
763 }
764 *enddir = '*';
765 *(enddir + 1) = 0;
766 hDir = HDIR_CREATE;
767 nm = ulM;
768 if (recurse)
769 fl = FILE_DIRECTORY;
770 DosError(FERR_DISABLEHARDERR);
771 rc = DosFindFirst(maskstr, &hDir,
772 (FILE_NORMAL | FILE_READONLY | FILE_ARCHIVED |
773 FILE_SYSTEM | FILE_HIDDEN) | fl,
774 ffb4, sizeof(FILEFINDBUF4) * nm, &nm, FIL_QUERYEASIZE);
775 if (!rc) {
776 while (!rc) {
777 fb = (BYTE *) ffb4;
778 x = 0;
779 while (x < nm) {
780 pffb = (FILEFINDBUF4 *) fb;
781 if (pffb->attrFile & FILE_DIRECTORY) {
782 // Skip . and ..
783 if (recurse &&
784 (pffb->achName[0] != '.' ||
785 (pffb->achName[1] &&
786 (pffb->achName[1] != '.' || pffb->achName[2])))) {
787 if (fForceUpper)
788 strupr(pffb->achName);
789 else if (fForceLower)
790 strlwr(pffb->achName);
791 memcpy(enddir, pffb->achName, pffb->cchName + 1);
792 FillDirList(maskstr, skiplen, recurse, list, numfiles, numalloc);
793 }
794 }
795 else {
796 if (fForceUpper)
797 strupr(pffb->achName);
798 else if (fForceLower)
799 strlwr(pffb->achName);
800 memcpy(enddir, pffb->achName, pffb->cchName + 1);
801 if (AddToFileList
802 (maskstr + skiplen, pffb, list, numfiles, numalloc))
803 goto Abort;
804 }
805 fb += pffb->oNextEntryOffset;
806 x++;
807 }
808 nm = ulM;
809 DosError(FERR_DISABLEHARDERR);
810 rc = DosFindNext(hDir, ffb4, sizeof(FILEFINDBUF4) * nm, &nm);
811 }
812 Abort:
813 DosFindClose(hDir);
814 DosSleep(1);
815 }
816 free(maskstr);
817 free(ffb4);
818}
819
820//=== CompNames() Compare names for qsort ===
821
822static int CompNames(const void *n1, const void *n2)
823{
824 FILELIST *fl1 = *(FILELIST **) n1;
825 FILELIST *fl2 = *(FILELIST **) n2;
826
827 return stricmp(fl1->fname, fl2->fname);
828}
829
830//=== FillCnrsThread() Fill left and right containers ===
831
832static VOID FillCnrsThread(VOID *args)
833{
834 COMPARE *cmp = (COMPARE *) args;
835 HAB hab;
836 HMQ hmq;
837 BOOL notified = FALSE;
838
839 HWND hwndLeft, hwndRight;
840 CHAR szBuf[CCHMAXPATH];
841 CNRINFO cnri;
842
843 if (!cmp) {
844 Runtime_Error2(pszSrcFile, __LINE__, IDS_NODATATEXT);
845 _endthread();
846 }
847
848 DosError(FERR_DISABLEHARDERR);
849
850 hab = WinInitialize(0);
851 if (!hab)
852 Win_Error(NULLHANDLE, NULLHANDLE, pszSrcFile, __LINE__, "WinInitialize");
853 else {
854 hmq = WinCreateMsgQueue(hab, 0);
855 if (!hmq)
856 Win_Error(NULLHANDLE, NULLHANDLE, pszSrcFile, __LINE__,
857 "WinCreateMsgQueue");
858 else {
859 INT x;
860 INT l;
861 INT r;
862 ULONG cntr;
863 FILELIST **filesl = NULL;
864 FILELIST **filesr = NULL;
865 INT numfilesl = 0;
866 INT numfilesr = 0;
867 INT numallocl = 0;
868 INT numallocr = 0;
869 UINT lenl; // Directory prefix length
870 UINT lenr;
871 UINT recsNeeded;
872 PCNRITEM pcilFirst;
873 PCNRITEM pcirFirst;
874 PCNRITEM pcil;
875 PCNRITEM pcir;
876 RECORDINSERT ri;
877 CHAR *pch;
878
879 WinCancelShutdown(hmq, TRUE);
880 IncrThreadUsage();
881 hwndLeft = WinWindowFromID(cmp->hwnd, COMP_LEFTDIR);
882 hwndRight = WinWindowFromID(cmp->hwnd, COMP_RIGHTDIR);
883 lenl = strlen(cmp->leftdir);
884 if (cmp->leftdir[strlen(cmp->leftdir) - 1] != '\\')
885 lenl++;
886 lenr = strlen(cmp->rightdir);
887 if (cmp->rightdir[strlen(cmp->rightdir) - 1] != '\\')
888 lenr++;
889 priority_normal();
890 // Clear containers
891 RemoveCnrItems(hwndRight, NULL, 0, CMA_FREE | CMA_INVALIDATE);
892 RemoveCnrItems(hwndLeft, NULL, 0, CMA_FREE | CMA_INVALIDATE);
893 cmp->cmp->totalleft = cmp->cmp->totalright = 0;
894
895 // Build list of all files in left directory
896 if (fForceLower)
897 strlwr(cmp->leftdir);
898 else if (fForceUpper)
899 strupr(cmp->leftdir);
900 FillDirList(cmp->leftdir, lenl, cmp->includesubdirs,
901 &filesl, &numfilesl, &numallocl);
902
903 if (filesl)
904 qsort(filesl, numfilesl, sizeof(CHAR *), CompNames);
905
906 // Build list of all files in right directory
907 if (!*cmp->rightlist) {
908 if (fForceLower)
909 strlwr(cmp->rightdir);
910 else if (fForceUpper)
911 strupr(cmp->rightdir);
912 FillDirList(cmp->rightdir, lenr, cmp->includesubdirs,
913 &filesr, &numfilesr, &numallocr);
914 }
915 else {
916 // Use snapshot file
917 FILE *fp;
918 FILEFINDBUF4 fb4;
919 CHAR str[CCHMAXPATH * 2], *p;
920
921 memset(&fb4, 0, sizeof(fb4));
922 fp = fopen(cmp->rightlist, "r");
923 if (!fp)
924 Runtime_Error(pszSrcFile, __LINE__, "can not open %s (%d)",
925 cmp->rightlist, errno);
926 else {
927 while (!feof(fp)) {
928 // First get name of directory
929 if (!xfgets_bstripcr(str, sizeof(str), fp, pszSrcFile, __LINE__))
930 break; // EOF
931 p = str;
932 if (*p == '\"') {
933 // Quoted
934 p++;
935 if (*p && *p != '\"') {
936 p = strchr(p, '\"');
937 if (p) {
938 *p = 0;
939 if (*(str + 1)) {
940 strcpy(cmp->rightdir, str + 1);
941 if (fForceUpper)
942 strupr(cmp->rightdir);
943 else if (fForceLower)
944 strlwr(cmp->rightdir);
945 p = cmp->rightdir + (strlen(cmp->rightdir) - 1);
946 if (p - cmp->rightdir > 3 && *p == '\\')
947 *p = 0; // Chop trailing slash
948 break;
949 }
950 }
951 }
952 }
953 } // while !EOF
954
955 memset(&cnri, 0, sizeof(cnri));
956 cnri.cb = sizeof(cnri);
957 cnri.pszCnrTitle = cmp->rightdir;
958 if (!WinSendMsg(hwndRight, CM_SETCNRINFO,
959 MPFROMP(&cnri), MPFROMLONG(CMA_CNRTITLE))) {
960 Win_Error(hwndRight, cmp->hwnd, pszSrcFile, __LINE__, "CM_SETCNRINFO");
961 }
962
963 if (*cmp->rightdir) {
964 lenr = strlen(cmp->rightdir);
965 if (cmp->rightdir[strlen(cmp->rightdir) - 1] != '\\')
966 lenr++;
967 while (!feof(fp)) {
968 if (!xfgets_bstripcr
969 (str, sizeof(str), fp, pszSrcFile, __LINE__))
970 break;
971 p = str;
972 if (*p == '\"') {
973 p++;
974 if (*p && *p != '\"') {
975 p = strchr(p, '\"');
976 if (p) {
977 *p = 0;
978 p++;
979 if (*p == ',') {
980 p++;
981 if (!cmp->includesubdirs && atol(p) > lenr)
982 continue;
983 p = strchr(p, ',');
984 if (p) {
985 p++;
986 fb4.cbFile = atol(p);
987 p = strchr(p, ',');
988 if (p) {
989 p++;
990 fb4.fdateLastWrite.year = atol(p) - 1980;
991 p = strchr(p, '/');
992 if (p) {
993 p++;
994 fb4.fdateLastWrite.month = atol(p);
995 p = strchr(p, '/');
996 if (p) {
997 p++;
998 fb4.fdateLastWrite.day = atol(p);
999 p = strchr(p, ',');
1000 if (p) {
1001 p++;
1002 fb4.ftimeLastWrite.hours = atol(p);
1003 p = strchr(p, ':');
1004 if (p) {
1005 p++;
1006 fb4.ftimeLastWrite.minutes = atol(p);
1007 p = strchr(p, ':');
1008 if (p) {
1009 p++;
1010 fb4.ftimeLastWrite.twosecs = atol(p);
1011 p = strchr(p, ',');
1012 if (p) {
1013 p++;
1014 fb4.attrFile = atol(p);
1015 p = strchr(p, ',');
1016 if (p) {
1017 p++;
1018 fb4.cbList = atol(p) * 2;
1019 if (fForceUpper)
1020 strupr(str + 1);
1021 else if (fForceLower)
1022 strlwr(str + 1);
1023 if (AddToFileList((str + 1) + lenr,
1024 &fb4,
1025 &filesr,
1026 &numfilesr,
1027 &numallocr))
1028 break;
1029 }
1030 }
1031 }
1032 }
1033 }
1034 }
1035 }
1036 }
1037 }
1038 }
1039 }
1040 }
1041 }
1042 } // while
1043 } // if have rightdir
1044 fclose(fp);
1045 }
1046 } // if snapshot file
1047
1048 if (filesr)
1049 qsort(filesr, numfilesr, sizeof(CHAR *), CompNames);
1050
1051 // We now have two lists of files, both sorted.
1052 // Count total number of container entries required on each side
1053 l = r = 0;
1054 recsNeeded = 0;
1055 while ((filesl && filesl[l]) || (filesr && filesr[r])) {
1056
1057 if (filesl && filesl[l]) {
1058 if (filesr && filesr[r])
1059 x = stricmp(filesl[l]->fname, filesr[r]->fname);
1060 else
1061 x = -1; // Left side list longer
1062 }
1063 else
1064 x = +1; // Right side list longer
1065
1066 if (x <= 0)
1067 l++; // On left side
1068 if (x >= 0)
1069 r++; // On right side
1070
1071 recsNeeded++; // Keep count of how many entries req'd
1072
1073 } // while
1074
1075 WinSendMsg(cmp->hwnd, UM_CONTAINERHWND, MPVOID, MPVOID);
1076
1077 // Now insert records into the containers
1078 cntr = 0;
1079 l = r = 0;
1080 if (recsNeeded) {
1081 pcilFirst = WinSendMsg(hwndLeft,
1082 CM_ALLOCRECORD,
1083 MPFROMLONG(EXTRA_RECORD_BYTES),
1084 MPFROMLONG(recsNeeded));
1085 if (!pcilFirst) {
1086 Win_Error(hwndLeft, cmp->hwnd, pszSrcFile, __LINE__, "CM_ALLOCRECORD %u failed",
1087 recsNeeded);
1088 recsNeeded = 0;
1089 }
1090 }
1091 if (recsNeeded) {
1092 pcirFirst = WinSendMsg(hwndRight, CM_ALLOCRECORD,
1093 MPFROMLONG(EXTRA_RECORD_BYTES),
1094 MPFROMLONG(recsNeeded));
1095 if (!pcirFirst) {
1096 Win_Error(hwndRight, cmp->hwnd, pszSrcFile, __LINE__, "CM_ALLOCRECORD %u failed",
1097 recsNeeded);
1098 recsNeeded = 0;
1099 FreeCnrItemList(hwndLeft, pcilFirst);
1100 }
1101 }
1102
1103 if (recsNeeded) {
1104
1105 pcil = pcilFirst;
1106 pcir = pcirFirst;
1107 while ((filesl && filesl[l]) || (filesr && filesr[r])) {
1108 pcir->hwndCnr = hwndRight;
1109 pcir->rc.hptrIcon = (HPOINTER) 0;
1110 pcil->hwndCnr = hwndLeft;
1111 pcil->rc.hptrIcon = (HPOINTER) 0;
1112
1113 if (filesl && filesl[l]) {
1114 if (filesr && filesr[r])
1115 x = stricmp(filesl[l]->fname, filesr[r]->fname);
1116 else
1117 x = -1; // Left side list longer
1118 }
1119 else
1120 x = +1; // Right side list longer
1121
1122 if (x <= 0) {
1123 // File appears on left side
1124 BldFullPathName(szBuf, cmp->leftdir, filesl[l]->fname);
1125 //sprintf(szBuf, "%s%s%s", cmp->leftdir,
1126 // (cmp->leftdir[strlen(cmp->leftdir) - 1] == '\\') ?
1127 // NullStr : "\\", filesl[l]->fname);
1128 pcil->pszFileName = xstrdup(szBuf, pszSrcFile, __LINE__);
1129 pcil->pszDisplayName = pcil->pszFileName + lenl;
1130 pcil->attrFile = filesl[l]->attrFile;
1131 pcil->pszDispAttr = FileAttrToString(pcil->attrFile);
1132 pcil->cbFile = filesl[l]->cbFile;
1133 pcil->easize = filesl[l]->easize;
1134 pcil->date.day = filesl[l]->date.day;
1135 pcil->date.month = filesl[l]->date.month;
1136 pcil->date.year = filesl[l]->date.year + 1980;
1137 pcil->time.seconds = filesl[l]->time.twosecs * 2;
1138 pcil->time.minutes = filesl[l]->time.minutes;
1139 pcil->time.hours = filesl[l]->time.hours;
1140 pcil->ladate.day = filesl[l]->ladate.day;
1141 pcil->ladate.month = filesl[l]->ladate.month;
1142 pcil->ladate.year = filesl[l]->ladate.year + 1980;
1143 pcil->latime.seconds = filesl[l]->latime.twosecs * 2;
1144 pcil->latime.minutes = filesl[l]->latime.minutes;
1145 pcil->latime.hours = filesl[l]->latime.hours;
1146 pcil->crdate.day = filesl[l]->crdate.day;
1147 pcil->crdate.month = filesl[l]->crdate.month;
1148 pcil->crdate.year = filesl[l]->crdate.year + 1980;
1149 pcil->crtime.seconds = filesl[l]->crtime.twosecs * 2;
1150 pcil->crtime.minutes = filesl[l]->crtime.minutes;
1151 pcil->crtime.hours = filesl[l]->crtime.hours;
1152 if (*cmp->dcd.mask.szMask) {
1153 if (!Filter((PMINIRECORDCORE) pcil, (PVOID)&cmp->dcd.mask)) {
1154 pcil->rc.flRecordAttr |= CRA_FILTERED;
1155 pcir->rc.flRecordAttr |= CRA_FILTERED;
1156 }
1157 }
1158 } // if on left
1159
1160 if (x >= 0) {
1161 // File appears on right side
1162 BldFullPathName(szBuf, cmp->rightdir, filesr[r]->fname);
1163 //sprintf(szBuf, "%s%s%s", cmp->rightdir,
1164 // (cmp->rightdir[strlen(cmp->rightdir) - 1] == '\\') ?
1165 // NullStr : "\\", filesr[r]->fname);
1166 pcir->pszFileName = xstrdup(szBuf, pszSrcFile, __LINE__); // 31 Jul 07 SHL
1167 pcir->pszDisplayName = pcir->pszFileName + lenr;
1168 pcir->attrFile = filesr[r]->attrFile;
1169 // pcir->rc.hptrIcon = hptrFile;
1170 pcir->pszDispAttr = FileAttrToString(pcir->attrFile);
1171 pcir->cbFile = filesr[r]->cbFile;
1172 pcir->easize = filesr[r]->easize;
1173 pcir->date.day = filesr[r]->date.day;
1174 pcir->date.month = filesr[r]->date.month;
1175 pcir->date.year = filesr[r]->date.year + 1980;
1176 pcir->time.seconds = filesr[r]->time.twosecs * 2;
1177 pcir->time.minutes = filesr[r]->time.minutes;
1178 pcir->time.hours = filesr[r]->time.hours;
1179 pcir->ladate.day = filesr[r]->ladate.day;
1180 pcir->ladate.month = filesr[r]->ladate.month;
1181 pcir->ladate.year = filesr[r]->ladate.year + 1980;
1182 pcir->latime.seconds = filesr[r]->latime.twosecs * 2;
1183 pcir->latime.minutes = filesr[r]->latime.minutes;
1184 pcir->latime.hours = filesr[r]->latime.hours;
1185 pcir->crdate.day = filesr[r]->crdate.day;
1186 pcir->crdate.month = filesr[r]->crdate.month;
1187 pcir->crdate.year = filesr[r]->crdate.year + 1980;
1188 pcir->crtime.seconds = filesr[r]->crtime.twosecs * 2;
1189 pcir->crtime.minutes = filesr[r]->crtime.minutes;
1190 pcir->crtime.hours = filesr[r]->crtime.hours;
1191 if (~pcil->rc.flRecordAttr & CRA_FILTERED &&
1192 *cmp->dcd.mask.szMask) {
1193 if (!Filter((PMINIRECORDCORE)pcir, (PVOID)&cmp->dcd.mask)) {
1194 pcil->rc.flRecordAttr |= CRA_FILTERED;
1195 pcir->rc.flRecordAttr |= CRA_FILTERED;
1196 }
1197 }
1198 } // if on right
1199
1200 if (x == 0) {
1201 // File appears on both sides
1202 pcil->flags |= CNRITEM_EXISTS;
1203 pcir->flags |= CNRITEM_EXISTS;
1204 pch = szBuf;
1205 // Subject field holds status messages
1206 *pch = 0;
1207 if (pcil->cbFile + pcil->easize > pcir->cbFile + pcir->easize) {
1208 pcil->flags |= CNRITEM_LARGER;
1209 pcir->flags |= CNRITEM_SMALLER;
1210 strcpy(pch, GetPString(IDS_LARGERTEXT));
1211 pch += 6;
1212 }
1213 else if (pcil->cbFile + pcil->easize <
1214 pcir->cbFile + pcir->easize) {
1215 pcil->flags |= CNRITEM_SMALLER;
1216 pcir->flags |= CNRITEM_LARGER;
1217 strcpy(pch, GetPString(IDS_SMALLERTEXT));
1218 pch += 7;
1219 }
1220 if ((pcil->date.year > pcir->date.year) ? TRUE :
1221 (pcil->date.year < pcir->date.year) ? FALSE :
1222 (pcil->date.month > pcir->date.month) ? TRUE :
1223 (pcil->date.month < pcir->date.month) ? FALSE :
1224 (pcil->date.day > pcir->date.day) ? TRUE :
1225 (pcil->date.day < pcir->date.day) ? FALSE :
1226 (pcil->time.hours > pcir->time.hours) ? TRUE :
1227 (pcil->time.hours < pcir->time.hours) ? FALSE :
1228 (pcil->time.minutes > pcir->time.minutes) ? TRUE :
1229 (pcil->time.minutes < pcir->time.minutes) ? FALSE :
1230 (pcil->time.seconds > pcir->time.seconds) ? TRUE :
1231 (pcil->time.seconds < pcir->time.seconds) ? FALSE : FALSE) {
1232 pcil->flags |= CNRITEM_NEWER;
1233 pcir->flags |= CNRITEM_OLDER;
1234 if (pch != szBuf) {
1235 strcpy(pch, ", ");
1236 pch += 2;
1237 }
1238 strcpy(pch, GetPString(IDS_NEWERTEXT));
1239 pch += 5;
1240 }
1241 else if ((pcil->date.year < pcir->date.year) ? TRUE :
1242 (pcil->date.year > pcir->date.year) ? FALSE :
1243 (pcil->date.month < pcir->date.month) ? TRUE :
1244 (pcil->date.month > pcir->date.month) ? FALSE :
1245 (pcil->date.day < pcir->date.day) ? TRUE :
1246 (pcil->date.day > pcir->date.day) ? FALSE :
1247 (pcil->time.hours < pcir->time.hours) ? TRUE :
1248 (pcil->time.hours > pcir->time.hours) ? FALSE :
1249 (pcil->time.minutes < pcir->time.minutes) ? TRUE :
1250 (pcil->time.minutes > pcir->time.minutes) ? FALSE :
1251 (pcil->time.seconds < pcir->time.seconds) ? TRUE :
1252 (pcil->time.seconds > pcir->time.seconds) ? FALSE :
1253 FALSE) {
1254 pcil->flags |= CNRITEM_OLDER;
1255 pcir->flags |= CNRITEM_NEWER;
1256 if (pch != szBuf) {
1257 strcpy(pch, ", ");
1258 pch += 2;
1259 }
1260 strcpy(pch, GetPString(IDS_OLDERTEXT));
1261 pch += 5;
1262 }
1263 pcil->pszSubject = *szBuf ?
1264 xstrdup(szBuf, pszSrcFile, __LINE__) :
1265 NullStr;
1266
1267 } // if on both sides
1268
1269 if (x <= 0) {
1270 free(filesl[l]);
1271 l++;
1272 }
1273
1274 if (x >= 0) {
1275 free(filesr[r]);
1276 r++;
1277 }
1278
1279 // Ensure empty buffers point somewhere
1280 if (!pcil->pszFileName) {
1281 pcil->pszFileName = NullStr;
1282 pcil->pszDisplayName = pcil->pszFileName;
1283 }
1284
1285 if (!pcir->pszFileName) {
1286 pcir->pszFileName = NullStr;
1287 pcir->pszDisplayName = pcir->pszFileName;
1288 }
1289
1290 pcil->rc.pszIcon = pcil->pszDisplayName;
1291 pcir->rc.pszIcon = pcir->pszDisplayName;
1292
1293 pcil->pszLongName = NullStr;
1294 pcir->pszLongName = NullStr;
1295
1296 if (!pcil->pszSubject)
1297 pcil->pszSubject = NullStr;
1298 if (!pcir->pszSubject)
1299 pcil->pszSubject = NullStr;
1300
1301 if (!pcil->pszDispAttr)
1302 pcil->pszDispAttr = NullStr;
1303 if (!pcir->pszDispAttr)
1304 pcil->pszDispAttr = NullStr;
1305
1306 // fixme to be time based - every 2 sec should be OK
1307 if (!(cntr % 500))
1308 DosSleep(1);
1309 else if (!(cntr % 50))
1310 DosSleep(1);
1311
1312 cntr++;
1313
1314 pcil = (PCNRITEM) pcil->rc.preccNextRecord;
1315 pcir = (PCNRITEM) pcir->rc.preccNextRecord;
1316
1317 } // while filling left or right
1318
1319 if (filesl)
1320 free(filesl); // Free header - have already freed elements
1321 filesl = NULL;
1322 if (filesr)
1323 free(filesr);
1324 filesr = NULL;
1325 // Insert 'em
1326 WinSendMsg(cmp->hwnd, UM_CONTAINERDIR, MPVOID, MPVOID);
1327
1328 memset(&ri, 0, sizeof(RECORDINSERT));
1329 ri.cb = sizeof(RECORDINSERT);
1330 ri.pRecordOrder = (PRECORDCORE) CMA_END;
1331 ri.pRecordParent = (PRECORDCORE) NULL;
1332 ri.zOrder = (ULONG) CMA_TOP;
1333 ri.cRecordsInsert = recsNeeded;
1334 ri.fInvalidateRecord = FALSE;
1335 if (!WinSendMsg(hwndLeft, CM_INSERTRECORD,
1336 MPFROMP(pcilFirst), MPFROMP(&ri))) {
1337 Win_Error(hwndLeft, cmp->hwnd, pszSrcFile, __LINE__, "CM_INSERTRECORD");
1338 FreeCnrItemList(hwndLeft, pcilFirst);
1339 numfilesl = 0;
1340 }
1341
1342 memset(&ri, 0, sizeof(RECORDINSERT));
1343 ri.cb = sizeof(RECORDINSERT);
1344 ri.pRecordOrder = (PRECORDCORE) CMA_END;
1345 ri.pRecordParent = (PRECORDCORE) NULL;
1346 ri.zOrder = (ULONG) CMA_TOP;
1347 ri.cRecordsInsert = recsNeeded;
1348 ri.fInvalidateRecord = FALSE;
1349
1350 if (!WinSendMsg(hwndRight, CM_INSERTRECORD,
1351 MPFROMP(pcirFirst), MPFROMP(&ri))) {
1352 Win_Error(hwndRight, cmp->hwnd, pszSrcFile, __LINE__, "CM_INSERTRECORD");
1353 RemoveCnrItems(hwndLeft, NULL, 0, CMA_FREE | CMA_INVALIDATE);
1354 FreeCnrItemList(hwndRight, pcirFirst);
1355 numfilesr = 0;
1356 }
1357
1358 cmp->cmp->totalleft = numfilesl;
1359 cmp->cmp->totalright = numfilesr;
1360
1361 } // if recsNeeded
1362
1363 Deselect(hwndLeft);
1364 Deselect(hwndRight);
1365
1366 if (!PostMsg(cmp->hwnd, UM_CONTAINER_FILLED, MPVOID, MPVOID))
1367 WinSendMsg(cmp->hwnd, UM_CONTAINER_FILLED, MPVOID, MPVOID);
1368 notified = TRUE;
1369
1370 if (filesl)
1371 FreeList((CHAR **)filesl); // Must have failed to create container
1372 if (filesr)
1373 FreeList((CHAR **)filesr);
1374
1375 WinDestroyMsgQueue(hmq);
1376 }
1377 DecrThreadUsage();
1378 WinTerminate(hab);
1379 }
1380 if (!notified)
1381 PostMsg(cmp->hwnd, UM_CONTAINER_FILLED, MPVOID, MPVOID);
1382 free(cmp);
1383 DosPostEventSem(CompactSem);
1384}
1385
1386// fixme to be gone - use variable
1387#define hwndLeft (WinWindowFromID(hwnd,COMP_LEFTDIR))
1388#define hwndRight (WinWindowFromID(hwnd,COMP_RIGHTDIR))
1389
1390//=== CompareDlgProc() Compare directories dialog procedure ===
1391
1392MRESULT EXPENTRY CompareDlgProc(HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2)
1393{
1394 COMPARE *cmp;
1395 BOOL temp;
1396
1397 static HPOINTER hptr;
1398
1399 switch (msg) {
1400 case WM_INITDLG:
1401 cmp = (COMPARE *) mp2;
1402 if (!cmp) {
1403 Runtime_Error2(pszSrcFile, __LINE__, IDS_NODATATEXT);
1404 WinDismissDlg(hwnd, 0);
1405 }
1406 else {
1407 if (!hptr)
1408 hptr = WinLoadPointer(HWND_DESKTOP, FM3ModHandle, COMPARE_ICON);
1409 WinDefDlgProc(hwnd, WM_SETICON, MPFROMLONG(hptr), MPVOID);
1410 cmp->hwnd = hwnd;
1411 WinSetWindowPtr(hwnd, QWL_USER, (PVOID) cmp);
1412 SetCnrCols(hwndLeft, TRUE);
1413 SetCnrCols(hwndRight, TRUE);
1414 WinSendMsg(hwnd, UM_SETUP, MPVOID, MPVOID);
1415 WinSendMsg(hwnd, UM_SETDIR, MPVOID, MPVOID);
1416 PostMsg(hwnd, UM_STRETCH, MPVOID, MPVOID);
1417 {
1418 USHORT ids[] = { COMP_LEFTDIR, COMP_RIGHTDIR, COMP_TOTALLEFT,
1419 COMP_TOTALRIGHT, COMP_SELLEFT, COMP_SELRIGHT,
1420 0
1421 };
1422 INT x;
1423
1424 for (x = 0; ids[x]; x++)
1425 SetPresParams(WinWindowFromID(hwnd, ids[x]),
1426 &RGBGREY,
1427 &RGBBLACK, &RGBBLACK, GetPString(IDS_8HELVTEXT));
1428 }
1429 }
1430 break;
1431
1432 case UM_STRETCH:
1433 {
1434 SWP swp, swpC;
1435 LONG titl, szbx, szby, sz;
1436 HWND hwndActive;
1437
1438 WinQueryWindowPos(hwnd, &swp);
1439 if (!(swp.fl & (SWP_HIDE | SWP_MINIMIZE))) {
1440 hwndActive = WinQueryFocus(HWND_DESKTOP);
1441 szbx = SysVal(SV_CXSIZEBORDER);
1442 szby = SysVal(SV_CYSIZEBORDER);
1443 titl = SysVal(SV_CYTITLEBAR);
1444 titl += 26;
1445 swp.cx -= (szbx * 2);
1446 sz = (swp.cx / 8);
1447 WinQueryWindowPos(WinWindowFromID(hwnd, COMP_LEFTDIR), &swpC);
1448 WinSetWindowPos(WinWindowFromID(hwnd, COMP_LEFTDIR), HWND_TOP,
1449 szbx + 6,
1450 swpC.y,
1451 (swp.cx / 2) - (szbx + 6),
1452 ((swp.cy - swpC.y) - titl) - szby,
1453 SWP_MOVE | SWP_SIZE);
1454 WinSetWindowPos(WinWindowFromID(hwnd, COMP_RIGHTDIR), HWND_TOP,
1455 (swp.cx / 2) + (szbx + 6),
1456 swpC.y,
1457 (swp.cx / 2) - (szbx + 6),
1458 ((swp.cy - swpC.y) - titl) - szby,
1459 SWP_MOVE | SWP_SIZE);
1460 WinSetWindowPos(WinWindowFromID(hwnd, COMP_TOTALLEFTHDR), HWND_TOP,
1461 szbx + 6,
1462 ((swp.cy - titl) - szby) + 4,
1463 sz - (szbx + 6), 20, SWP_MOVE | SWP_SIZE);
1464 WinSetWindowPos(WinWindowFromID(hwnd, COMP_TOTALLEFT), HWND_TOP,
1465 sz + (szbx + 6),
1466 ((swp.cy - titl) - szby) + 4,
1467 sz - (szbx + 6), 20, SWP_MOVE | SWP_SIZE);
1468 WinSetWindowPos(WinWindowFromID(hwnd, COMP_SELLEFTHDR), HWND_TOP,
1469 (sz * 2) + (szbx + 6),
1470 ((swp.cy - titl) - szby) + 4,
1471 sz - (szbx + 6), 20, SWP_MOVE | SWP_SIZE);
1472 WinSetWindowPos(WinWindowFromID(hwnd, COMP_SELLEFT), HWND_TOP,
1473 (sz * 3) + (szbx + 6),
1474 ((swp.cy - titl) - szby) + 4,
1475 sz - (szbx + 6), 20, SWP_MOVE | SWP_SIZE);
1476 WinSetWindowPos(WinWindowFromID(hwnd, COMP_TOTALRIGHTHDR), HWND_TOP,
1477 (sz * 4) + (szbx + 6),
1478 ((swp.cy - titl) - szby) + 4,
1479 sz - (szbx + 6), 20, SWP_MOVE | SWP_SIZE);
1480 WinSetWindowPos(WinWindowFromID(hwnd, COMP_TOTALRIGHT), HWND_TOP,
1481 (sz * 5) + (szbx + 6),
1482 ((swp.cy - titl) - szby) + 4,
1483 sz - (szbx + 6), 20, SWP_MOVE | SWP_SIZE);
1484 WinSetWindowPos(WinWindowFromID(hwnd, COMP_SELRIGHTHDR), HWND_TOP,
1485 (sz * 6) + (szbx + 6),
1486 ((swp.cy - titl) - szby) + 4,
1487 sz - (szbx + 6), 20, SWP_MOVE | SWP_SIZE);
1488 WinSetWindowPos(WinWindowFromID(hwnd, COMP_SELRIGHT), HWND_TOP,
1489 (sz * 7) + (szbx + 6),
1490 ((swp.cy - titl) - szby) + 4,
1491 sz - (szbx + 6), 20, SWP_MOVE | SWP_SIZE);
1492 PaintRecessedWindow(WinWindowFromID(hwnd, COMP_TOTALLEFT),
1493 (HPS) 0, FALSE, FALSE);
1494 PaintRecessedWindow(WinWindowFromID(hwnd, COMP_SELLEFT),
1495 (HPS) 0, FALSE, FALSE);
1496 PaintRecessedWindow(WinWindowFromID(hwnd, COMP_TOTALRIGHT),
1497 (HPS) 0, FALSE, FALSE);
1498 PaintRecessedWindow(WinWindowFromID(hwnd, COMP_SELRIGHT),
1499 (HPS) 0, FALSE, FALSE);
1500 PaintRecessedWindow(hwndLeft, (HPS) 0,
1501 (hwndActive == hwndLeft), TRUE);
1502 PaintRecessedWindow(hwndRight, (HPS) 0,
1503 (hwndActive == hwndRight), TRUE);
1504 }
1505 }
1506 return 0;
1507
1508 case WM_ADJUSTWINDOWPOS:
1509 PostMsg(hwnd, UM_STRETCH, MPVOID, MPVOID);
1510 break;
1511
1512 case UM_SETUP:
1513 {
1514 CNRINFO cnri;
1515 BOOL tempsubj;
1516
1517 cmp = INSTDATA(hwnd);
1518 if (cmp) {
1519 cmp->dcd.size = sizeof(DIRCNRDATA);
1520 cmp->dcd.type = DIR_FRAME;
1521 cmp->dcd.hwndFrame = hwnd;
1522 cmp->dcd.hwndClient = hwnd;
1523 cmp->dcd.mask.attrFile = (FILE_DIRECTORY | FILE_ARCHIVED |
1524 FILE_READONLY | FILE_SYSTEM | FILE_HIDDEN);
1525 LoadDetailsSwitches("DirCmp", &cmp->dcd);
1526 cmp->dcd.detailslongname = FALSE;
1527 cmp->dcd.detailsicon = FALSE; // TRUE;
1528 }
1529 memset(&cnri, 0, sizeof(CNRINFO));
1530 cnri.cb = sizeof(CNRINFO);
1531 WinSendDlgItemMsg(hwnd, COMP_LEFTDIR, CM_QUERYCNRINFO,
1532 MPFROMP(&cnri), MPFROMLONG(sizeof(CNRINFO)));
1533 cnri.flWindowAttr |= (CA_OWNERDRAW | CV_MINI);
1534 cnri.xVertSplitbar = DIR_SPLITBAR_OFFSET - 68;
1535 WinSendDlgItemMsg(hwnd, COMP_LEFTDIR, CM_SETCNRINFO, MPFROMP(&cnri),
1536 MPFROMLONG(CMA_FLWINDOWATTR | CMA_XVERTSPLITBAR));
1537 memset(&cnri, 0, sizeof(CNRINFO));
1538 cnri.cb = sizeof(CNRINFO);
1539 WinSendDlgItemMsg(hwnd, COMP_RIGHTDIR, CM_QUERYCNRINFO,
1540 MPFROMP(&cnri), MPFROMLONG(sizeof(CNRINFO)));
1541 cnri.flWindowAttr |= (CA_OWNERDRAW | CV_MINI);
1542 cnri.xVertSplitbar = DIR_SPLITBAR_OFFSET - 54;
1543 WinSendDlgItemMsg(hwnd, COMP_RIGHTDIR, CM_SETCNRINFO, MPFROMP(&cnri),
1544 MPFROMLONG(CMA_FLWINDOWATTR | CMA_XVERTSPLITBAR));
1545 AdjustCnrColRO(hwndLeft, GetPString(IDS_FILENAMECOLTEXT), TRUE, FALSE);
1546 AdjustCnrColRO(hwndLeft, GetPString(IDS_LONGNAMECOLTEXT), TRUE, FALSE);
1547 AdjustCnrColRO(hwndRight, GetPString(IDS_FILENAMECOLTEXT), TRUE, FALSE);
1548 AdjustCnrColRO(hwndRight, GetPString(IDS_LONGNAMECOLTEXT), TRUE, FALSE);
1549 AdjustCnrColsForPref(hwndLeft, cmp->leftdir, &cmp->dcd, TRUE);
1550 tempsubj = cmp->dcd.detailssubject;
1551 cmp->dcd.detailssubject = FALSE;
1552 AdjustCnrColsForPref(hwndRight, cmp->rightdir, &cmp->dcd, TRUE);
1553 if (*cmp->rightlist) {
1554 AdjustCnrColVis(hwndRight, GetPString(IDS_LADATECOLTEXT), FALSE,
1555 FALSE);
1556 AdjustCnrColVis(hwndRight, GetPString(IDS_LATIMECOLTEXT), FALSE,
1557 FALSE);
1558 AdjustCnrColVis(hwndRight, GetPString(IDS_CRDATECOLTEXT), FALSE,
1559 FALSE);
1560 AdjustCnrColVis(hwndRight, GetPString(IDS_CRTIMECOLTEXT), FALSE,
1561 FALSE);
1562 }
1563 cmp->dcd.detailssubject = tempsubj;
1564 }
1565 return 0;
1566
1567 case WM_DRAWITEM:
1568 if (mp2) {
1569 POWNERITEM pown = (POWNERITEM)mp2;
1570 PCNRDRAWITEMINFO pcown;
1571 PCNRITEM pci;
1572
1573 pcown = (PCNRDRAWITEMINFO)pown->hItem;
1574 if (pcown) {
1575 pci = (PCNRITEM) pcown->pRecord;
1576 // 01 Aug 07 SHL if field null or blank, we draw
1577 // fixme to know why - probably to optimize and bypass draw?
1578 if (pci && (INT)pci != -1 && !*pci->pszFileName)
1579 return MRFROMLONG(TRUE);
1580 }
1581 }
1582 return 0;
1583
1584 case UM_CONTAINERHWND:
1585 WinSetDlgItemText(hwnd, COMP_NOTE, GetPString(IDS_COMPHOLDBLDLISTTEXT));
1586 return 0;
1587
1588 case UM_CONTAINERDIR:
1589 WinSetDlgItemText(hwnd, COMP_NOTE, GetPString(IDS_COMPHOLDFILLCNRTEXT));
1590 return 0;
1591
1592 case UM_CONTAINER_FILLED:
1593 cmp = INSTDATA(hwnd);
1594 if (!cmp) {
1595 Runtime_Error(pszSrcFile, __LINE__, "pCompare NULL");
1596 WinDismissDlg(hwnd, 0);
1597 }
1598 else {
1599 CHAR s[81];
1600
1601 cmp->filling = FALSE;
1602 WinEnableWindow(hwndLeft, TRUE);
1603 WinEnableWindow(hwndRight, TRUE);
1604 WinEnableWindowUpdate(hwndLeft, TRUE);
1605 WinEnableWindowUpdate(hwndRight, TRUE);
1606 sprintf(s, " %d", cmp->totalleft);
1607 WinSetDlgItemText(hwnd, COMP_TOTALLEFT, s);
1608 sprintf(s, " %d", cmp->totalright);
1609 WinSetDlgItemText(hwnd, COMP_TOTALRIGHT, s);
1610 sprintf(s, " %d", cmp->selleft);
1611 WinSetDlgItemText(hwnd, COMP_SELLEFT, s);
1612 sprintf(s, " %d", cmp->selright);
1613 WinSetDlgItemText(hwnd, COMP_SELRIGHT, s);
1614 WinEnableWindow(WinWindowFromID(hwnd, DID_OK), TRUE);
1615 WinEnableWindow(WinWindowFromID(hwnd, DID_CANCEL), TRUE);
1616 WinEnableWindow(WinWindowFromID(hwnd, COMP_COLLECT), TRUE);
1617 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTBOTH), TRUE);
1618 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTONE), TRUE);
1619 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTNEWER), TRUE);
1620 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTOLDER), TRUE);
1621 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTBIGGER), TRUE);
1622 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSMALLER), TRUE);
1623 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTBOTH), TRUE);
1624 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTONE), TRUE);
1625 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTNEWER), TRUE);
1626 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTOLDER), TRUE);
1627 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTBIGGER), TRUE);
1628 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTSMALLER), TRUE);
1629 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTALL), TRUE);
1630 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSAMECONTENT), TRUE);
1631 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTIDENTICAL), TRUE);
1632 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSAME), TRUE);
1633 WinEnableWindow(WinWindowFromID(hwnd, IDM_INVERT), TRUE);
1634 WinEnableWindow(WinWindowFromID(hwnd, COMP_SETDIRS), TRUE);
1635 WinEnableWindow(WinWindowFromID(hwnd, COMP_DELETELEFT), TRUE);
1636 WinEnableWindow(WinWindowFromID(hwnd, COMP_FILTER), TRUE);
1637 if (!*cmp->rightlist) {
1638 WinEnableWindow(WinWindowFromID(hwnd, COMP_COPYLEFT), TRUE);
1639 WinEnableWindow(WinWindowFromID(hwnd, COMP_MOVELEFT), TRUE);
1640 WinEnableWindow(WinWindowFromID(hwnd, COMP_DELETERIGHT), TRUE);
1641 WinEnableWindow(WinWindowFromID(hwnd, COMP_COPYRIGHT), TRUE);
1642 WinEnableWindow(WinWindowFromID(hwnd, COMP_MOVERIGHT), TRUE);
1643 }
1644 WinEnableWindow(WinWindowFromID(hwnd, COMP_INCLUDESUBDIRS), TRUE);
1645 if (*cmp->dcd.mask.szMask)
1646 WinSetDlgItemText(hwnd, COMP_NOTE,
1647 GetPString(IDS_COMPREADYFILTEREDTEXT));
1648 else
1649 WinSetDlgItemText(hwnd, COMP_NOTE, GetPString(IDS_COMPREADYTEXT));
1650 }
1651 break;
1652
1653 case WM_INITMENU:
1654 cmp = INSTDATA(hwnd);
1655 if (cmp) {
1656 switch (SHORT1FROMMP(mp1)) {
1657 case IDM_COMMANDSMENU:
1658 SetupCommandMenu(cmp->dcd.hwndLastMenu, hwnd);
1659 break;
1660 }
1661 }
1662 break;
1663
1664 case WM_MENUEND:
1665 cmp = INSTDATA(hwnd);
1666 if (cmp) {
1667 if ((HWND) mp2 == cmp->dcd.hwndLastMenu) {
1668 MarkAll(hwndLeft, TRUE, FALSE, TRUE);
1669 MarkAll(hwndRight, TRUE, FALSE, TRUE);
1670 WinDestroyWindow(cmp->dcd.hwndLastMenu);
1671 cmp->dcd.hwndLastMenu = (HWND) 0;
1672 }
1673 }
1674 break;
1675
1676 case WM_CONTROL:
1677 switch (SHORT1FROMMP(mp1)) {
1678 case COMP_INCLUDESUBDIRS:
1679 switch (SHORT2FROMMP(mp1)) {
1680 case BN_CLICKED:
1681 cmp = INSTDATA(hwnd);
1682 if (cmp)
1683 *cmp->rightlist = 0;
1684 PostMsg(hwnd, UM_SETUP, MPVOID, MPVOID);
1685 PostMsg(hwnd, UM_SETDIR, MPVOID, MPVOID);
1686 break;
1687 }
1688 break;
1689 case COMP_HIDENOTSELECTED:
1690 switch (SHORT2FROMMP(mp1)) {
1691 case BN_CLICKED:
1692 WinSendMsg(hwnd, UM_HIDENOTSELECTED, MPVOID, MPVOID);
1693 break;
1694 }
1695 break;
1696
1697 case COMP_LEFTDIR:
1698 case COMP_RIGHTDIR:
1699 switch (SHORT2FROMMP(mp1)) {
1700 case CN_KILLFOCUS:
1701 PaintRecessedWindow(WinWindowFromID(hwnd, SHORT1FROMMP(mp1)),
1702 (HPS) 0, FALSE, TRUE);
1703 break;
1704
1705 case CN_SETFOCUS:
1706 PaintRecessedWindow(WinWindowFromID(hwnd, SHORT1FROMMP(mp1)),
1707 (HPS) 0, TRUE, TRUE);
1708 break;
1709
1710 case CN_ENTER:
1711 if (mp2) {
1712
1713 PCNRITEM pci = (PCNRITEM) ((PNOTIFYRECORDENTER) mp2)->pRecord;
1714 HWND hwndCnr = WinWindowFromID(hwnd, SHORT1FROMMP(mp1));
1715
1716 SetShiftState();
1717 if (pci) {
1718 if (pci->rc.flRecordAttr & CRA_INUSE || !pci || !*pci->pszFileName)
1719 break;
1720 WinSendMsg(hwndCnr, CM_SETRECORDEMPHASIS, MPFROMP(pci),
1721 MPFROM2SHORT(TRUE, CRA_INUSE));
1722 if (pci->attrFile & FILE_DIRECTORY) {
1723 if ((shiftstate & (KC_CTRL | KC_SHIFT)) == (KC_CTRL | KC_SHIFT))
1724 OpenObject(pci->pszFileName, Settings, hwnd);
1725 else
1726 OpenObject(pci->pszFileName, Default, hwnd);
1727 }
1728 else
1729 DefaultViewKeys(hwnd, hwnd, HWND_DESKTOP, NULL,
1730 pci->pszFileName);
1731 WinSendMsg(hwndCnr, CM_SETRECORDEMPHASIS,
1732 MPFROMP(pci),
1733 MPFROM2SHORT(FALSE, CRA_INUSE |
1734 ((fUnHilite) ? CRA_SELECTED : 0)));
1735 }
1736 }
1737 break;
1738
1739 case CN_CONTEXTMENU:
1740 cmp = INSTDATA(hwnd);
1741 if (cmp) {
1742
1743 PCNRITEM pci = (PCNRITEM) mp2;
1744 USHORT id = COMP_CNRMENU;
1745
1746 if (cmp->dcd.hwndLastMenu)
1747 WinDestroyWindow(cmp->dcd.hwndLastMenu);
1748 cmp->dcd.hwndLastMenu = (HWND) 0;
1749 cmp->hwndCalling = WinWindowFromID(hwnd, SHORT1FROMMP(mp1));
1750 if (pci) {
1751 if (!pci || !*pci->pszFileName || *cmp->rightlist)
1752 break;
1753 id = COMP_MENU;
1754 WinSendMsg(cmp->hwndCalling, CM_SETRECORDEMPHASIS,
1755 MPFROMP(pci), MPFROM2SHORT(TRUE, CRA_CURSORED));
1756 }
1757 cmp->dcd.hwndLastMenu = WinLoadMenu(HWND_DESKTOP, FM3ModHandle, id);
1758 if (cmp->dcd.hwndLastMenu) {
1759 if (id == COMP_CNRMENU) {
1760 if (SHORT1FROMMP(mp1) == COMP_RIGHTDIR)
1761 WinSendMsg(cmp->dcd.hwndLastMenu, MM_DELETEITEM,
1762 MPFROM2SHORT(IDM_SHOWSUBJECT, FALSE), MPVOID);
1763 SetDetailsSwitches(cmp->dcd.hwndLastMenu, &cmp->dcd);
1764 if (SHORT1FROMMP(mp1) == COMP_LEFTDIR)
1765 WinSendMsg(cmp->dcd.hwndLastMenu, MM_DELETEITEM,
1766 MPFROM2SHORT(IDM_LOADLISTFILE, 0), MPVOID);
1767 else if (*cmp->rightlist)
1768 WinSendMsg(cmp->dcd.hwndLastMenu, MM_DELETEITEM,
1769 MPFROM2SHORT(IDM_SAVELISTFILE, 0), MPVOID);
1770 }
1771 PopupMenu(hwnd, hwnd, cmp->dcd.hwndLastMenu);
1772 }
1773 }
1774 break;
1775
1776 case CN_INITDRAG:
1777 cmp = INSTDATA(hwnd);
1778 if (*cmp->rightlist && SHORT1FROMMP(mp1) == COMP_RIGHTDIR)
1779 break;
1780 DoFileDrag(WinWindowFromID(hwnd, SHORT1FROMMP(mp1)),
1781 (HWND) 0, mp2, NULL, NULL, TRUE);
1782 break;
1783
1784 case CN_BEGINEDIT:
1785 case CN_REALLOCPSZ:
1786 // fixme to be gone - field edits not allowed
1787 Runtime_Error(pszSrcFile, __LINE__,
1788 "CN_BEGINEDIT/CN_REALLOCPSZ unexpected");
1789 break;
1790
1791 case CN_EMPHASIS:
1792 {
1793 PNOTIFYRECORDEMPHASIS pre = mp2;
1794 PCNRITEM pci;
1795
1796 if (pre->fEmphasisMask & CRA_SELECTED) {
1797 pci = (PCNRITEM) pre->pRecord;
1798 if (pci) {
1799 if (!pci || !*pci->pszFileName) {
1800 if (pci->rc.flRecordAttr & CRA_SELECTED)
1801 WinSendDlgItemMsg(hwnd, SHORT1FROMMP(mp1),
1802 CM_SETRECORDEMPHASIS,
1803 MPFROMP(pci),
1804 MPFROM2SHORT(FALSE, CRA_SELECTED));
1805 }
1806 else {
1807
1808 CHAR s[81];
1809
1810 cmp = INSTDATA(hwnd);
1811 if (pci->rc.flRecordAttr & CRA_SELECTED) {
1812 if (SHORT1FROMMP(mp1) == COMP_LEFTDIR)
1813 cmp->selleft++;
1814 else
1815 cmp->selright++;
1816 }
1817 else {
1818 if (SHORT1FROMMP(mp1) == COMP_LEFTDIR) {
1819 if (cmp->selleft)
1820 cmp->selleft--;
1821 }
1822 else {
1823 if (cmp->selright)
1824 cmp->selright--;
1825 }
1826 }
1827 if (SHORT1FROMMP(mp1) == COMP_LEFTDIR) {
1828 if (WinIsWindowEnabled(hwndLeft) || !(cmp->selleft % 50)) {
1829 sprintf(s, " %d", cmp->selleft);
1830 WinSetDlgItemText(hwnd, COMP_SELLEFT, s);
1831 }
1832 }
1833 else {
1834 if (WinIsWindowEnabled(hwndRight) || !(cmp->selright % 50)) {
1835 sprintf(s, " %d", cmp->selright);
1836 WinSetDlgItemText(hwnd, COMP_SELRIGHT, s);
1837 }
1838 }
1839 }
1840 }
1841 }
1842 }
1843 break;
1844
1845 case CN_SCROLL:
1846 cmp = INSTDATA(hwnd);
1847 if (!cmp->forcescroll) {
1848
1849 PNOTIFYSCROLL pns = mp2;
1850
1851 if (pns->fScroll & CMA_VERTICAL) {
1852 cmp->forcescroll = TRUE;
1853 WinSendDlgItemMsg(hwnd, (SHORT1FROMMP(mp1) == COMP_LEFTDIR) ?
1854 COMP_RIGHTDIR : COMP_LEFTDIR,
1855 CM_SCROLLWINDOW, MPFROMSHORT(CMA_VERTICAL),
1856 MPFROMLONG(pns->lScrollInc));
1857 cmp->forcescroll = FALSE;
1858 }
1859 }
1860 break;
1861 }
1862 break; // COMP_RIGHTDIR
1863 }
1864 return 0; // WM_CONTROL
1865
1866 case UM_SETDIR:
1867 cmp = INSTDATA(hwnd);
1868 if (cmp) {
1869
1870 COMPARE *forthread;
1871 CNRINFO cnri;
1872
1873 cmp->includesubdirs = WinQueryButtonCheckstate(hwnd,
1874 COMP_INCLUDESUBDIRS);
1875 memset(&cnri, 0, sizeof(CNRINFO));
1876 cnri.cb = sizeof(CNRINFO);
1877 cnri.pszCnrTitle = cmp->leftdir;
1878 cnri.flWindowAttr = CV_DETAIL | CV_MINI |
1879 CA_CONTAINERTITLE | CA_TITLESEPARATOR |
1880 CA_DETAILSVIEWTITLES | CA_OWNERDRAW;
1881 WinSendDlgItemMsg(hwnd, COMP_LEFTDIR, CM_SETCNRINFO, MPFROMP(&cnri),
1882 MPFROMLONG(CMA_CNRTITLE | CMA_FLWINDOWATTR));
1883 cnri.pszCnrTitle = cmp->rightdir;
1884 WinSendDlgItemMsg(hwnd, COMP_RIGHTDIR, CM_SETCNRINFO, MPFROMP(&cnri),
1885 MPFROMLONG(CMA_CNRTITLE | CMA_FLWINDOWATTR));
1886 WinCheckButton(hwnd, COMP_HIDENOTSELECTED, 0);
1887 cmp->filling = TRUE;
1888 forthread = xmalloc(sizeof(COMPARE), pszSrcFile, __LINE__);
1889 if (!forthread)
1890 WinDismissDlg(hwnd, 0);
1891 else {
1892 *forthread = *cmp;
1893 forthread->cmp = cmp;
1894 if (_beginthread(FillCnrsThread, NULL, 122880, (PVOID) forthread) ==
1895 -1) {
1896 Runtime_Error(pszSrcFile, __LINE__,
1897 GetPString(IDS_COULDNTSTARTTHREADTEXT));
1898 WinDismissDlg(hwnd, 0);
1899 free(forthread);
1900 }
1901 else {
1902 WinEnableWindowUpdate(hwndLeft, FALSE);
1903 WinEnableWindowUpdate(hwndRight, FALSE);
1904 cmp->selleft = cmp->selright = 0;
1905 WinSetDlgItemText(hwnd, COMP_SELLEFT, "0");
1906 WinSetDlgItemText(hwnd, COMP_SELRIGHT, "0");
1907 WinSetDlgItemText(hwnd, COMP_TOTALLEFT, "0");
1908 WinSetDlgItemText(hwnd, COMP_TOTALRIGHT, "0");
1909 WinSetDlgItemText(hwnd, COMP_NOTE,
1910 GetPString(IDS_COMPHOLDREADDISKTEXT));
1911 WinEnableWindow(hwndRight, FALSE);
1912 WinEnableWindow(hwndLeft, FALSE);
1913 WinEnableWindow(WinWindowFromID(hwnd, DID_OK), FALSE);
1914 WinEnableWindow(WinWindowFromID(hwnd, DID_CANCEL), FALSE);
1915 WinEnableWindow(WinWindowFromID(hwnd, COMP_COLLECT), FALSE);
1916 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTBOTH), FALSE);
1917 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTONE), FALSE);
1918 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTNEWER), FALSE);
1919 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTOLDER), FALSE);
1920 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTBIGGER), FALSE);
1921 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSMALLER), FALSE);
1922 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTBOTH), FALSE);
1923 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTONE), FALSE);
1924 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTNEWER), FALSE);
1925 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTOLDER), FALSE);
1926 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTBIGGER), FALSE);
1927 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTSMALLER), FALSE);
1928 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTALL), FALSE);
1929 WinEnableWindow(WinWindowFromID(hwnd, COMP_INCLUDESUBDIRS), FALSE);
1930 WinEnableWindow(WinWindowFromID(hwnd, COMP_SETDIRS), FALSE);
1931 WinEnableWindow(WinWindowFromID(hwnd, COMP_DELETELEFT), FALSE);
1932 WinEnableWindow(WinWindowFromID(hwnd, COMP_DELETERIGHT), FALSE);
1933 WinEnableWindow(WinWindowFromID(hwnd, COMP_COPYLEFT), FALSE);
1934 WinEnableWindow(WinWindowFromID(hwnd, COMP_MOVELEFT), FALSE);
1935 WinEnableWindow(WinWindowFromID(hwnd, COMP_COPYRIGHT), FALSE);
1936 WinEnableWindow(WinWindowFromID(hwnd, COMP_MOVERIGHT), FALSE);
1937 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSAMECONTENT),
1938 FALSE);
1939 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTIDENTICAL), FALSE);
1940 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSAME), FALSE);
1941 WinEnableWindow(WinWindowFromID(hwnd, IDM_INVERT), FALSE);
1942 WinEnableWindow(WinWindowFromID(hwnd, COMP_FILTER), FALSE);
1943 }
1944 }
1945 }
1946 return 0;
1947
1948 case UM_FILTER:
1949 cmp = INSTDATA(hwnd);
1950 if (cmp) {
1951 if (mp1) {
1952 DosEnterCritSec();
1953 SetMask((CHAR *) mp1, &cmp->dcd.mask);
1954 DosExitCritSec();
1955 }
1956 cmp->dcd.suspendview = 1;
1957 WinSendMsg(hwndLeft, CM_FILTER, MPFROMP(Filter),
1958 MPFROMP(&cmp->dcd.mask));
1959 WinSendMsg(hwndRight, CM_FILTER, MPFROMP(Filter),
1960 MPFROMP(&cmp->dcd.mask));
1961 cmp->dcd.suspendview = 0;
1962 if (*cmp->dcd.mask.szMask)
1963 WinSetDlgItemText(hwnd, COMP_NOTE,
1964 GetPString(IDS_COMPREADYFILTEREDTEXT));
1965 else
1966 WinSetDlgItemText(hwnd, COMP_NOTE, GetPString(IDS_COMPREADYTEXT));
1967 }
1968 return 0;
1969
1970 case UM_HIDENOTSELECTED:
1971 cmp = INSTDATA(hwnd);
1972 if (cmp) {
1973 USHORT wantHide = WinQueryButtonCheckstate(hwnd,
1974 COMP_HIDENOTSELECTED);
1975
1976 cmp->dcd.suspendview = 1;
1977 if (wantHide) {
1978 BOOL needRefresh = FALSE;
1979 HWND hwndl = WinWindowFromID(cmp->hwnd, COMP_LEFTDIR);
1980 HWND hwndr = WinWindowFromID(cmp->hwnd, COMP_RIGHTDIR);
1981 PCNRITEM pcil = WinSendMsg(hwndl, CM_QUERYRECORD, MPVOID,
1982 MPFROM2SHORT(CMA_FIRST, CMA_ITEMORDER));
1983 PCNRITEM pcir = WinSendMsg(hwndr, CM_QUERYRECORD, MPVOID,
1984 MPFROM2SHORT(CMA_FIRST, CMA_ITEMORDER));
1985
1986 while (pcil && (INT) pcil != -1 && pcir && (INT) pcir != -1) {
1987 if (~pcil->rc.flRecordAttr & CRA_SELECTED &&
1988 ~pcir->rc.flRecordAttr & CRA_SELECTED) {
1989 pcil->rc.flRecordAttr |= CRA_FILTERED;
1990 pcir->rc.flRecordAttr |= CRA_FILTERED;
1991 needRefresh = TRUE;
1992 }
1993 pcil = WinSendMsg(hwndl, CM_QUERYRECORD, MPFROMP(pcil),
1994 MPFROM2SHORT(CMA_NEXT, CMA_ITEMORDER));
1995 pcir = WinSendMsg(hwndr, CM_QUERYRECORD, MPFROMP(pcir),
1996 MPFROM2SHORT(CMA_NEXT, CMA_ITEMORDER));
1997 } // while
1998 if (needRefresh) {
1999 WinSendMsg(hwndl, CM_INVALIDATERECORD,
2000 MPVOID, MPFROM2SHORT(0, CMA_REPOSITION));
2001 WinSendMsg(hwndr, CM_INVALIDATERECORD,
2002 MPVOID, MPFROM2SHORT(0, CMA_REPOSITION));
2003 }
2004 }
2005 else {
2006 WinSendMsg(hwndLeft, CM_FILTER, MPFROMP(Filter),
2007 MPFROMP(&cmp->dcd.mask));
2008 WinSendMsg(hwndRight, CM_FILTER, MPFROMP(Filter),
2009 MPFROMP(&cmp->dcd.mask));
2010 }
2011 cmp->dcd.suspendview = 0;
2012 if (*cmp->dcd.mask.szMask)
2013 WinSetDlgItemText(hwnd, COMP_NOTE,
2014 GetPString(IDS_COMPREADYFILTEREDTEXT));
2015 else
2016 WinSetDlgItemText(hwnd, COMP_NOTE, GetPString(IDS_COMPREADYTEXT));
2017 }
2018 return 0;
2019
2020 case WM_COMMAND:
2021 switch (SHORT1FROMMP(mp1)) {
2022 case IDM_COMPARE:
2023 cmp = INSTDATA(hwnd);
2024 if (cmp) {
2025
2026 PCNRITEM pci;
2027 CHAR ofile[CCHMAXPATH];
2028
2029 pci = (PCNRITEM) WinSendMsg(cmp->hwndCalling,
2030 CM_QUERYRECORDEMPHASIS,
2031 MPFROMLONG(CMA_FIRST),
2032 MPFROMSHORT(CRA_CURSORED));
2033 // 01 Aug 07 SHL
2034 if (pci && *pci->pszFileName) {
2035 if (cmp->hwndCalling == hwndLeft)
2036 strcpy(ofile, cmp->rightdir);
2037 else
2038 strcpy(ofile, cmp->leftdir);
2039 if (ofile[strlen(ofile) - 1] != '\\')
2040 strcat(ofile, "\\");
2041 strcat(ofile, pci->pszDisplayName);
2042 if (*compare) {
2043 CHAR *fakelist[3];
2044 fakelist[0] = pci->pszFileName;
2045 fakelist[1] = ofile;
2046 fakelist[2] = NULL;
2047 ExecOnList(hwnd, compare,
2048 WINDOWED | SEPARATEKEEP, NULL, fakelist, NULL);
2049 }
2050 else {
2051 FCOMPARE fc;
2052 memset(&fc, 0, sizeof(fc));
2053 fc.size = sizeof(fc);
2054 fc.hwndParent = hwnd;
2055 strcpy(fc.file1, pci->pszFileName);
2056 strcpy(fc.file2, ofile);
2057 WinDlgBox(HWND_DESKTOP, hwnd,
2058 CFileDlgProc, FM3ModHandle, FCMP_FRAME, (PVOID) & fc);
2059 }
2060 }
2061 }
2062 break;
2063
2064 case COMP_FILTER:
2065 case IDM_FILTER:
2066 cmp = INSTDATA(hwnd);
2067 if (cmp) {
2068
2069 BOOL empty = FALSE;
2070 PCNRITEM pci;
2071 CHAR *p;
2072 BOOL temp;
2073
2074 if (!*cmp->dcd.mask.szMask) {
2075 empty = TRUE;
2076 temp = fSelectedAlways;
2077 fSelectedAlways = TRUE;
2078 pci = (PCNRITEM)CurrentRecord(hwnd);
2079 fSelectedAlways = temp;
2080 // 01 Aug 07 SHL
2081 if (pci && ~pci->attrFile & FILE_DIRECTORY) {
2082 p = strrchr(pci->pszFileName, '\\');
2083 if (p) {
2084 p++;
2085 strcpy(cmp->dcd.mask.szMask, p);
2086 }
2087 }
2088 }
2089 cmp->dcd.mask.fNoAttribs = TRUE;
2090 cmp->dcd.mask.attrFile = ALLATTRS;
2091 cmp->dcd.mask.antiattr = 0;
2092 if (WinDlgBox(HWND_DESKTOP, hwnd, PickMaskDlgProc,
2093 FM3ModHandle, MSK_FRAME, MPFROMP(&cmp->dcd.mask))) {
2094 cmp->dcd.mask.attrFile = ALLATTRS;
2095 cmp->dcd.mask.antiattr = 0;
2096 WinSendMsg(hwnd, UM_FILTER, MPVOID, MPVOID);
2097 }
2098 else if (empty) {
2099 *cmp->dcd.mask.szMask = 0;
2100 cmp->dcd.mask.attrFile = ALLATTRS;
2101 cmp->dcd.mask.antiattr = 0;
2102 }
2103 }
2104 break;
2105
2106 case IDM_SHOWSUBJECT:
2107 case IDM_SHOWEAS:
2108 case IDM_SHOWSIZE:
2109 case IDM_SHOWLWDATE:
2110 case IDM_SHOWLWTIME:
2111 case IDM_SHOWLADATE:
2112 case IDM_SHOWLATIME:
2113 case IDM_SHOWCRDATE:
2114 case IDM_SHOWCRTIME:
2115 case IDM_SHOWATTR:
2116 cmp = INSTDATA(hwnd);
2117 if (cmp) {
2118
2119 DIRCNRDATA dcd1;
2120 BOOL tempsubj;
2121
2122 dcd1 = cmp->dcd;
2123 AdjustDetailsSwitches(hwndLeft,
2124 (HWND) 0, SHORT1FROMMP(mp1),
2125 cmp->leftdir, "DirCmp", &cmp->dcd, TRUE);
2126 tempsubj = cmp->dcd.detailssubject;
2127 cmp->dcd = dcd1;
2128 cmp->dcd.detailssubject = FALSE;
2129 AdjustDetailsSwitches(hwndRight,
2130 cmp->dcd.hwndLastMenu, SHORT1FROMMP(mp1),
2131 cmp->rightdir, "DirCmp", &cmp->dcd, TRUE);
2132 cmp->dcd.detailssubject = tempsubj;
2133 }
2134 break;
2135
2136 case IDM_LOADLISTFILE:
2137 cmp = INSTDATA(hwnd);
2138 if (cmp) {
2139
2140 CHAR fullname[CCHMAXPATH];
2141
2142 strcpy(fullname, "*.PMD");
2143 if (insert_filename(HWND_DESKTOP, fullname, TRUE, FALSE) &&
2144 *fullname && !strchr(fullname, '*') && !strchr(fullname, '?')) {
2145 strcpy(cmp->rightlist, fullname);
2146 PostMsg(hwnd, UM_SETUP, MPVOID, MPVOID);
2147 PostMsg(hwnd, UM_SETDIR, MPVOID, MPVOID);
2148 }
2149 }
2150 break;
2151
2152 case IDM_SAVELISTFILE:
2153 cmp = INSTDATA(hwnd);
2154 if (cmp) {
2155
2156 SNAPSTUFF *sf;
2157 CHAR fullname[CCHMAXPATH];
2158
2159 strcpy(fullname, "*.PMD");
2160 if (export_filename(HWND_DESKTOP, fullname, 1) && *fullname &&
2161 !strchr(fullname, '*') && !strchr(fullname, '?')) {
2162 sf = xmallocz(sizeof(SNAPSTUFF), pszSrcFile, __LINE__);
2163 if (sf) {
2164 strcpy(sf->filename, fullname);
2165 if (hwndLeft == cmp->hwndCalling)
2166 strcpy(sf->dirname, cmp->leftdir);
2167 else
2168 strcpy(sf->dirname, cmp->rightdir);
2169 sf->recurse = cmp->includesubdirs;
2170 if (_beginthread(StartSnap, NULL, 65536, (PVOID) sf) == -1) {
2171 Runtime_Error(pszSrcFile, __LINE__,
2172 GetPString(IDS_COULDNTSTARTTHREADTEXT));
2173 free(sf);
2174 }
2175 }
2176 }
2177 }
2178 break;
2179
2180 case COMP_SETDIRS:
2181 cmp = INSTDATA(hwnd);
2182 if (cmp) {
2183
2184 WALK2 wa;
2185
2186 memset(&wa, 0, sizeof(wa));
2187 wa.size = sizeof(wa);
2188 strcpy(wa.szCurrentPath1, cmp->leftdir);
2189 strcpy(wa.szCurrentPath2, cmp->rightdir);
2190 if (WinDlgBox(HWND_DESKTOP, hwnd, WalkTwoCmpDlgProc,
2191 FM3ModHandle, WALK2_FRAME,
2192 MPFROMP(&wa)) &&
2193 !IsFile(wa.szCurrentPath1) &&
2194 !IsFile(wa.szCurrentPath2)) {
2195 strcpy(cmp->leftdir, wa.szCurrentPath1);
2196 strcpy(cmp->rightdir, wa.szCurrentPath2);
2197 *cmp->rightlist = 0;
2198 PostMsg(hwnd, UM_SETUP, MPVOID, MPVOID);
2199 PostMsg(hwnd, UM_SETDIR, MPVOID, MPVOID);
2200 }
2201 }
2202 break;
2203
2204 case COMP_COPYLEFT:
2205 case COMP_MOVELEFT:
2206 case COMP_COPYRIGHT:
2207 case COMP_MOVERIGHT:
2208 case COMP_DELETELEFT:
2209 case COMP_DELETERIGHT:
2210 cmp = INSTDATA(hwnd);
2211 if (cmp) {
2212
2213 COMPARE *forthread;
2214
2215 cmp->filling = TRUE;
2216 forthread = xmalloc(sizeof(COMPARE), pszSrcFile, __LINE__);
2217 if (forthread) {
2218 *forthread = *cmp;
2219 forthread->cmp = cmp;
2220 forthread->action = SHORT1FROMMP(mp1);
2221 if (_beginthread(ActionCnrThread, NULL, 122880, (PVOID) forthread)
2222 == -1) {
2223 Runtime_Error(pszSrcFile, __LINE__,
2224 GetPString(IDS_COULDNTSTARTTHREADTEXT));
2225 free(forthread);
2226 }
2227 else {
2228 WinEnableWindowUpdate(hwndLeft, FALSE);
2229 WinEnableWindowUpdate(hwndRight, FALSE);
2230 switch (SHORT1FROMMP(mp1)) {
2231 case COMP_DELETELEFT:
2232 case COMP_DELETERIGHT:
2233 WinSetDlgItemText(hwnd, COMP_NOTE,
2234 GetPString(IDS_COMPHOLDDELETINGTEXT));
2235 break;
2236 case COMP_MOVELEFT:
2237 case COMP_MOVERIGHT:
2238 WinSetDlgItemText(hwnd, COMP_NOTE,
2239 GetPString(IDS_COMPHOLDMOVINGTEXT));
2240 break;
2241 case COMP_COPYLEFT:
2242 case COMP_COPYRIGHT:
2243 WinSetDlgItemText(hwnd, COMP_NOTE,
2244 GetPString(IDS_COMPHOLDCOPYINGTEXT));
2245 break;
2246 default:
2247 WinSetDlgItemText(hwnd, COMP_NOTE,
2248 GetPString(IDS_COMPHOLDDUNNOTEXT));
2249 break;
2250 }
2251 WinEnableWindow(hwndRight, FALSE);
2252 WinEnableWindow(hwndLeft, FALSE);
2253 WinEnableWindow(WinWindowFromID(hwnd, DID_OK), FALSE);
2254 WinEnableWindow(WinWindowFromID(hwnd, DID_CANCEL), FALSE);
2255 WinEnableWindow(WinWindowFromID(hwnd, COMP_COLLECT), FALSE);
2256 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTBOTH), FALSE);
2257 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTONE), FALSE);
2258 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTNEWER), FALSE);
2259 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTOLDER), FALSE);
2260 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTBIGGER), FALSE);
2261 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSMALLER), FALSE);
2262 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTBOTH), FALSE);
2263 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTONE), FALSE);
2264 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTNEWER), FALSE);
2265 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTOLDER), FALSE);
2266 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTBIGGER), FALSE);
2267 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTSMALLER),
2268 FALSE);
2269 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTALL), FALSE);
2270 WinEnableWindow(WinWindowFromID(hwnd, COMP_INCLUDESUBDIRS),
2271 FALSE);
2272 WinEnableWindow(WinWindowFromID(hwnd, COMP_SETDIRS), FALSE);
2273 WinEnableWindow(WinWindowFromID(hwnd, COMP_DELETELEFT), FALSE);
2274 WinEnableWindow(WinWindowFromID(hwnd, COMP_DELETERIGHT), FALSE);
2275 WinEnableWindow(WinWindowFromID(hwnd, COMP_COPYLEFT), FALSE);
2276 WinEnableWindow(WinWindowFromID(hwnd, COMP_MOVELEFT), FALSE);
2277 WinEnableWindow(WinWindowFromID(hwnd, COMP_COPYRIGHT), FALSE);
2278 WinEnableWindow(WinWindowFromID(hwnd, COMP_MOVERIGHT), FALSE);
2279 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSAMECONTENT),
2280 FALSE);
2281 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTIDENTICAL),
2282 FALSE);
2283 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSAME), FALSE);
2284 WinEnableWindow(WinWindowFromID(hwnd, IDM_INVERT), FALSE);
2285 WinEnableWindow(WinWindowFromID(hwnd, COMP_FILTER), FALSE);
2286 }
2287 }
2288 }
2289 break;
2290
2291 case DID_OK:
2292 WinDismissDlg(hwnd, 0);
2293 break;
2294 case DID_CANCEL:
2295 WinDismissDlg(hwnd, 1);
2296 break;
2297
2298 case IDM_HELP:
2299 if (hwndHelp)
2300 WinSendMsg(hwndHelp, HM_DISPLAY_HELP,
2301 MPFROM2SHORT(HELP_COMPARE, 0), MPFROMSHORT(HM_RESOURCEID));
2302 break;
2303
2304 case IDM_DESELECTALL:
2305 case IDM_SELECTNEWER:
2306 case IDM_SELECTOLDER:
2307 case IDM_SELECTBIGGER:
2308 case IDM_SELECTSMALLER:
2309 case IDM_DESELECTNEWER:
2310 case IDM_DESELECTOLDER:
2311 case IDM_DESELECTBIGGER:
2312 case IDM_DESELECTSMALLER:
2313 case IDM_DESELECTONE:
2314 case IDM_DESELECTBOTH:
2315 case IDM_SELECTBOTH:
2316 case IDM_SELECTONE:
2317 case IDM_SELECTSAMECONTENT:
2318 case IDM_SELECTIDENTICAL: // Name, size and time
2319 case IDM_SELECTSAME: // Name and size
2320 case IDM_INVERT:
2321 cmp = INSTDATA(hwnd);
2322 if (!cmp)
2323 Runtime_Error2(pszSrcFile, __LINE__, IDS_NODATATEXT);
2324 else {
2325 COMPARE *forthread;
2326
2327 cmp->filling = TRUE;
2328 forthread = xmalloc(sizeof(COMPARE), pszSrcFile, __LINE__);
2329 if (forthread) {
2330 *forthread = *cmp;
2331 forthread->cmp = cmp;
2332 forthread->action = SHORT1FROMMP(mp1);
2333 if (_beginthread(SelectCnrsThread, NULL, 65536, (PVOID) forthread)
2334 == -1) {
2335 Runtime_Error(pszSrcFile, __LINE__,
2336 GetPString(IDS_COULDNTSTARTTHREADTEXT));
2337 free(forthread);
2338 }
2339 else {
2340 WinEnableWindowUpdate(hwndLeft, FALSE);
2341 WinEnableWindowUpdate(hwndRight, FALSE);
2342 switch (SHORT1FROMMP(mp1)) {
2343 case IDM_DESELECTALL:
2344 case IDM_DESELECTNEWER:
2345 case IDM_DESELECTOLDER:
2346 case IDM_DESELECTBIGGER:
2347 case IDM_DESELECTSMALLER:
2348 case IDM_DESELECTONE:
2349 case IDM_DESELECTBOTH:
2350 WinSetDlgItemText(hwnd, COMP_NOTE,
2351 GetPString(IDS_COMPHOLDDESELTEXT));
2352 break;
2353 case IDM_INVERT:
2354 WinSetDlgItemText(hwnd, COMP_NOTE,
2355 GetPString(IDS_COMPHOLDINVERTTEXT));
2356 break;
2357 default:
2358 WinSetDlgItemText(hwnd, COMP_NOTE,
2359 GetPString(IDS_COMPHOLDSELTEXT));
2360 break;
2361 }
2362 WinEnableWindow(hwndRight, FALSE);
2363 WinEnableWindow(hwndLeft, FALSE);
2364 WinEnableWindow(WinWindowFromID(hwnd, DID_OK), FALSE);
2365 WinEnableWindow(WinWindowFromID(hwnd, DID_CANCEL), FALSE);
2366 WinEnableWindow(WinWindowFromID(hwnd, COMP_COLLECT), FALSE);
2367 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTBOTH), FALSE);
2368 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTONE), FALSE);
2369 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTNEWER), FALSE);
2370 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTOLDER), FALSE);
2371 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTBIGGER), FALSE);
2372 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSMALLER), FALSE);
2373 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTBOTH), FALSE);
2374 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTONE), FALSE);
2375 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTNEWER), FALSE);
2376 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTOLDER), FALSE);
2377 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTBIGGER), FALSE);
2378 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTSMALLER),
2379 FALSE);
2380 WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTALL), FALSE);
2381 WinEnableWindow(WinWindowFromID(hwnd, COMP_INCLUDESUBDIRS),
2382 FALSE);
2383 WinEnableWindow(WinWindowFromID(hwnd, COMP_SETDIRS), FALSE);
2384 WinEnableWindow(WinWindowFromID(hwnd, COMP_DELETELEFT), FALSE);
2385 WinEnableWindow(WinWindowFromID(hwnd, COMP_DELETERIGHT), FALSE);
2386 WinEnableWindow(WinWindowFromID(hwnd, COMP_COPYLEFT), FALSE);
2387 WinEnableWindow(WinWindowFromID(hwnd, COMP_MOVELEFT), FALSE);
2388 WinEnableWindow(WinWindowFromID(hwnd, COMP_COPYRIGHT), FALSE);
2389 WinEnableWindow(WinWindowFromID(hwnd, COMP_MOVERIGHT), FALSE);
2390 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSAMECONTENT),
2391 FALSE);
2392 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTIDENTICAL),
2393 FALSE);
2394 WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSAME), FALSE);
2395 WinEnableWindow(WinWindowFromID(hwnd, IDM_INVERT), FALSE);
2396 WinEnableWindow(WinWindowFromID(hwnd, COMP_FILTER), FALSE);
2397 }
2398 }
2399 }
2400 break;
2401
2402 case COMP_COLLECT:
2403 cmp = INSTDATA(hwnd);
2404 if (!cmp)
2405 Runtime_Error2(pszSrcFile, __LINE__, IDS_NODATATEXT);
2406 else {
2407 CHAR **listl;
2408 CHAR **listr = NULL;
2409 if (!Collector) {
2410 SWP swp;
2411 HWND hwndC;
2412 if (!fAutoTile &&
2413 !ParentIsDesktop(hwnd, cmp->hwndParent) &&
2414 !fExternalCollector &&
2415 !strcmp(realappname, FM3Str)) {
2416 GetNextWindowPos(cmp->hwndParent, &swp, NULL, NULL);
2417 }
2418 hwndC = StartCollector(fExternalCollector ||
2419 strcmp(realappname, FM3Str) ?
2420 HWND_DESKTOP :
2421 cmp->hwndParent,
2422 4);
2423 if (hwndC) {
2424 if (!fAutoTile &&
2425 !ParentIsDesktop(hwnd, cmp->hwndParent) &&
2426 !fExternalCollector &&
2427 !strcmp(realappname, FM3Str)) {
2428 WinSetWindowPos(hwndC, HWND_TOP,
2429 swp.x, swp.y, swp.cx, swp.cy,
2430 SWP_MOVE | SWP_SIZE | SWP_SHOW | SWP_ZORDER);
2431 }
2432 else if (!ParentIsDesktop(hwnd, cmp->hwndParent) &&
2433 fAutoTile &&
2434 !strcmp(realappname, FM3Str)) {
2435 TileChildren(cmp->hwndParent, TRUE);
2436 }
2437 DosSleep(32); // 05 Aug 07 GKY 64
2438 PostMsg(hwnd, WM_COMMAND, MPFROM2SHORT(COMP_COLLECT, 0), MPVOID);
2439 break;
2440 }
2441 }
2442 else
2443 StartCollector(cmp->hwndParent, 4);
2444
2445 temp = fSelectedAlways;
2446 fSelectedAlways = TRUE;
2447 listl = BuildList(hwndLeft);
2448 if (!*cmp->rightlist)
2449 listr = BuildList(hwndRight);
2450 fSelectedAlways = temp;
2451
2452 if (listl || listr) {
2453 if (Collector) {
2454 // 07 Aug 07 SHL Avoid collected from empty list
2455 if (listl && listl[0] && *listl[0]) {
2456 if (PostMsg(Collector, WM_COMMAND,
2457 MPFROM2SHORT(IDM_COLLECTOR, 0), MPFROMP(listl)))
2458 listl = NULL; // Collector will free
2459 }
2460 if (listr && listr[0] && *listr[0]) {
2461 if (PostMsg(Collector, WM_COMMAND,
2462 MPFROM2SHORT(IDM_COLLECTOR, 0), MPFROMP(listr)))
2463 listr = NULL; // Collector will free
2464 }
2465 WinSetWindowPos(WinQueryWindow(WinQueryWindow(Collector,
2466 QW_PARENT),
2467 QW_PARENT),
2468 HWND_TOP, 0, 0, 0, 0,
2469 SWP_ACTIVATE);
2470 }
2471 FreeList(listl);
2472 FreeList(listr);
2473 }
2474 }
2475 break;
2476 }
2477 return 0;
2478
2479 case WM_CLOSE:
2480 WinDismissDlg(hwnd, 0);
2481 return 0;
2482
2483 case WM_DESTROY:
2484 cmp = INSTDATA(hwnd);
2485 if (cmp) {
2486 if (cmp->dcd.hwndLastMenu)
2487 WinDestroyWindow(cmp->dcd.hwndLastMenu);
2488 if (cmp->dcd.hwndObject) {
2489 WinSetWindowPtr(cmp->dcd.hwndObject, QWL_USER, (PVOID) NULL);
2490 if (!PostMsg(cmp->dcd.hwndObject, WM_CLOSE, MPVOID, MPVOID))
2491 WinSendMsg(cmp->dcd.hwndObject, WM_CLOSE, MPVOID, MPVOID);
2492 }
2493 free(cmp);
2494 }
2495 EmptyCnr(hwndLeft);
2496 EmptyCnr(hwndRight);
2497 DosPostEventSem(CompactSem);
2498 break;
2499 }
2500 return WinDefDlgProc(hwnd, msg, mp1, mp2);
2501}
Note: See TracBrowser for help on using the repository browser.