source: trunk/dll/treecnr.c@ 1892

Last change on this file since 1892 was 1883, checked in by Gregg Young, 10 years ago

Comments for CS [1882]

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 97.8 KB
RevLine 
[1335]1
[36]2/***********************************************************************
3
4 $Id: treecnr.c 1883 2015-10-12 20:02:58Z gyoung $
5
6 Tree containers
7
8 Copyright (c) 1993-98 M. Kimes
[1856]9 Copyright (c) 2001, 2015 Steven H. Levine
[36]10
[156]11 16 Oct 02 SHL Handle large partitions
12 11 Jun 03 SHL Add JFS and FAT32 support
13 25 May 05 SHL Rename comnam to szCommonName and fix typo
14 25 May 05 SHL Use ULONGLONG and CommaFmtULL
[176]15 26 May 05 SHL More large file formatting updates
[186]16 05 Jun 05 SHL Use QWL_USER
[246]17 06 Aug 05 SHL Renames
[305]18 08 Dec 05 SHL TreeCnrWndProc: disable menu items if drive not ready
[352]19 17 Jul 06 SHL Use Runtime_Error
[443]20 15 Aug 06 SHL Rework SetMask args
[472]21 31 Aug 06 JS Add more partitioning menu items
[787]22 22 Oct 06 GKY Add NDFS32 support
[549]23 29 Dec 06 GKY Fixed menu gray out for remote drives (added variable "remote")
24 29 Dec 06 GKY Enabled edit of drive flags on "not ready" drives
[555]25 18 Feb 07 GKY More drive type and icon support
[557]26 08 Mar 07 SHL Ensure drive icon updates after drive flags change
27 09 Mar 07 GKY Use SelectDriveIcon
[593]28 30 Mar 07 GKY Remove GetPString for window class names
[603]29 06 Apr 07 GKY Work around PM DragInfo and DrgFreeDISH limits
30 06 Apr 07 GKY Add some error checking in drag/drop
[618]31 19 Apr 07 SHL Sync with AcceptOneDrop GetOneDrop mods
32 19 Apr 07 SHL Add more drag/drop error checking
[672]33 12 May 07 SHL Use dcd->ulItemsToUnHilite; sync with UnHilite arg mods
[688]34 10 Jun 07 GKY Add CheckPmDrgLimit including IsFm2Window as part of work around PM drag limit
35 10 Jun 07 GKY Mouse button 3 white space click to fail silently
[726]36 05 Jul 07 SHL Disable leftover debug code
[751]37 02 Aug 07 SHL Sync with CNRITEM mods
[775]38 06 Aug 07 GKY Reduce DosSleep times (ticket 148)
[787]39 14 Aug 07 SHL Revert ShowTreeRec DosSleep to 0
40 14 Aug 07 SHL Optimze ShowTreeRec collapse - was really slow
[793]41 20 Aug 07 GKY Move #pragma alloc_text to end for OpenWatcom compat
[802]42 22 Aug 07 SHL Disable DbgMsgs shipped with 3.0.8beta1
[809]43 26 Aug 07 SHL Revert to DosSleep(0)
[872]44 22 Nov 07 GKY Use CopyPresParams to fix presparam inconsistencies in menus
[917]45 10 Jan 08 SHL Sync with CfgDlgProc mods
[953]46 15 Feb 08 SHL Sync with settings menu rework
[954]47 15 Feb 08 SHL Avoid death if tree container 0 width
[1102]48 19 Jul 08 GKY Replace save_dir2(dir) with pFM2SaveDirectory
49 02 Aug 08 GKY Always pass temp variable point to UM_SHOWME to avoid freeing pci->pszFileName early
[1251]50 19 Oct 08 GKY Fixed logic for greying menu items (Format etc) on remote and virtual drives (it was reversed)
51 19 Oct 08 GKY Fixed context menu to be "drives" menu on unformatted drives
[1303]52 28 Nov 08 GKY Remove unneeded DosEnterCriSec calls
[1335]53 10 Dec 08 SHL Integrate exception handler support
[1357]54 25 Dec 08 GKY Add code to allow write verify to be turned off on a per drive basis
55 26 Dec 08 GKY Implemented DROPHELP for the tree container
[1360]56 27 Dec 08 GKY Add refresh removable media to tree container menus
57 28 Dec 08 GKY Rework partition submenu to gray out unavailable items (check for existence of files)
[1394]58 and have no default choice.
[1375]59 01 Jan 09 GKY Add Seek and Scan to drives & directory context menus pass drive/dir as search root
[1391]60 11 Jan 09 GKY Replace font names in the string file with global set at compile in init.c
[1395]61 07 Feb 09 GKY Allow user to turn off alert and/or error beeps in settings notebook.
62 07 Feb 09 GKY Add *DateFormat functions to format dates based on locale
63 07 Feb 09 GKY Eliminate Win_Error2 by moving function names to PCSZs used in Win_Error
[1400]64 08 Mar 09 GKY Renamed commafmt.h i18nutil.h
65 08 Mar 09 GKY Additional strings move to PCSZs in init.c
[1411]66 12 Mar 09 SHL Use common SearchContainer
[1402]67 14 Mar 09 GKY Prevent execution of UM_SHOWME while drive scan is occuring
[1428]68 06 Jun 09 GKY Add option to show file system type or drive label in tree
69 06 Jun 09 GKY Status line to show file sys/label not shown in tree; shortened to fit split status
70 07 Jun 09 GKY Fixed double names in tree container when collapsed tree is accessed
[1455]71 before recursive scan
[1439]72 12 Jul 09 GKY Add option to show file system type or drive label in tree
[1455]73 (get NOPRESCAN drives working)
[1444]74 22 Jul 09 GKY Code changes to use semaphores to serialize drive scanning
75 22 Jul 09 GKY Consolidated driveflag setting code in DriveFlagsOne
76 22 Jul 09 GKY Streamline scanning code for faster Tree rescans
[1455]77 14 Sep 09 SHL Drop experimental code
[1456]78 15 Sep 09 SHL Use UM_GREP when passing pathname
[1477]79 15 Nov 09 GKY Add semaphore to fix double names in tree container caused by UM_SHOWME
[1856]80 before scan completes
[1480]81 22 Nov 09 GKY Add LVM.EXE to partition submenu
[1506]82 17 JAN 10 GKY Changes to get working with Watcom 1.9 Beta (1/16/10). Mostly cast
[1856]83 CHAR CONSTANT * as CHAR *.
[1506]84 11 Apr 10 GKY Fix drive tree rescan failure and program hang caused by event sem
[1856]85 never being posted
[1553]86 20 Nov 10 GKY Rework scanning code to remove redundant scans, prevent double directory
[1856]87 entries in the tree container, fix related semaphore performance using
88 combination of event and mutex semaphores
[1663]89 04 Aug 12 GKY Fix trap reported by Ben
[1674]90 30 Dec 12 GKY Changed refresh removable media to query LVM directly to call Rediscover_PRMs (Ticket 472);
[1856]91 Also added a tree rescan following volume detach.
[1741]92 22 Feb 14 GKY Fix warn readonly yes don't ask to work when recursing directories.
[1796]93 07 Sep 14 GKY Fix tree container mis-draws (stacked icons with RWS) The problem was magnified
[1856]94 by RWS but I think the occasional extra blank directory or duplicating
95 directories is related.
[1799]96 16 Mar 15 GKY Add semaphore hmtxFiltering to prevent freeing dcd while filtering. Prevents
[1856]97 a trap when FM2 is shutdown or the container is closed while tree
98 container is still populating
[1803]99 02 May 15 GKY Changes to allow a JAVA executable object to be created using "Real object"
[1856]100 menu item on a jar file.
[1828]101 12 Jul 15 GKY Fixed trap caused by pci->pszFileName being NullStr
[1856]102 07 Aug 15 SHL Rework to use AddFleshWorkRequest rather than direct calls to Stubby/Flesh/Unflesh
[1860]103 20 Aug 15 SHL Sync with SetFleshFocusPath mods
[1862]104 22 Aug 15 GKY Improve ability of maketop to get directory position in tree correct on first
[1867]105 open of states with large and/or deep tree structures
[1871]106 24 Aug 15 GKY Remove fDummy code
107 20 Sep 15 GKY Get expand and switch code to work with Flesh, UnFlesh and Stubby running on
108 a thread. Loop and idle ExpandAll; Add CollapseAll; Move tree expand to a
109 thread; Have ShowTreeRec wait for the Flesh thread.
[1873]110 26 Sep 15 GKY Adjustments to ShowTreeRec to eliminate failures and reduce retries and container
111 noise on tree switches.
112 26 Sep 15 GKY Remove fInitialDriveScan code
113 26 Sep 15 GKY Changes to speed up ExpandAll
[1874]114 26 Sep 15 GKY Put UM_TOPDIR in the object window so it can call WaitFleshWorkListEmpty
115 while avoiding thread 1
116 27 Sep 15 GKY DosSleep times in WaitFleshWorkListEmpty set by caller
[1875]117 04 Oct 15 GKY Move the eUnflesh call from UM_ENTER to the object window so WaitFleshWorkListEmpty
118 can be used (UM_ENTER is on TID 1); Prevent eUnflesh from running if no child
119 directories are present; treat floppies like invalid drives on rescan (IDM_UPDATE
120 to avoid them seen as directories and having random subdirectories attached to
121 them.
[1876]122 10 Oct 15 GKY Eliminate some unnecessary Flesh and UnFlesh calls
123 10 Oct 15 GKY Update icon and display name on CD/DVD eject in all cases.
124 10 Oct 15 GKY Don't use Flesh thread for floppy drive scans fix them getting mistakenly identified
125 as directories and add nonexistent subdirectories.
[1883]126 12 Oct 15 GKY Increase ExpandAll waits for removable drives avoids directory name corruption
[1439]127
[36]128***********************************************************************/
129
[2]130#include <stdlib.h>
131#include <string.h>
132#include <ctype.h>
[156]133
[907]134#define INCL_DOS
135#define INCL_WIN
136#define INCL_LONGLONG
[1251]137#define INCL_DOSERRORS
[907]138
[1178]139#include "fm3dll.h"
[1227]140#include "fm3dll2.h" // #define's for UM_*, control id's, etc.
141#include "treecnr.h"
[1213]142#include "mainwnd2.h" // Data declaration(s)
143#include "grep.h" // Data declaration(s)
144#include "dircnrs.h" // Data declaration(s)
145#include "info.h" // Data declaration(s)
[2]146#include "fm3dlg.h"
147#include "fm3str.h"
148#include "mle.h"
[907]149#include "comp.h" // COMPARE
150#include "filldir.h" // RemoveCnrItems...
151#include "errutil.h" // Dos_Error...
152#include "strutil.h" // GetPString
[953]153#include "notebook.h" // CfgDlgProc
[1077]154#include "command.h" // RunCommand
[1471]155#include "worker.h" // Action, MassAction
[1178]156#include "mainwnd.h" // BubbleHelp, FindDirCnrByName, GetNextWindowPos
[1157]157#include "misc.h" // CnrDirectEdit, EmphasizeButton, FindDirCnr
[1471]158 // FindDirCnr, FixSwitchList, OpenEdit, QuickPopup
159 // SetSortChecks, SwitchCommand, CheckMenu
160 // CurrentRecord, IsFm2Window
[1157]161#include "common.h" // CommonCnrProc, CommonDriveCmd, CommonFrameWndProc
[1471]162 // CommonTextProc
[1178]163#include "valid.h" // CheckDrive, DriveFlagsOne, IsValidDrive
[1157]164#include "chklist.h" // DropListProc
165#include "select.h" // ExpandAll
[1178]166#include "findrec.h" // FindCnrRecord, FindParentRecord, ShowCnrRecord
[1856]167#include "flesh.h" // AddFleshWorkRequest
[1157]168#include "notify.h" // HideNote
169#include "objwin.h" // MakeObjWin
170#include "notify.h" // NotifyError
171#include "remap.h" // RemapDlgProc
172#include "saveclip.h" // SaveListDlgProc
173#include "update.h" // SelectDriveIcon, UpdateCnrList, UpdateCnrRecord
174#include "sortcnr.h" // SortTreeCnr
[1178]175#include "droplist.h" // AcceptOneDrop, CheckPmDrgLimit, DropHelp, GetOneDrop
176#include "presparm.h" // CopyPresParams
177#include "defview.h" // DefaultViewKeys
178#include "draglist.h" // DoFileDrag
179#include "filter.h" // Filter
180#include "shadow.h" // OpenObject
181#include "mkdir.h" // PMMkDir
182#include "collect.h" // StartCollector
183#include "viewer.h" // StartMLEEditor
184#include "newview.h" // StartViewer
185#include "walkem.h" // WalkAllDlgProc
[1400]186#include "i18nutil.h" // CommaFmtULL
[1178]187#include "wrappers.h" // xDosFindFirst
188#include "systemf.h" // runemf2
189#include "dirs.h" // save_dir2
[1017]190#include "fortify.h"
[1856]191#include "init.h" // NullStr etc.
[1335]192#include "excputil.h" // xbeginthread
[1741]193#include "copyf.h" // ignorereadonly
[1017]194
[1213]195// Data definitions
196
197#pragma data_seg(GLOBAL1)
198HWND LastDir;
199HWND TreeCnrMenu;
200INT driveserial[26];
201BOOL fDCOpens;
202BOOL fFollowTree;
203BOOL fTopDir;
[1360]204BOOL fLVMGui;
205BOOL fDFSee;
206BOOL fFDisk;
207BOOL fMiniLVM;
208BOOL fLVM;
[1873]209BOOL fExpandAll;
[1213]210HPOINTER hptrDunno;
211HWND hwndMainMenu;
212
213#pragma data_seg(GLOBAL2)
214ULONG FM3UL;
215INT TreesortFlags;
216
[2]217#pragma data_seg(DATA1)
[352]218
219static PSZ pszSrcFile = __FILE__;
[1213]220static BOOL fOkayMinimize;
[1871]221static HMQ hmqExpandTree;
[352]222
[551]223APIRET16 APIENTRY16 Dos16MemAvail(PULONG pulAvailMem);
[2]224
[551]225typedef struct APPNOTIFY
226{
227 HAPP happ;
228 CHAR device;
[2]229 struct APPNOTIFY *next;
230 struct APPNOTIFY *prev;
[551]231}
232APPNOTIFY;
[2]233
[551]234MRESULT EXPENTRY OpenButtonProc(HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2)
[352]235{
[2]236 static BOOL emphasized = FALSE;
237
[551]238 switch (msg) {
239 case WM_CREATE:
240 {
241 MRESULT rc;
[2]242
[551]243 rc = PFNWPButton(hwnd, msg, mp1, mp2);
[1391]244 //fixme to allow user to change presparams 1-10-09 GKY
[551]245 WinSetPresParam(hwnd, PP_FONTNAMESIZE,
[1391]246 strlen(FNT_8TIMESNEWROMAN) + 1,
[1400]247 (PVOID) FNT_8TIMESNEWROMAN);
[551]248 return rc;
249 }
[2]250
[551]251 case WM_MOUSEMOVE:
252 BubbleHelp(hwnd, TRUE, FALSE, TRUE, GetPString(IDS_OPENBUTTONHELP));
253 break;
[2]254
[551]255 case WM_CONTEXTMENU:
256 PostMsg(WinQueryWindow(hwnd, QW_PARENT),
257 WM_COMMAND, MPFROM2SHORT(IDM_OPENWALK, 0), MPVOID);
258 return 0;
[2]259
[551]260 case DM_DRAGOVER:
261 if (!emphasized) {
262 emphasized = TRUE;
263 EmphasizeButton(hwnd, emphasized);
264 }
[618]265 if (AcceptOneDrop(hwnd, mp1, mp2))
[551]266 return MRFROM2SHORT(DOR_DROP, DO_MOVE);
267 return MRFROM2SHORT(DOR_NEVERDROP, 0);
[2]268
[551]269 case DM_DRAGLEAVE:
270 if (emphasized) {
271 emphasized = FALSE;
272 EmphasizeButton(hwnd, emphasized);
273 }
274 break;
[2]275
[551]276 case DM_DROPHELP:
277 DropHelp(mp1, mp2, hwnd, GetPString(IDS_OPENDROPHELP));
278 return 0;
[2]279
[551]280 case DM_DROP:
281 {
282 char szFrom[CCHMAXPATH + 2];
[2]283
[551]284 if (emphasized) {
285 emphasized = FALSE;
286 EmphasizeButton(hwnd, emphasized);
[2]287 }
[618]288 if (GetOneDrop(hwnd, mp1, mp2, szFrom, sizeof(szFrom))) {
[551]289 MakeValidDir(szFrom);
290 WinSendMsg(WinQueryWindow(hwnd, QW_PARENT),
291 UM_OPENWINDOWFORME, MPFROMP(szFrom), MPVOID);
292 }
293 }
294 return 0;
[2]295
296 }
[551]297 return PFNWPButton(hwnd, msg, mp1, mp2);
[2]298}
299
[1856]300/**
301 * Find a record in tree view, move it so it shows in container and
302 * make it the current record
303 * @param hwndCnr is container which must be in tree view
304 * @param pszDir_ is full path name to find
305 */
306
[787]307VOID ShowTreeRec(HWND hwndCnr,
[1865]308 PCSZ pszDir_,
[787]309 BOOL collapsefirst,
[551]310 BOOL maketop)
[352]311{
[1856]312 PCNRITEM pci;
313 PCNRITEM pciToSelect;
314 PCNRITEM pciP;
315 UINT retries;
[551]316 BOOL quickbail = FALSE;
[1856]317 PSZ p;
318 BOOL found;
319 CHAR szDir[CCHMAXPATH];
[1867]320 CHAR szDirArg[CCHMAXPATH]; // Copy of passed value
321 CHAR chSaved;
[2]322
[1873]323 strcpy(szDirArg, pszDir_); // Cache here in case arg content changed by some other thread
324
[787]325 // already positioned to requested record?
[2]326 pci = WinSendMsg(hwndCnr,
[176]327 CM_QUERYRECORDEMPHASIS,
[551]328 MPFROMLONG(CMA_FIRST), MPFROMSHORT(CRA_CURSORED));
[1867]329 if (pci && (INT)pci != -1 && !stricmp(pci->pszFileName, szDirArg)) {
[1856]330 quickbail = TRUE; // Already at requested record - bypass repositioning
[787]331 goto MakeTop;
[2]332 }
[1862]333 // 2015-08-13 SHL add retry logic 2015-08-22 GKY increase retries from 10 to 100 to
334 // eliminate switch failures on deep or large tree state switches
335 for (found = FALSE, retries = 0; !found && retries < 100; retries++) {
[1856]336
337 pci = FindCnrRecord(hwndCnr,
[1867]338 szDirArg,
[1856]339 NULL, // pciParent
340 TRUE, // partial
341 FALSE, // partmatch
342 TRUE); // noenv
343
344 if (pci && (INT)pci != -1) {
345 found = TRUE;
346 break; // Found it
347 }
348
[1867]349 // Walk down directory tree, expanding as needed
350 strcpy(szDir, szDirArg);
[787]351 p = szDir + 3; // Point after root backslash
[1867]352 chSaved = *p; // Remember for restore
353 *p = 0; // Chop after backslash
[1856]354
[551]355 for (;;) {
[1856]356 // Try to match path prefix
357 pciP = FindCnrRecord(hwndCnr,
358 szDir,
359 NULL, // pciParent
360 TRUE, // partial
361 FALSE, // partmatch
362 TRUE); // noenv
363 if (!pciP || (INT)pciP == -1) {
[1874]364 WaitFleshWorkListEmpty(szDirArg, 240); // 2015-08-23 SHL
[1856]365 break; // No match
[2]366 }
[1867]367 if (!stricmp(szDirArg, pciP->pszFileName)) {
[1856]368 pci = pciP;
369 found = TRUE;
370 break; // Got full match
371 }
372
[1867]373 // Got partial match
374
[1856]375 if (~pciP->rc.flRecordAttr & CRA_EXPANDED) {
376 WinSendMsg(hwndCnr, CM_EXPANDTREE, MPFROMP(pciP), MPVOID);
377 }
378
[1867]379 // Add next component to path unless no more components
380 if (p) {
381 *p = chSaved; // Restore
382 if (chSaved) {
383 if (chSaved == '\\')
384 p++; // Get past last backslash
385 p = strchr(p, '\\'); // Find next backslash
386 if (p) {
387 chSaved = *p;
388 *p = 0; // Truncate at backslash
389 }
390 }
391 }
[1874]392 WaitFleshWorkListEmpty(NULL, 240); // 2015-09-26 GKY Let Flesh thread catch up
[1856]393 } // while expanding
394
395 } // for
396 if (found) {
397 // Found it
[787]398 if (~pci->rc.flRecordAttr & CRA_CURSORED) {
[551]399 if (collapsefirst) {
[1874]400 WaitFleshWorkListEmpty(NULL, 240);
[176]401 pciP = WinSendMsg(hwndCnr,
402 CM_QUERYRECORD,
[551]403 MPVOID, MPFROM2SHORT(CMA_FIRST, CMA_ITEMORDER));
404 while (pciP && (INT) pciP != -1) {
[787]405 if (pciP->rc.flRecordAttr & CRA_EXPANDED) {
406 // collapse top level of all branches
[551]407 WinSendMsg(hwndCnr, CM_COLLAPSETREE, MPFROMP(pciP), MPVOID);
[787]408 }
[176]409 pciP = WinSendMsg(hwndCnr,
410 CM_QUERYRECORD,
411 MPFROMP(pciP),
[551]412 MPFROM2SHORT(CMA_NEXT, CMA_ITEMORDER));
[787]413 } // while
[1856]414 } // if collapse
415
416 // Expand parent branches
417 // 2015-08-06 SHL FIXME to bypass if we did not collapse since search already expanded - maybe?
[2]418 pciToSelect = pci;
[551]419 for (;;) {
[176]420 pciP = WinSendMsg(hwndCnr,
421 CM_QUERYRECORD,
422 MPFROMP(pciToSelect),
[551]423 MPFROM2SHORT(CMA_PARENT, CMA_ITEMORDER));
[1856]424 if (!pciP || (INT)pciP == -1)
425 break; // Done
426 // Got parent
427 if (~pciP->rc.flRecordAttr & CRA_EXPANDED)
428 WinSendMsg(hwndCnr, CM_EXPANDTREE, MPFROMP(pciP), MPVOID);
429 pciToSelect = pciP;
[809]430 DosSleep(0); // Let GUI update
[787]431 } // for
[1856]432 } // if not cursored
433
434 MakeTop:
[1673]435 // make record visible
[2]436 pciToSelect = pci;
[551]437 if (pciToSelect && (INT) pciToSelect != -1) {
[1865]438 if (fSwitchTreeExpand && ~pciToSelect->rc.flRecordAttr & CRA_EXPANDED) {
[1856]439 WinSendMsg(hwndCnr, CM_EXPANDTREE, MPFROMP(pciToSelect), MPVOID);
[1865]440 }
[1871]441 if (maketop || fTopDir) {
[1873]442 if (fCollapseFirst && !quickbail) {
[1874]443 WaitFleshWorkListEmpty(NULL, 240); //Let the root expand first otherwise it makes top
[1873]444 }
[1867]445 ShowCnrRecord(hwndCnr, (PMINIRECORDCORE)pciToSelect);
[1865]446 }
[1856]447
[787]448 if (!quickbail) {
[1874]449 WaitFleshWorkListEmpty(szDirArg, 240); // 2015-08-19 SHL try to ensure contents stable
[907]450 WinSendMsg(hwndCnr,
[787]451 CM_SETRECORDEMPHASIS,
452 MPFROMP(pciToSelect),
453 MPFROM2SHORT(TRUE, CRA_SELECTED | CRA_CURSORED));
454 }
[2]455 }
456 }
457}
458
[551]459MRESULT EXPENTRY TreeTitleWndProc(HWND hwnd, ULONG msg, MPARAM mp1,
460 MPARAM mp2)
[352]461{
[551]462 PFNWP oldproc = (PFNWP) WinQueryWindowPtr(hwnd, QWL_USER);
[2]463
[551]464 switch (msg) {
465 case WM_CONTEXTMENU:
466 return WinSendMsg(WinQueryWindow(hwnd, QW_PARENT),
467 UM_CONTEXTMENU, mp1, mp2);
[2]468 }
[551]469 return oldproc(hwnd, msg, mp1, mp2);
[2]470}
471
[551]472MRESULT EXPENTRY TreeStatProc(HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2)
[352]473{
[551]474 switch (msg) {
475 case WM_CREATE:
476 return CommonTextProc(hwnd, msg, mp1, mp2);
[2]477
[551]478 case WM_CONTEXTMENU:
479 PostMsg(WinQueryWindow(hwnd, QW_PARENT), msg, mp1, mp2);
480 return 0;
[2]481
[551]482 case WM_PAINT:
483 {
484 MRESULT mr = PFNWPStatic(hwnd, msg, mp1, mp2);
[2]485
[551]486 PaintRecessedWindow(hwnd, (HPS) 0, FALSE, FALSE);
487 return mr;
488 }
[2]489
[551]490 case WM_SETFOCUS:
491 if (mp2)
492 PostMsg(hwnd, UM_FOCUSME, MPVOID, MPVOID);
493 break;
[2]494
[551]495 case UM_FOCUSME:
496 WinSetFocus(HWND_DESKTOP, WinQueryWindow(hwnd, QW_PARENT));
497 return 0;
[2]498 }
[551]499 return PFNWPStatic(hwnd, msg, mp1, mp2);
[2]500}
501
[551]502MRESULT EXPENTRY TreeFrameWndProc(HWND hwnd, ULONG msg, MPARAM mp1,
503 MPARAM mp2)
[352]504{
[551]505 switch (msg) {
506 case UM_RESCAN:
507 PostMsg(WinQueryWindow(hwnd, QW_PARENT), msg, mp1, mp2);
508 return 0;
[2]509
[551]510 case WM_ADJUSTWINDOWPOS:
511 {
512 SWP *pswp;
[2]513
[551]514 pswp = (SWP *) mp1;
515 if (ParentIsDesktop(hwnd, (HWND) 0)) {
516 if (pswp->fl & (SWP_HIDE | SWP_MINIMIZE))
517 HideNote();
[2]518 }
[551]519 }
520 break;
[2]521
[551]522 case WM_TRACKFRAME:
523 if (!fFreeTree && !ParentIsDesktop(hwnd, (HWND) 0)) {
524 switch (SHORT1FROMMP(mp1) & TF_MOVE) {
525 case TF_MOVE:
526 case TF_LEFT:
527 case TF_TOP:
528 case (TF_LEFT | TF_BOTTOM):
529 case (TF_LEFT | TF_TOP):
530 {
531 SWP swp;
[2]532
[551]533 WinQueryWindowPos(hwnd, &swp);
534 if (!(swp.fl & SWP_ACTIVATE))
535 WinSetWindowPos(hwnd, HWND_TOP, 0, 0, 0, 0,
536 SWP_ZORDER | SWP_ACTIVATE);
[176]537 }
[551]538 return 0;
[2]539 }
[551]540 }
541 break;
[2]542
[551]543 case WM_CALCFRAMERECT:
544 if (*(ULONG *) realappname != FM3UL) {
[2]545
[551]546 MRESULT mr;
547 PRECTL prectl;
[2]548
[551]549 mr = CommonFrameWndProc(TREE_CNR, hwnd, msg, mp1, mp2);
[2]550
[1673]551 /**
[551]552 * Calculate the position of the client rectangle.
553 * Otherwise, we'll see a lot of redraw when we move the
554 * client during WM_FORMATFRAME.
555 */
[2]556
[551]557 if (mr && mp2) {
558 prectl = (PRECTL) mp1;
559 prectl->yTop -= 22;
[2]560 }
[551]561 return mr;
562 }
563 break;
[2]564
[551]565 case WM_FORMATFRAME:
566 {
567 SHORT sCount;
568 PSWP pswp, pswpClient, pswpNew;
[2]569
[551]570 sCount = (SHORT) CommonFrameWndProc(TREE_CNR, hwnd, msg, mp1, mp2);
[2]571
[1673]572 // Reformat the frame to "squeeze" the client
[2]573
[551]574 pswp = (PSWP) mp1;
575 {
576 SHORT x;
[2]577
[551]578 for (x = 0; x < sCount; x++) {
579 if (WinQueryWindowUShort(pswp->hwnd, QWS_ID) == FID_CLIENT) {
580 pswpClient = pswp;
581 break;
[176]582 }
[551]583 pswp++;
[176]584 }
[551]585 }
586 pswpNew = (PSWP) mp1 + sCount;
587 *pswpNew = *pswpClient;
588 pswpNew->hwnd = WinWindowFromID(hwnd, MAIN_STATUS);
589 if (*(ULONG *) realappname == FM3UL) {
[2]590
[551]591 PSWP pswpTitlebar = (PSWP) 0, pswpMinbutton = (PSWP) 0;
592 SHORT x;
[2]593
[551]594 pswpNew->hwnd = WinWindowFromID(hwnd, IDM_OPENWINDOW);
595 pswp = (PSWP) mp1;
596 for (x = 0; x < sCount; x++) {
597 if (WinQueryWindowUShort(pswp->hwnd, QWS_ID) == FID_TITLEBAR)
598 pswpTitlebar = pswp;
599 else if (WinQueryWindowUShort(pswp->hwnd, QWS_ID) == FID_MINMAX)
600 pswpMinbutton = pswp;
601 if (pswpTitlebar && pswpMinbutton)
602 break;
603 pswp++;
[176]604 }
[551]605 pswpNew->cy = pswpMinbutton->cy + 3;
606 pswpNew->cx = min(pswpNew->cy, (pswpMinbutton->cx / 2) + 3);
607 pswpTitlebar->cx -= (pswpNew->cx + 1);
608 pswpNew->x = pswpTitlebar->x + pswpTitlebar->cx;
609 pswpNew->y = pswpMinbutton->y - 1;
[2]610 }
[551]611 else {
612 pswpNew->x = pswpClient->x + 3;
613 pswpNew->y = (pswpClient->y + pswpClient->cy) - 20;
614 pswpNew->cx = pswpClient->cx - 6;
615 pswpNew->cy = 18;
616 pswpClient->cy -= 22;
617 }
618 sCount++;
619 return MRFROMSHORT(sCount);
620 }
[2]621
[551]622 case WM_QUERYFRAMECTLCOUNT:
623 {
624 SHORT sCount;
[2]625
[551]626 sCount = (SHORT) CommonFrameWndProc(TREE_CNR, hwnd, msg, mp1, mp2);
627 sCount++;
628 return MRFROMSHORT(sCount);
629 }
[2]630 }
[551]631 return CommonFrameWndProc(TREE_CNR, hwnd, msg, mp1, mp2);
[2]632}
633
[551]634MRESULT EXPENTRY TreeClientWndProc(HWND hwnd, ULONG msg, MPARAM mp1,
635 MPARAM mp2)
636{
637 switch (msg) {
638 case UM_CONTAINERHWND:
639 return MRFROMLONG(WinWindowFromID(hwnd, TREE_CNR));
[2]640
[551]641 case UM_VIEWSMENU:
[875]642 return MRFROMLONG(CheckMenu(hwndMainMenu, &TreeCnrMenu, TREECNR_POPUP));
[2]643
[551]644 case UM_TIMER:
645 case UM_ACTION:
646 case UM_SHOWME:
647 case UM_OPENWINDOWFORME:
648 case UM_MINIMIZE:
649 case UM_MAXIMIZE:
650 case WM_INITMENU:
651 case UM_INITMENU:
652 case UM_FILTER:
653 case UM_FILESMENU:
654 case UM_UPDATERECORD:
655 case UM_UPDATERECORDLIST:
656 case MM_PORTHOLEINIT:
657 case UM_DRIVECMD:
658 case WM_CLOSE:
659 case WM_CONTROL:
660 case UM_COMMAND:
661 case WM_COMMAND:
662 return WinSendMsg(WinWindowFromID(hwnd, TREE_CNR), msg, mp1, mp2);
[2]663
[551]664 case WM_PSETFOCUS:
665 case WM_SETFOCUS:
666 if (mp2)
667 PostMsg(hwnd, UM_FOCUSME, MPVOID, MPVOID);
668 break;
[2]669
[551]670 case UM_FOCUSME:
671 WinSetFocus(HWND_DESKTOP, WinWindowFromID(hwnd, TREE_CNR));
672 break;
[2]673
[551]674 case WM_ERASEBACKGROUND:
675 WinFillRect((HPS) mp1, (PRECTL) mp2, 0x00d0d0d0);
676 return 0;
[2]677
[551]678 case WM_PAINT:
679 {
680 HPS hps;
681 RECTL rcl;
[2]682
[551]683 hps = WinBeginPaint(hwnd, (HPS) 0, NULL);
684 if (hps) {
685 WinQueryWindowRect(hwnd, &rcl);
686 WinFillRect(hps, &rcl, CLR_PALEGRAY);
687 PaintRecessedWindow(WinWindowFromID(WinQueryWindow(hwnd, QW_PARENT),
688 MAIN_STATUS), hps, FALSE, FALSE);
689 WinEndPaint(hps);
[2]690 }
[551]691 }
692 break;
[2]693
[551]694 case WM_SIZE:
695 WinSetWindowPos(WinWindowFromID(hwnd, TREE_CNR),
696 HWND_TOP,
697 0,
698 0,
699 SHORT1FROMMP(mp2),
700 SHORT2FROMMP(mp2), SWP_SHOW | SWP_MOVE | SWP_SIZE);
701 if (hwndMain)
702 PostMsg(hwndMain, UM_SIZE, MPVOID, MPVOID);
703 break;
[2]704
[551]705 case WM_CONTEXTMENU:
706 case UM_CONTEXTMENU:
707 PostMsg(WinWindowFromID(hwnd, TREE_CNR),
708 WM_CONTROL, MPFROM2SHORT(TREE_CNR, CN_CONTEXTMENU), MPVOID);
709 return 0;
[2]710 }
[551]711 return WinDefWindowProc(hwnd, msg, mp1, mp2);
[2]712}
713
[1856]714ULONG ulScanPostCnt;
715
[551]716MRESULT EXPENTRY TreeObjWndProc(HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2)
[156]717{
[2]718 DIRCNRDATA *dcd;
719
[551]720 switch (msg) {
721 case UM_SHOWME:
722 if (mp1) {
[1335]723# ifdef FORTIFY
724 Fortify_BecomeOwner(mp1);
725# endif
[551]726 dcd = INSTDATA(hwnd);
727 if (dcd) {
[2]728
[1856]729 /* Hold off if switching on focus change and
730 RestoreDirCnrState has restored one or directory directory containers
731 See RestoreDirCnrState()
732 */
733 if (cDirectoriesRestored > 0)
734 cDirectoriesRestored--;
735
736 if (!cDirectoriesRestored) {
737 BOOL tempsusp = dcd->suspendview;
738 BOOL tempfollow = fFollowTree;
739 dcd->suspendview = TRUE;
740 fFollowTree = FALSE;
[1873]741 priority_idle(); // 2015-09-26 GKY Majority of work done by Flesh and UI threads
742 ShowTreeRec(dcd->hwndCnr, (CHAR *)mp1, fCollapseFirst, TRUE);
743 priority_normal();
[1856]744 PostMsg(hwndTree, WM_COMMAND, MPFROM2SHORT(IDM_UPDATE, 0), MPVOID);
745
746 dcd->suspendview = (USHORT)tempsusp; // Restore
[1871]747 fFollowTree = tempfollow; // Restore
[1856]748 }
[2]749 }
[1039]750 free((CHAR *)mp1);
[551]751 }
752 return 0;
[2]753
[1874]754 case UM_TOPDIR:
755 if (mp1) {
756 dcd = INSTDATA(hwnd);
757 if (dcd) {
758 PCNRITEM pci = (PCNRITEM) mp1;
759 WaitFleshWorkListEmpty(pci->pszFileName, 240);
760 ShowCnrRecord(dcd->hwndCnr, (PMINIRECORDCORE) pci);
761 }
762 }
763 return 0;
764
[551]765 case DM_PRINTOBJECT:
766 return MRFROMLONG(DRR_TARGET);
[2]767
[551]768 case DM_DISCARDOBJECT:
769 dcd = INSTDATA(hwnd);
770 if (fFM2Deletes && dcd) {
[2]771
[551]772 LISTINFO *li;
773 CNRDRAGINFO cni;
[2]774
[551]775 cni.pRecord = NULL;
776 cni.pDragInfo = (PDRAGINFO) mp1;
777 li = DoFileDrop(dcd->hwndCnr,
[726]778 dcd->directory, FALSE, MPVOID, MPFROMP(&cni));
[687]779 CheckPmDrgLimit(cni.pDragInfo);
[551]780 if (li) {
781 li->type = ((fDefaultDeletePerm) ? IDM_PERMDELETE : IDM_DELETE);
782 if (!PostMsg(hwnd, UM_MASSACTION, MPFROMP(li), MPVOID))
783 FreeListInfo(li);
784 else
785 return MRFROMLONG(DRR_SOURCE);
[2]786 }
[551]787 }
788 return MRFROMLONG(DRR_TARGET);
[2]789
[551]790 case UM_EXPAND:
791 dcd = WinQueryWindowPtr(hwnd, QWL_USER);
792 if (!dcd)
[1398]793 Runtime_Error(pszSrcFile, __LINE__, NULL);
[551]794 else {
795 BOOL tempsusp = dcd->suspendview;
[1871]796 INT x = 0;
797 BOOL fExpanding = TRUE;
[1882]798 PCNRITEM pci = (PCNRITEM) mp2;
[2]799
[1882]800 if (!pci) {
801 Runtime_Error(pszSrcFile, __LINE__, NULL);
802 return 0;
803 }
[551]804 dcd->suspendview = TRUE;
[1871]805 priority_idle();
806 if (SHORT1FROMMP(mp1) == IDM_EXPAND) {
[1882]807 if (!(driveflags[toupper(*pci->pszFileName) - 'A'] & DRIVE_REMOVABLE))
808 fExpandAll = TRUE;
[1871]809 while (fExpanding) { // Not serialized not practical to wait on very large directories
810 x++;
811 if (!IsFleshWorkListEmpty()) {
[1882]812 WaitFleshWorkListEmpty(NULL, fExpandAll ? 1 : 50); // Let it expand
[1871]813 }
[1882]814 fExpanding = ExpandAll(dcd->hwndCnr, x, pci);
[1871]815 DosSleep(240);
816 }
817 fExpandAll = FALSE;
818 }
819 else
[1882]820 CollapseAll(dcd->hwndCnr, pci);
[1871]821 priority_normal();
[1796]822 DosSleep(1); // Fixes tree epansion (dir text and icons all placed on
[1856]823 // the same line as the drive) failure on startup using RWS
[1533]824 dcd->suspendview = (USHORT) tempsusp;
[551]825 PostMsg(dcd->hwndCnr, UM_FILTER, MPVOID, MPVOID);
826 }
827 return 0;
[2]828
[551]829 case UM_UPDATERECORDLIST:
830 dcd = WinQueryWindowPtr(hwnd, QWL_USER);
831 if (!dcd || !mp1)
[1398]832 Runtime_Error(pszSrcFile, __LINE__, NULL);
[551]833 else {
834 INT numentries = 0;
835 CHAR **list = (CHAR **) mp1;
[2]836
[551]837 while (list[numentries])
838 numentries++;
[1394]839 if (numentries)
840 UpdateCnrList(dcd->hwndCnr, list, numentries, TRUE, dcd);
[551]841 }
842 return 0;
[2]843
[1875]844 case UM_SETUP2:
845 {
846 PCNRITEM pci = (PCNRITEM) mp1;
847
848 if (pci) {
[1876]849 if ((INT) mp2 == 21 && pci->rc.hptrIcon == hptrCDROM) {
850 if (fEjectCDScan)
851 PostMsg(hwndTree, WM_COMMAND, MPFROM2SHORT(IDM_RESCAN, 0), MPVOID);
852 else {
853 driveflags[toupper(*pci->pszFileName) - 'A'] |= DRIVE_INVALID;
854 PostMsg(hwndTree, WM_COMMAND, MPFROM2SHORT(IDM_UPDATE, 0), MPVOID);
855 }
[1875]856 }
857 NotifyError(pci->pszFileName, (ULONG) mp2);
858 }
859 }
860 return 0;
861
[551]862 case UM_SETUP:
[1077]863# ifdef FORTIFY
864 Fortify_EnterScope();
865# endif
[551]866 dcd = WinQueryWindowPtr(hwnd, QWL_USER);
867 if (!dcd)
[1398]868 Runtime_Error(pszSrcFile, __LINE__, NULL);
[551]869 else {
[1077]870# ifdef FORTIFY
[1078]871 Fortify_BecomeOwner(dcd);
[1077]872# endif
[551]873 dcd->hwndObject = hwnd;
874 if (ParentIsDesktop(hwnd, dcd->hwndParent))
[1880]875 DosSleep(100);
[551]876 }
877 return 0;
878
879 case UM_RESCAN2:
880 dcd = WinQueryWindowPtr(hwnd, QWL_USER);
881 if (!dcd)
[1398]882 Runtime_Error(pszSrcFile, __LINE__, NULL);
[551]883 // Bypass if not running integrated (i.e if vtree)
884 else if (hwndStatus &&
885 dcd->hwndFrame == WinQueryActiveWindow(dcd->hwndParent)) {
886 CHAR s[CCHMAXPATH * 2];
887 PCNRITEM pci = (PCNRITEM) mp1;
888 FSALLOCATE fsa;
889 struct
890 {
891 ULONG serial;
892 CHAR volumelength;
893 CHAR volumelabel[CCHMAXPATH];
[2]894 }
[551]895 volser;
896 CHAR tb[64];
897 CHAR szFree[64];
898 CNRINFO cnri;
[1425]899 CHAR FileSystem[CCHMAXPATH * 2];
900 CHAR szTmpLabel[CCHMAXPATH];
901 ULONG type;
[2]902
[551]903 strcpy(s, GetPString(IDS_TREETEXT));
904 memset(&cnri, 0, sizeof(CNRINFO));
905 cnri.cb = sizeof(CNRINFO);
906 WinSendMsg(dcd->hwndCnr,
907 CM_QUERYCNRINFO,
908 MPFROMP(&cnri), MPFROMLONG(sizeof(CNRINFO)));
909 if (cnri.cRecords) {
910 sprintf(s, GetPString(IDS_NUMDRIVESTEXT), cnri.cRecords);
[1876]911 if (pci && (INT) pci != -1) {
[730]912 if (!(driveflags[toupper(*pci->pszFileName) - 'A'] &
[551]913 DRIVE_REMOVABLE) ||
[730]914 driveserial[toupper(*pci->pszFileName) - 'A'] != -1) {
[551]915 memset(&volser, 0, sizeof(volser));
916 DosError(FERR_DISABLEHARDERR);
[730]917 if (!DosQueryFSInfo(toupper(*pci->pszFileName) - '@',
[551]918 FSIL_VOLSER,
919 &volser,
920 (ULONG) sizeof(volser)) &&
921 dcd->hwndFrame == WinQueryActiveWindow(dcd->hwndParent)) {
[176]922 DosError(FERR_DISABLEHARDERR);
[730]923 if (!DosQueryFSInfo(toupper(*pci->pszFileName) - '@',
[551]924 FSIL_ALLOC, &fsa, sizeof(FSALLOCATE))) {
925 CommaFmtULL(tb, sizeof(tb),
926 (ULONGLONG) fsa.cUnitAvail * (fsa.cSectorUnit *
927 fsa.cbSector), 'M');
928 sprintf(szFree, " %s %s", tb, GetPString(IDS_FREETEXT));
929 }
930 else
[1856]931 *szFree = 0;
932 //Show information on status line not shown in the tree container
[1455]933 driveserial[toupper(*pci->pszFileName) - 'A'] = volser.serial;
[1856]934 if (CheckDrive(toupper(*pci->pszFileName), FileSystem, &type) == -1 ||
935 fShowFSTypeInTree)
[1455]936 strcpy(FileSystem, NullStr);
937 if (fShowDriveLabelInTree)
938 strcpy(szTmpLabel, NullStr);
939 else
940 strcpy(szTmpLabel, volser.volumelabel);
941 if (fSplitStatus) {
942 CHAR temp[CCHMAXPATH] = " [";
[1431]943
[1455]944 strcat(temp, s);
945 strcat(temp, "]");
946 sprintf(s,
947 GetPString(fShowFSTypeInTree ? IDS_TREESTATUSSTART1TEXT :
[1856]948 fShowDriveLabelInTree ? IDS_TREESTATUSSTART2TEXT :
949 IDS_TREESTATUSSTARTTEXT), toupper(*pci->pszFileName),
950 FileSystem, szTmpLabel, volser.serial, szFree);
[1455]951 strcat(s, temp);
952 }
953 else {
954 strcat(s, " [");
955 sprintf(&s[strlen(s)],
956 GetPString(fShowFSTypeInTree ? IDS_TREESTATUSSTART1TEXT :
[1856]957 fShowDriveLabelInTree ? IDS_TREESTATUSSTART2TEXT :
958 IDS_TREESTATUSSTARTTEXT), toupper(*pci->pszFileName),
959 FileSystem, szTmpLabel, volser.serial, szFree);
[1455]960 strcat(s, "]");
961 }
[551]962 if (!fMoreButtons) {
963 if (*dcd->mask.szMask ||
964 (dcd->mask.attrFile != ALLATTRS ||
965 ((fFilesInTree ||
[730]966 (driveflags[toupper(*pci->pszFileName)] &
[551]967 DRIVE_INCLUDEFILES)) ?
968 dcd->mask.antiattr :
969 (dcd->mask.antiattr &&
970 dcd->mask.antiattr != FILE_DIRECTORY)))) {
971 sprintf(&s[strlen(s)],
972 " (%s)",
973 (*dcd->mask.szMask) ?
974 dcd->mask.szMask : GetPString(IDS_ATTRTEXT));
[176]975 }
976 }
977 }
978 }
[1875]979 else {
980 // find root record and strip it if needed
981 pci = FindParentRecord(dcd->hwndCnr, pci);
982 driveserial[toupper(*pci->pszFileName) - 'A'] = -1;
[1876]983 if (pci->fleshed) {
[1875]984 WaitFleshWorkListEmpty(pci->pszFileName, 240); // 2015-08-19 SHL in case pci still in work list
[1876]985 if ((toupper(*pci->pszFileName) - 'A') > 1) {
986 AddFleshWorkRequest(hwnd, pci, eUnFlesh);
987 }
988 else
989 UnFlesh(hwnd, pci);
[1875]990 }
[551]991 }
[176]992 }
[2]993 }
[1856]994 // 21 Sep 09 SHL FIXME to know why checking again - focus change?
[551]995 if (dcd->hwndFrame == WinQueryActiveWindow(dcd->hwndParent))
996 WinSetWindowText(hwndStatus, s);
997 }
998 return 0;
[2]999
[551]1000 case UM_RESCAN:
[1858]1001 // Populate container
[551]1002 dcd = WinQueryWindowPtr(hwnd, QWL_USER);
1003 if (!dcd)
[1398]1004 Runtime_Error(pszSrcFile, __LINE__, NULL);
[551]1005 else {
[751]1006 RemoveCnrItems(dcd->hwndCnr, NULL, 0, CMA_FREE | CMA_INVALIDATE | CMA_ERASE);
[551]1007 WinSendMsg(dcd->hwndCnr,
1008 CM_SCROLLWINDOW, MPFROMSHORT(CMA_VERTICAL), MPFROMLONG(-1));
1009 WinSendMsg(dcd->hwndCnr,
1010 CM_SCROLLWINDOW,
[1455]1011 MPFROMSHORT(CMA_HORIZONTAL), MPFROMLONG(-1));
[551]1012 FillTreeCnr(dcd->hwndCnr, dcd->hwndParent);
1013 if (fOkayMinimize) {
1014 PostMsg(dcd->hwndCnr, UM_MINIMIZE, MPVOID, MPVOID);
1015 fOkayMinimize = FALSE;
[2]1016 }
[551]1017 WinSendMsg(dcd->hwndCnr,
1018 CM_INVALIDATERECORD,
[1856]1019 MPVOID, MPFROM2SHORT(0, CMA_ERASE | CMA_REPOSITION));
[551]1020 PostMsg(dcd->hwndCnr, UM_RESCAN, MPVOID, MPVOID);
1021 }
1022 return 0;
[2]1023
[551]1024 case UM_COMMAND:
1025 if (mp1) {
[2]1026
[551]1027 LISTINFO *li = (LISTINFO *) mp1;
[2]1028
[551]1029 switch (li->type) {
1030 case IDM_DOITYOURSELF:
1031 case IDM_APPENDTOCLIP:
1032 case IDM_SAVETOCLIP:
1033 case IDM_ARCHIVE:
1034 case IDM_VIEW:
1035 case IDM_EDIT:
1036 case IDM_OBJECT:
1037 case IDM_SHADOW:
1038 case IDM_SHADOW2:
[1803]1039 case IDM_JAVAEXE:
[551]1040 case IDM_PRINT:
1041 case IDM_ATTRS:
1042 case IDM_DELETE:
1043 case IDM_PERMDELETE:
[1856]1044 if (li->type == IDM_DELETE)
1045 ignorereadonly = FALSE;
[551]1046 if (PostMsg(hwnd, UM_MASSACTION, mp1, mp2))
1047 return (MRESULT) TRUE;
1048 default:
1049 if (PostMsg(hwnd, UM_ACTION, mp1, mp2))
1050 return (MRESULT) TRUE;
[2]1051 }
[551]1052 }
1053 return 0;
[2]1054
[551]1055 case UM_MASSACTION:
1056 if (mp1) {
[2]1057
[551]1058 dcd = WinQueryWindowPtr(hwnd, QWL_USER);
1059 if (!dcd)
[1398]1060 Runtime_Error(pszSrcFile, __LINE__, NULL);
[551]1061 else {
1062 WORKER *wk;
[1077]1063# ifdef FORTIFY
1064 Fortify_EnterScope();
1065# endif
[551]1066 wk = xmallocz(sizeof(WORKER), pszSrcFile, __LINE__);
1067 if (!wk)
1068 FreeListInfo((LISTINFO *) mp1);
[352]1069 else {
[551]1070 wk->size = sizeof(WORKER);
1071 wk->hwndCnr = dcd->hwndCnr;
1072 wk->hwndParent = dcd->hwndParent;
1073 wk->hwndFrame = dcd->hwndFrame;
1074 wk->hwndClient = dcd->hwndClient;
1075 wk->li = (LISTINFO *) mp1;
1076 strcpy(wk->directory, dcd->directory);
[1335]1077 if (xbeginthread(MassAction,
1078 122880,
1079 wk,
1080 pszSrcFile,
1081 __LINE__) == -1)
1082 {
[1077]1083 free(wk);
[551]1084 FreeListInfo((LISTINFO *) mp1);
[176]1085 }
1086 }
[1077]1087# ifdef FORTIFY
1088 Fortify_LeaveScope();
1089# endif
[2]1090 }
[551]1091 }
1092 return 0;
[2]1093
[551]1094 case UM_ACTION:
[1077]1095# ifdef FORTIFY
1096 Fortify_EnterScope();
1097# endif
[551]1098 if (mp1) {
[1077]1099# ifdef FORTIFY
[1078]1100 Fortify_BecomeOwner(mp1);
[1077]1101# endif
[551]1102 dcd = WinQueryWindowPtr(hwnd, QWL_USER);
1103 if (!dcd)
[1398]1104 Runtime_Error(pszSrcFile, __LINE__, NULL);
[551]1105 else {
1106 WORKER *wk;
1107 wk = xmallocz(sizeof(WORKER), pszSrcFile, __LINE__);
1108 if (!wk)
1109 FreeListInfo((LISTINFO *) mp1);
[352]1110 else {
[551]1111 wk->size = sizeof(WORKER);
1112 wk->hwndCnr = dcd->hwndCnr;
1113 wk->hwndParent = dcd->hwndParent;
1114 wk->hwndFrame = dcd->hwndFrame;
1115 wk->hwndClient = dcd->hwndClient;
1116 wk->li = (LISTINFO *) mp1;
1117 strcpy(wk->directory, dcd->directory);
[1335]1118 if (xbeginthread(Action,
1119 122880,
1120 wk,
1121 pszSrcFile,
1122 __LINE__) == -1)
1123 {
[1077]1124 free(wk);
[551]1125 FreeListInfo((LISTINFO *) mp1);
[176]1126 }
1127 }
[2]1128 }
[551]1129 }
[1077]1130# ifdef FORTIFY
1131 Fortify_LeaveScope();
1132# endif
[551]1133 return 0;
[2]1134
[551]1135 case WM_CLOSE:
1136 WinDestroyWindow(hwnd);
1137 break;
[2]1138
[551]1139 case WM_DESTROY:
1140 hwndTree = (HWND) 0;
1141 dcd = WinQueryWindowPtr(hwnd, QWL_USER);
1142 if (dcd) {
1143 WinSendMsg(dcd->hwndCnr,
1144 UM_CLOSE, MPFROMLONG(dcd->dontclose != FALSE), MPVOID);
[1513]1145 WinSetWindowPtr(dcd->hwndCnr, QWL_USER, NULL); // 13 Apr 10 SHL Set NULL before freeing dcd
[1039]1146 free(dcd);
[1063]1147# ifdef FORTIFY
1148 Fortify_LeaveScope();
[1077]1149# endif
[551]1150 }
[1860]1151 xDosPostEventSem(CompactSem);
[551]1152 if (!PostMsg((HWND) 0, WM_QUIT, MPVOID, MPVOID))
1153 WinSendMsg((HWND) 0, WM_QUIT, MPVOID, MPVOID);
1154 break;
[2]1155 }
[551]1156 return WinDefWindowProc(hwnd, msg, mp1, mp2);
[2]1157}
1158
[551]1159MRESULT EXPENTRY TreeCnrWndProc(HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2)
[305]1160{
[551]1161 static APPNOTIFY *apphead = NULL, *apptail = NULL;
[672]1162 DIRCNRDATA *dcd = INSTDATA(hwnd);
[1411]1163 PCNRITEM pci;
[1856]1164 APIRET rc;
[2]1165
[551]1166 switch (msg) {
1167 case DM_PRINTOBJECT:
1168 return MRFROMLONG(DRR_TARGET);
1169
1170 case DM_DISCARDOBJECT:
1171 if (dcd)
1172 return WinSendMsg(dcd->hwndObject, msg, mp1, mp2);
1173 else
[2]1174 return MRFROMLONG(DRR_TARGET);
1175
[551]1176 case WM_CHAR:
1177 shiftstate = (SHORT1FROMMP(mp1) & (KC_SHIFT | KC_ALT | KC_CTRL));
1178 if (SHORT1FROMMP(mp1) & KC_KEYUP)
1179 return (MRESULT) TRUE;
1180 if (SHORT1FROMMP(mp1) & KC_VIRTUALKEY) {
1181 switch (SHORT2FROMMP(mp2)) {
1182 case VK_INSERT:
1183 if ((shiftstate & KC_CTRL) == KC_CTRL)
1184 PostMsg(hwnd, WM_COMMAND, MPFROM2SHORT(IDM_MKDIR, 0), MPVOID);
1185 break;
1186 case VK_DELETE:
1187 if ((shiftstate & KC_CTRL) == KC_CTRL)
1188 PostMsg(hwnd, WM_COMMAND, MPFROM2SHORT(IDM_PERMDELETE, 0), MPVOID);
1189 else if ((shiftstate & KC_SHIFT) == KC_SHIFT)
1190 PostMsg(hwnd, WM_COMMAND, MPFROM2SHORT(IDM_SAVETOCLIP, 0), MPVOID);
1191 else
1192 PostMsg(hwnd, WM_COMMAND, MPFROM2SHORT(IDM_DELETE, 0), MPVOID);
1193 break;
[1411]1194 } // switch
[551]1195 }
[2]1196
[1411]1197 if (SearchContainer(hwnd, msg, mp1, mp2))
1198 return (MRESULT)TRUE; // Avoid default handler
[2]1199
[1411]1200 break; // Let default handler see key
[2]1201
[551]1202 case WM_MOUSEMOVE:
1203 case WM_BUTTON1UP:
1204 case WM_BUTTON2UP:
1205 case WM_BUTTON3UP:
1206 shiftstate = (SHORT2FROMMP(mp2) & (KC_SHIFT | KC_ALT | KC_CTRL));
1207 break;
[2]1208
[551]1209 case UM_TIMER:
1210 if (dcd && dcd->hwndFrame == WinQueryActiveWindow(dcd->hwndParent) &&
1211 hwndStatus2) {
[841]1212 FILEFINDBUF3L ffb;
[761]1213 ULONG nm = 1;
[551]1214 HDIR hdir = HDIR_CREATE;
[2]1215
[551]1216 if (*SwapperDat) {
[838]1217 if (!xDosFindFirst(SwapperDat,
1218 &hdir,
1219 FILE_NORMAL | FILE_HIDDEN |
1220 FILE_SYSTEM | FILE_ARCHIVED | FILE_READONLY,
[841]1221 &ffb, sizeof(ffb), &nm, FIL_STANDARDL)) {
[551]1222 CHAR tb[39], tm[39], tpm[39], s[163];
1223 ULONG amem;
[2]1224
[551]1225 priority_bumped();
1226 DosFindClose(hdir);
1227 if (!DosQuerySysInfo(QSV_TOTAVAILMEM,
1228 QSV_TOTAVAILMEM,
1229 (PVOID) & amem, sizeof(amem))) {
1230 CommaFmtULL(tpm, sizeof(tpm), amem, 'M');
[176]1231 }
1232 else
[551]1233 *tpm = 0;
1234 if (!Dos16MemAvail(&amem))
1235 CommaFmtULL(tm, sizeof(tm), amem, 'M');
1236 else
1237 *tm = 0;
1238 CommaFmtULL(tb, sizeof(tb), ffb.cbFile, 'M');
1239 sprintf(s, " %s %s%s%s%s%s",
1240 GetPString(IDS_SWAPFILETEXT),
1241 tb,
1242 *tm ? GetPString(IDS_TREEMEMTEXT) : NullStr,
1243 tm, *tpm ? "/" : NullStr, tpm);
1244 WinSetWindowText(hwndStatus2, s);
[176]1245 }
1246 else
[551]1247 WinSetWindowText(hwndStatus2, NullStr);
[2]1248 }
[551]1249 else
1250 WinSetWindowText(hwndStatus2, NullStr);
1251 }
[1856]1252 // 13 Jul 09 SHL FIXME to make sense
[551]1253 if (msg == UM_TIMER)
1254 return 0;
1255 break;
[2]1256
[551]1257 case WM_PRESPARAMCHANGED:
[1400]1258 PresParamChanged(hwnd, PCSZ_TREECNR, mp1, mp2);
[551]1259 break;
[2]1260
[551]1261 case UM_FILESMENU:
1262 {
1263 HWND menuHwnd = (HWND) 0;
[1251]1264 FSALLOCATE fsa;
[2]1265
[1856]1266 pci = (PCNRITEM)CurrentRecord(hwnd);
1267 if (pci && (INT)pci != -1) {
[1335]1268 if (IsRoot(pci->pszFileName) || !DosQueryFSInfo(toupper(*pci->pszFileName) - '@',
1269 FSIL_ALLOC, &fsa,
1270 sizeof(FSALLOCATE)))
[875]1271 menuHwnd = CheckMenu(hwndMainMenu, &TreeMenu, TREE_POPUP);
[551]1272 else {
[875]1273 menuHwnd = CheckMenu(hwndMainMenu, &DirMenu, DIR_POPUP);
[176]1274 }
[551]1275 if (!(pci->attrFile & FILE_DIRECTORY))
[875]1276 menuHwnd = CheckMenu(hwndMainMenu, &FileMenu, FILE_POPUP);
[2]1277 }
[551]1278 return MRFROMLONG(menuHwnd);
1279 }
[2]1280
[551]1281 case UM_COMPARE:
1282 if (dcd && mp1 && mp2) {
[2]1283
[551]1284 COMPARE *cmp;
[1009]1285 CHAR *leftdir = (CHAR *)mp1, *rightdir = (CHAR *)mp2;
[2]1286
[551]1287 if (!IsFile(leftdir) && !IsFile(rightdir)) {
1288 cmp = xmallocz(sizeof(COMPARE), pszSrcFile, __LINE__);
1289 if (cmp) {
1290 cmp->size = sizeof(COMPARE);
1291 strcpy(cmp->leftdir, leftdir);
1292 strcpy(cmp->rightdir, rightdir);
1293 cmp->hwndParent = dcd->hwndParent;
1294 cmp->dcd.hwndParent = dcd->hwndParent;
1295 WinDlgBox(HWND_DESKTOP,
1296 HWND_DESKTOP,
1297 CompareDlgProc, FM3ModHandle, COMP_FRAME, MPFROMP(cmp));
[176]1298 }
[2]1299 }
[551]1300 }
1301 return 0;
[2]1302
[551]1303 case UM_UPDATERECORDLIST:
1304 if (dcd && mp1)
1305 WinSendMsg(dcd->hwndObject, msg, mp1, mp2);
1306 return 0;
[2]1307
[551]1308 case UM_UPDATERECORD:
1309 if (dcd && mp1) {
1310 CHAR *filename;
1311 filename = mp1;
[1352]1312 if (filename) {
[1394]1313 UpdateCnrRecord(hwnd, filename, TRUE, dcd);
[1352]1314 }
[551]1315 }
1316 return 0;
[2]1317
[551]1318 case WM_SETFOCUS:
1319 if (dcd && hwndStatus && mp2) {
1320 WinSendMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
1321 if (hwndMain)
1322 PostMsg(hwndMain, UM_ADVISEFOCUS, MPFROMLONG(dcd->hwndFrame), MPVOID);
1323 }
1324 break;
[2]1325
[551]1326 case UM_RESCAN:
[1552]1327
[551]1328 if (dcd && dcd->hwndFrame == WinQueryActiveWindow(dcd->hwndParent)) {
[1673]1329 // put name of our window on status line
[2]1330
[551]1331 PCNRITEM pci = NULL;
1332 CHAR str[CCHMAXPATH + 6];
[2]1333
[551]1334 if (fAutoView && hwndMain) {
1335 pci = WinSendMsg(hwnd,
1336 CM_QUERYRECORDEMPHASIS,
1337 MPFROMLONG(CMA_FIRST), MPFROMSHORT(CRA_CURSORED));
1338 if (pci && (INT) pci != -1 && fComments &&
[730]1339 !(driveflags[toupper(*pci->pszFileName) - 'A'] & DRIVE_SLOW))
1340 WinSendMsg(hwndMain, UM_LOADFILE, MPFROMP(pci->pszFileName), MPVOID);
[551]1341 else
1342 WinSendMsg(hwndMain, UM_LOADFILE, MPVOID, MPVOID);
1343 }
1344 if (!fAutoView || !hwndMain)
1345 pci = (PCNRITEM) WinSendMsg(hwnd,
1346 CM_QUERYRECORDEMPHASIS,
1347 MPFROMLONG(CMA_FIRST),
1348 MPFROMSHORT(CRA_CURSORED));
1349 if ((INT) pci == -1)
1350 pci = NULL;
1351 if (pci) {
1352 if (*(ULONG *) realappname == FM3UL) {
[730]1353 sprintf(str, "%s %s", GetPString(IDS_DTTEXT), pci->pszFileName);
[551]1354 WinSetWindowText(dcd->hwndFrame, str);
1355 WinSetWindowText(WinWindowFromID(dcd->hwndFrame, FID_TITLEBAR),
1356 str);
[176]1357 }
[551]1358 else
1359 WinSetWindowText(WinWindowFromID(dcd->hwndFrame,
[1856]1360 MAIN_STATUS), pci->pszFileName);
[1411]1361 if (fMoreButtons && hwndName) {
1362 CHAR szDate[DATE_BUF_BYTES];
[1395]1363
[1411]1364 DateFormat(szDate, pci->date);
[730]1365 WinSetWindowText(hwndName, pci->pszFileName);
[1395]1366 sprintf(str, "%s %02u%s%02u%s%02u", szDate,
[1411]1367 pci->time.hours, TimeSeparator,
1368 pci->time.minutes, TimeSeparator, pci->time.seconds);
[551]1369 WinSetWindowText(hwndDate, str);
1370 WinSetWindowText(hwndAttr, pci->pszDispAttr);
[176]1371 }
[2]1372 }
[551]1373 PostMsg(dcd->hwndObject, UM_RESCAN2, MPFROMP(pci), MPVOID);
1374 if (hwndStatus2)
1375 PostMsg(hwnd, UM_TIMER, MPVOID, MPVOID);
1376 }
1377 return 0;
[2]1378
[551]1379 case UM_SETUP:
[1335]1380# ifdef FORTIFY
1381 // Balance WM_DESTROY
1382 Fortify_EnterScope();
1383# endif
1384
[551]1385 if (!dcd) {
[1398]1386 Runtime_Error(pszSrcFile, __LINE__, NULL);
[551]1387 PostMsg(hwnd, WM_CLOSE, MPVOID, MPVOID);
[2]1388 return 0;
[551]1389 }
1390 else {
1391 if (!dcd->hwndObject) {
[1673]1392 // first time through -- set things up
[551]1393 CNRINFO cnri;
[2]1394
[1077]1395# ifdef FORTIFY
1396 Fortify_EnterScope();
1397# endif
1398
[1400]1399 RestorePresParams(hwnd, PCSZ_TREECNR);
[551]1400 memset(&cnri, 0, sizeof(CNRINFO));
1401 cnri.cb = sizeof(CNRINFO);
1402 WinSendMsg(hwnd,
1403 CM_QUERYCNRINFO,
1404 MPFROMP(&cnri), MPFROMLONG(sizeof(CNRINFO)));
1405 cnri.cyLineSpacing = 0;
[766]1406 cnri.cxTreeIndent = 12;
[551]1407 cnri.pSortRecord = (PVOID) SortTreeCnr;
1408 cnri.flWindowAttr &= (~(CV_NAME | CV_DETAIL | CV_TEXT));
1409 cnri.flWindowAttr |= (CV_TREE | CA_TREELINE | CV_ICON | CV_MINI);
1410 {
1411 ULONG size = sizeof(ULONG);
[2]1412
[551]1413 PrfQueryProfileData(fmprof,
1414 appname,
1415 "TreeflWindowAttr",
1416 (PVOID) & cnri.flWindowAttr, &size);
1417 size = sizeof(MASK);
1418 *dcd->mask.prompt = 0;
1419 if (!*dcd->mask.szMask && !dcd->mask.attrFile) {
1420 if (PrfQueryProfileSize(fmprof,
1421 appname, "TreeFilter", &size) && size) {
1422 PrfQueryProfileData(fmprof,
1423 appname, "TreeFilter", &dcd->mask, &size);
1424 SetMask(NULL, &dcd->mask);
[176]1425 }
[551]1426 else
1427 dcd->mask.attrFile = (FILE_READONLY | FILE_NORMAL |
1428 FILE_ARCHIVED | FILE_DIRECTORY |
1429 FILE_HIDDEN | FILE_SYSTEM);
[176]1430 }
[551]1431 dcd->mask.attrFile |= FILE_DIRECTORY;
[176]1432 }
[551]1433 cnri.flWindowAttr &= (~(CA_MIXEDTARGETEMPH | CA_ORDEREDTARGETEMPH));
1434 cnri.flWindowAttr |= CV_FLOW;
[1394]1435 dcd->flWindowAttr = cnri.flWindowAttr;
[551]1436 WinSendMsg(hwnd,
1437 CM_SETCNRINFO,
1438 MPFROMP(&cnri),
1439 MPFROMLONG(CMA_FLWINDOWATTR | CMA_LINESPACING |
[1394]1440 CMA_CXTREEINDENT | CMA_PSORTRECORD));
[1335]1441 if (xbeginthread(MakeObjWin,
1442 327680,
1443 dcd,
1444 pszSrcFile,
1445 __LINE__) == -1)
1446 {
[551]1447 PostMsg(hwnd, WM_CLOSE, MPVOID, MPVOID);
1448 }
1449 else
[766]1450 DosSleep(1);
[1079]1451# ifdef FORTIFY
1452 Fortify_LeaveScope();
1453# endif
[2]1454 }
[551]1455 }
1456 return 0;
[2]1457
[551]1458 case WM_BUTTON3CLICK:
1459 case WM_CHORD:
1460 {
1461 PCNRITEM pci = NULL;
1462 QUERYRECFROMRECT pqr;
1463 NOTIFYRECORDENTER nr;
1464 BOOL tbool = fDCOpens;
1465 RECTL rectl;
1466 POINTL ptl;
[2]1467
[551]1468 shiftstate = (SHORT2FROMMP(mp2) & (KC_SHIFT | KC_ALT | KC_CTRL));
1469 if (msg == WM_CHORD) {
1470 if (!WinQueryPointerPos(HWND_DESKTOP, &ptl))
1471 break;
[766]1472 WinMapWindowPoints(HWND_DESKTOP, hwnd, &ptl, 1);
[2]1473 }
[551]1474 else {
1475 ptl.x = SHORT1FROMMP(mp1);
1476 ptl.y = SHORT2FROMMP(mp1);
1477 }
1478 memset(&rectl, 0, sizeof(rectl));
1479 memset(&pqr, 0, sizeof(pqr));
1480 pqr.cb = sizeof(pqr);
1481 pqr.rect.xLeft = ptl.x - 1;
1482 pqr.rect.xRight = ptl.x + 1;
1483 pqr.rect.yTop = ptl.y + 1;
1484 pqr.rect.yBottom = ptl.y - 1;
1485 pqr.fsSearch = CMA_PARTIAL;
1486 pci = (PCNRITEM) WinSendMsg(hwnd,
1487 CM_QUERYRECORDFROMRECT,
1488 MPFROMLONG(CMA_FIRST), MPFROMP(&pqr));
1489 if (!pci || (INT) pci == -1)
[1398]1490 break; //Probable B3 click on white space
[551]1491 else {
1492 memset(&nr, 0, sizeof(nr));
1493 nr.hwndCnr = hwnd;
1494 nr.pRecord = (PRECORDCORE) pci;
1495 fDCOpens = TRUE;
1496 WinSendMsg(hwnd,
1497 WM_CONTROL,
1498 MPFROM2SHORT(WinQueryWindowUShort(hwnd,
1499 QWS_ID),
1500 CN_ENTER), MPFROMP(&nr));
1501 PostMsg(hwnd, UM_RESTOREDC, MPFROMLONG(tbool), MPVOID);
1502 }
1503 }
1504 break;
[2]1505
[551]1506 case UM_RESTOREDC:
1507 fDCOpens = (BOOL) mp1;
1508 return 0;
[2]1509
[551]1510 case WM_CONTROL:
1511 DosError(FERR_DISABLEHARDERR);
1512 if (dcd) {
1513 switch (SHORT2FROMMP(mp1)) {
1514 case CN_BEGINEDIT:
1515 case CN_REALLOCPSZ:
1516 case CN_ENDEDIT:
1517 {
1518 MRESULT mre;
[2]1519
[551]1520 mre = CnrDirectEdit(hwnd, msg, mp1, mp2);
1521 if (mre != (MRESULT) - 1)
1522 return mre;
1523 }
1524 break;
[2]1525
[551]1526 case CN_DRAGLEAVE:
1527 if (mp2) {
[2]1528
[551]1529 PDRAGINFO pDInfo;
[2]1530
[618]1531 // fixme to know why - seems superfluous
[551]1532 pDInfo = ((PCNRDRAGINFO) mp2)->pDragInfo;
1533 DrgAccessDraginfo(pDInfo);
1534 DrgFreeDraginfo(pDInfo);
1535 }
[1394]1536 return 0;
[1357]1537
1538 case CN_DROPHELP:
1539 if (mp2) {
1540
1541 PDRAGINFO pDInfo;
1542 PCNRITEM pci;
1543 ULONG numitems;
1544 USHORT usOperation;
1545
1546 pci = (PCNRITEM) ((PCNRDRAGINFO) mp2)->pRecord;
1547 pDInfo = (PDRAGINFO) ((PCNRDRAGINFO) mp2)->pDragInfo;
1548 if (!DrgAccessDraginfo(pDInfo)) {
1549 Win_Error(hwnd, hwnd, pszSrcFile, __LINE__,
1550 GetPString(IDS_DROPERRORTEXT));
1551 }
1552 else {
1553 numitems = DrgQueryDragitemCount(pDInfo);
[1394]1554 usOperation = pDInfo->usOperation;
1555 if (usOperation == DO_DEFAULT)
1556 usOperation = fCopyDefault ? DO_COPY : DO_MOVE;
[1357]1557 FreeDragInfoData(hwnd, pDInfo);
1558 saymsg(MB_ENTER | MB_ICONASTERISK,
1559 hwnd,
1560 GetPString(IDS_DROPHELPHDRTEXT),
1561 GetPString(IDS_DROPHELPTEXT),
1562 numitems,
1563 &"s"[numitems == 1L],
1564 pci ? NullStr : GetPString(IDS_NOTEXT),
1565 pci ? NullStr : " ",
1566 pci ? pci->pszFileName : NullStr,
1567 pci ? " " : NullStr,
1568 GetPString((usOperation == DO_MOVE) ?
1569 IDS_MOVETEXT :
1570 (usOperation == DO_LINK) ?
1571 IDS_LINKTEXT : IDS_COPYTEXT));
1572 }
1573 }
[551]1574 return 0;
[2]1575
[551]1576 case CN_DRAGAFTER:
1577 case CN_DRAGOVER:
1578 if (mp2) {
[2]1579
[551]1580 PDRAGITEM pDItem;
1581 PDRAGINFO pDInfo;
1582 PCNRITEM pci;
1583 USHORT uso;
[2]1584
[551]1585 pDInfo = ((PCNRDRAGINFO) mp2)->pDragInfo;
[618]1586 if (!DrgAccessDraginfo(pDInfo)) {
1587 Win_Error(hwnd, hwnd, pszSrcFile, __LINE__,
[1402]1588 PCSZ_DRGACCESSDRAGINFO);
[1673]1589 return (MRFROM2SHORT(DOR_NODROP, 0)); // Drop not valid
[618]1590 }
[551]1591 pci = (PCNRITEM) ((PCNRDRAGINFO) mp2)->pRecord;
1592 if ((INT) pci == -1)
1593 pci = NULL;
1594 if (pci && (pci->flags & (RECFLAGS_ENV | RECFLAGS_NODROP))) {
1595 DrgFreeDraginfo(pDInfo);
1596 return MRFROM2SHORT(DOR_NODROP, 0);
1597 }
1598 if (!WinIsWindowEnabled(dcd->hwndFrame)) {
1599 DrgFreeDraginfo(pDInfo);
1600 return MRFROM2SHORT(DOR_NODROP, 0);
1601 }
1602 if (pci) {
1603 uso = pDInfo->usOperation;
1604 if (uso == DO_DEFAULT)
1605 uso = (fCopyDefault) ? DO_COPY : DO_MOVE;
1606 if (!(pci->attrFile & FILE_DIRECTORY)) {
1607 if (uso != DO_LINK && uso != DO_COPY && uso != DO_MOVE) {
[176]1608 DrgFreeDraginfo(pDInfo);
[551]1609 return (MRFROM2SHORT(DOR_NODROP, 0));
[176]1610 }
[551]1611 if (uso != DO_LINK &&
[730]1612 !(driveflags[toupper(*pci->pszFileName) - 'A'] &
[551]1613 DRIVE_NOTWRITEABLE)) {
[2]1614
[551]1615 ARC_TYPE *info;
[2]1616
[551]1617 if (!fQuickArcFind &&
[730]1618 !(driveflags[toupper(*pci->pszFileName) - 'A'] &
[551]1619 DRIVE_SLOW))
[730]1620 info = find_type(pci->pszFileName, NULL);
[551]1621 else
[730]1622 info = quick_find_type(pci->pszFileName, NULL);
[551]1623 if (!info || ((uso == DO_MOVE && !info->move) ||
1624 (uso == DO_COPY && !info->create))) {
1625 DrgFreeDraginfo(pDInfo);
1626 return (MRFROM2SHORT(DOR_NODROP, 0));
[176]1627 }
1628 }
1629 }
[551]1630 }
[1856]1631 pDItem = DrgQueryDragitemPtr(pDInfo, // Access DRAGITEM
1632 0); // Index to DRAGITEM
1633 if (DrgVerifyRMF(pDItem, // Check valid rendering
[1673]1634 (CHAR *) DRM_OS2FILE, // mechanisms and data
[1856]1635 NULL) || DrgVerifyRMF(pDItem,
1636 (CHAR *) DRM_FM2ARCMEMBER,
1637 (CHAR *) DRF_FM2ARCHIVE)) { // formats
1638 DrgFreeDraginfo(pDInfo); // Free DRAGINFO
[551]1639 if (!pci || (INT) pci == -1)
1640 return MRFROM2SHORT(DOR_DROP, DO_MOVE);
[730]1641 if (driveflags[toupper(*pci->pszFileName) - 'A'] &
[551]1642 DRIVE_NOTWRITEABLE)
1643 return MRFROM2SHORT(DOR_DROP, DO_LINK);
[730]1644 if (toupper(*pci->pszFileName) < 'C')
[551]1645 return MRFROM2SHORT(DOR_DROP, DO_COPY);
[1856]1646 return MRFROM2SHORT(DOR_DROP, // Return okay to drop
[551]1647 ((fCopyDefault) ? DO_COPY : DO_MOVE));
1648 }
[1856]1649 DrgFreeDraginfo(pDInfo); // Free DRAGINFO
[551]1650 }
[1856]1651 return MRFROM2SHORT(DOR_NODROP, 0); // Drop not valid
[2]1652
[551]1653 case CN_INITDRAG:
1654 {
1655 PCNRDRAGINIT pcd = (PCNRDRAGINIT) mp2;
1656 PCNRITEM pci;
[2]1657
[551]1658 if (!pcd) {
[1398]1659 Runtime_Error(pszSrcFile, __LINE__, NULL);
[551]1660 break;
1661 }
1662 else {
1663 pci = (PCNRITEM) pcd->pRecord;
1664 if (!pci || (INT) pci == -1) {
[1398]1665 Runtime_Error(pszSrcFile, __LINE__, NULL);
[551]1666 break;
[176]1667 }
[551]1668 if (pci->flags & (RECFLAGS_ENV | RECFLAGS_NODRAG)) {
1669 Runtime_Error(pszSrcFile, __LINE__, "drag not allowed");
1670 break;
1671 }
1672 if (hwndStatus2) {
[730]1673 WinSetWindowText(hwndStatus2, (IsRoot(pci->pszFileName)) ?
[1498]1674 (CHAR *) GetPString(IDS_DRAGROOTTEXT) :
[551]1675 (pci->attrFile & FILE_DIRECTORY) ?
[1498]1676 (CHAR *) GetPString(IDS_DRAGDIRTEXT) :
1677 (CHAR *) GetPString(IDS_DRAGFILETEXT));
[551]1678 }
1679 DoFileDrag(hwnd, dcd->hwndObject, mp2, NULL, NULL, TRUE);
1680 if (hwndStatus2) {
1681 PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
1682 }
1683 }
1684 }
1685 return 0;
[2]1686
[551]1687 case CN_DROP:
1688 {
1689 LISTINFO *li;
1690 ULONG action = UM_ACTION;
[2]1691
[726]1692 li = DoFileDrop(hwnd, NULL, TRUE, mp1, mp2);
1693 CheckPmDrgLimit(((PCNRDRAGINFO)mp2)->pDragInfo);
[551]1694 if (li) {
1695 if (!*li->targetpath) {
1696 if (li->list[0])
1697 PMMkDir(dcd->hwndParent, li->list[0], FALSE);
1698 FreeListInfo(li);
1699 return 0;
1700 }
1701 if (li->list && li->list[0] && IsRoot(li->list[0]))
1702 li->type = DO_LINK;
1703 else if (fDragndropDlg && (!*li->arcname || !li->info)) {
[2]1704
[551]1705 CHECKLIST cl;
[2]1706
[551]1707 memset(&cl, 0, sizeof(cl));
1708 cl.size = sizeof(cl);
1709 cl.flags = li->type;
1710 cl.list = li->list;
1711 cl.cmd = li->type;
1712 cl.prompt = li->targetpath;
1713 li->type = WinDlgBox(HWND_DESKTOP,
1714 dcd->hwndParent,
1715 DropListProc,
[618]1716 FM3ModHandle, DND_FRAME, MPFROMP(&cl));
1717 if (li->type == DID_ERROR)
1718 Win_Error(hwnd, HWND_DESKTOP, pszSrcFile, __LINE__,
[1402]1719 GetPString(IDS_DRAGDROPDIALOGTEXT));
[618]1720 if (!li->type) {
[551]1721 FreeListInfo(li);
1722 return 0;
1723 }
1724 li->list = cl.list;
[618]1725 if (!li->list || !li->list[0]) {
[551]1726 FreeListInfo(li);
1727 return 0;
1728 }
1729 }
1730 switch (li->type) {
1731 case DO_LINK:
1732 if (fLinkSetsIcon) {
1733 li->type = IDM_SETICON;
1734 action = UM_MASSACTION;
1735 }
1736 else
1737 li->type = IDM_COMPARE;
1738 break;
1739 case DND_EXTRACT:
1740 if (*li->targetpath && !IsFile(li->targetpath))
1741 li->type = IDM_EXTRACT;
1742 break;
1743 case DND_MOVE:
1744 li->type = IDM_MOVE;
1745 if (*li->targetpath && IsFile(li->targetpath) == 1) {
1746 action = UM_MASSACTION;
1747 li->type = IDM_ARCHIVEM;
1748 }
1749 break;
1750 case DND_WILDMOVE:
1751 li->type = IDM_WILDMOVE;
1752 if (*li->targetpath && IsFile(li->targetpath) == 1) {
1753 action = UM_MASSACTION;
1754 li->type = IDM_ARCHIVEM;
1755 }
1756 break;
1757 case DND_OBJECT:
1758 li->type = IDM_OBJECT;
1759 action = UM_MASSACTION;
1760 break;
1761 case DND_SHADOW:
1762 li->type = IDM_SHADOW;
1763 action = UM_MASSACTION;
1764 break;
1765 case DND_COMPARE:
1766 li->type = IDM_COMPARE;
1767 break;
1768 case DND_SETICON:
1769 action = UM_MASSACTION;
1770 li->type = IDM_SETICON;
1771 break;
1772 case DND_COPY:
1773 li->type = IDM_COPY;
1774 if (*li->targetpath && IsFile(li->targetpath) == 1) {
1775 action = UM_MASSACTION;
1776 li->type = IDM_ARCHIVE;
1777 }
1778 break;
1779 case DND_WILDCOPY:
1780 li->type = IDM_WILDCOPY;
1781 if (*li->targetpath && IsFile(li->targetpath) == 1) {
1782 action = UM_MASSACTION;
1783 li->type = IDM_ARCHIVE;
1784 }
1785 break;
1786 default:
1787 if (*li->arcname && li->info) {
1788 action = UM_MASSACTION;
1789 li->type = (li->type == DO_MOVE) ?
1790 IDM_FAKEEXTRACTM : IDM_FAKEEXTRACT;
1791 }
1792 else if (*li->targetpath && IsFile(li->targetpath) == 1) {
1793 action = UM_MASSACTION;
1794 li->type = (li->type == DO_MOVE) ? IDM_ARCHIVEM : IDM_ARCHIVE;
1795 }
1796 else
1797 li->type = (li->type == DO_MOVE) ? IDM_MOVE : IDM_COPY;
1798 break;
1799 }
1800 if (!li->list || !li->list[0])
1801 FreeListInfo(li);
1802 else if (!PostMsg(dcd->hwndObject, action, MPFROMP(li), MPVOID))
1803 FreeListInfo(li);
1804 else {
[2]1805
[551]1806 USHORT usop = 0;
[2]1807
[551]1808 switch (li->type) {
1809 case IDM_COPY:
1810 case IDM_WILDCOPY:
1811 usop = DO_COPY;
1812 break;
1813 case IDM_MOVE:
1814 case IDM_WILDMOVE:
1815 case IDM_ARCHIVEM:
1816 usop = DO_MOVE;
1817 break;
[176]1818 }
[551]1819 if (usop)
1820 return MRFROM2SHORT(DOR_DROP, usop);
[176]1821 }
[551]1822 }
1823 }
1824 return 0;
[2]1825
[551]1826 case CN_EMPHASIS:
[1868]1827 {
1828 PNOTIFYRECORDEMPHASIS pre = mp2;
[2]1829
[1868]1830 if (pre->fEmphasisMask & CRA_SELECTED) {
1831 if (pre->pRecord->flRecordAttr & CRA_SELECTED) {
1832 if (((PCNRITEM) (pre->pRecord))->attrFile & FILE_DIRECTORY) {
1833 PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
1834 if (fFollowTree &&
1835 !(driveflags
1836 [toupper(*((PCNRITEM) pre->pRecord)->pszFileName) -
1837 'A'] & DRIVE_INVALID)) {
1838 if (!LastDir && !ParentIsDesktop(hwnd, dcd->hwndParent))
1839 LastDir = FindDirCnr(dcd->hwndParent);
1840 if (LastDir) {
1841
1842 NOTIFYRECORDENTER pri;
1843 BOOL tbool = fDCOpens;
1844
1845 fDCOpens = FALSE;
1846 memset(&pri, 0, sizeof(pri));
1847 pri.hwndCnr = hwnd;
1848 pri.fKey = FALSE;
1849 pri.pRecord = pre->pRecord;
1850 WinSendMsg(hwnd,
1851 WM_CONTROL,
1852 MPFROM2SHORT(SHORT1FROMMP(mp1),
1853 CN_ENTER), MPFROMP(&pri));
1854 fDCOpens = tbool;
1855 }
1856 }
1857 if (*(ULONG *) realappname != FM3UL)
1858 WinSetWindowText(WinWindowFromID(dcd->hwndFrame,
1859 MAIN_STATUS),
1860 ((PCNRITEM) (pre->pRecord))->pszFileName);
1861 }
1862 }
1863 }
1864 }
1865 break;
[2]1866
[551]1867 case CN_CONTEXTMENU:
1868 {
[1856]1869 PCNRITEM pci = (PCNRITEM)mp2;
[551]1870 BOOL wasFollowing;
[2]1871
[551]1872 wasFollowing = fFollowTree;
1873 fFollowTree = FALSE;
[1856]1874 if (pci && (INT)pci != -1 && !(pci->flags & RECFLAGS_ENV)) {
1875 // 2015-08-09 SHL try to ensure contents stable
1876 if (!IsFleshWorkListEmpty())
1877 WinPostMsg(hwnd, msg, mp1, mp2); // Try again later
1878 else {
1879 WinSendMsg(hwnd,
1880 CM_SETRECORDEMPHASIS,
1881 MPFROMP(pci), MPFROM2SHORT(TRUE, CRA_CURSORED));
1882 MarkAll(hwnd, FALSE, FALSE, TRUE);
1883 if (!(pci->attrFile & FILE_DIRECTORY))
1884 dcd->hwndLastMenu = CheckMenu(hwndMainMenu, &FileMenu, FILE_POPUP);
1885 else if (!IsRoot(pci->pszFileName))
1886 dcd->hwndLastMenu = CheckMenu(hwndMainMenu, &DirMenu, DIR_POPUP);
1887 else
1888 dcd->hwndLastMenu = CheckMenu(hwndMainMenu, &TreeMenu, TREE_POPUP);
1889 }
[551]1890 }
1891 else {
[875]1892 dcd->hwndLastMenu = CheckMenu(hwndMainMenu, &TreeCnrMenu, TREECNR_POPUP);
[551]1893 if (dcd->hwndLastMenu && !dcd->cnremphasized) {
1894 WinSendMsg(hwnd, CM_SETRECORDEMPHASIS, MPVOID,
1895 MPFROM2SHORT(TRUE, CRA_SOURCE));
1896 dcd->cnremphasized = TRUE;
1897 }
1898 }
1899 if (dcd->hwndLastMenu) {
1900 if (dcd->hwndLastMenu == DirMenu)
1901 WinEnableMenuItem(DirMenu, IDM_TREE, FALSE);
1902 if (dcd->hwndLastMenu == TreeCnrMenu) {
1903 if (dcd->flWindowAttr & CV_MINI)
1904 WinCheckMenuItem(dcd->hwndLastMenu, IDM_MINIICONS, TRUE);
1905 }
1906 if (!PopupMenu(hwnd, hwnd, dcd->hwndLastMenu)) {
1907 if (dcd->cnremphasized) {
1908 WinSendMsg(hwnd, CM_SETRECORDEMPHASIS, MPVOID,
1909 MPFROM2SHORT(FALSE, CRA_SOURCE));
1910 dcd->cnremphasized = FALSE;
[176]1911 }
[551]1912 if (dcd->hwndLastMenu != TreeCnrMenu)
1913 MarkAll(hwnd, TRUE, FALSE, TRUE);
[176]1914 }
[551]1915 }
1916 fFollowTree = wasFollowing;
1917 }
1918 break;
[2]1919
[551]1920 case CN_ENTER:
1921 if (mp2) {
1922 PCNRITEM pci = (PCNRITEM) ((PNOTIFYRECORDENTER) mp2)->pRecord;
[2]1923
[551]1924 PostMsg(hwnd, UM_ENTER, MPFROMP(pci), MPVOID);
1925 }
1926 break;
[2]1927
[551]1928 case CN_COLLAPSETREE:
1929 case CN_EXPANDTREE:
[1871]1930 WinPostQueueMsg(hmqExpandTree, CN_EXPANDTREE ? UM_EXPANDTREE :UM_COLLAPSETREE,
1931 mp2, MPFROMP(dcd));
[551]1932 break;
1933 } // switch WM_CONTROL
1934 }
1935 return 0;
[2]1936
[551]1937 case UM_ACTION:
1938 if (mp1) {
[2]1939
[551]1940 LISTINFO *li = mp1;
1941 ULONG action = (ULONG) mp2;
[2]1942
[551]1943 if (!li->list || !li->list[0] ||
1944 !PostMsg(dcd->hwndObject, action, MPFROMP(li), MPVOID))
1945 FreeListInfo(li);
1946 }
1947 return 0;
[2]1948
[551]1949 case UM_SHOWME:
1950 if (mp1 && dcd) {
[1009]1951 CHAR *dir = xstrdup((CHAR *)mp1, pszSrcFile, __LINE__);
[551]1952
1953 if (dir) {
1954 if (!PostMsg(dcd->hwndObject, UM_SHOWME, MPFROMP(dir), MPVOID))
[1039]1955 free(dir);
[1856]1956 else
[1860]1957 SetFleshFocusPath(dir);
[2]1958 }
[551]1959 }
1960 return 0;
[2]1961
[551]1962 case UM_TOPDIR:
1963 if (mp1) {
[1874]1964 PostMsg(dcd->hwndObject, UM_TOPDIR, mp1, MPVOID);
[551]1965 }
1966 return 0;
[2]1967
[551]1968 case UM_ENTER:
1969 {
[847]1970 FILEFINDBUF3 ffb;
[551]1971 HDIR hDir = HDIR_CREATE;
[761]1972 ULONG nm = 1;
[551]1973 BOOL IsOk = FALSE;
1974 ULONG ulDriveNum, ulDriveMap;
1975 PCNRITEM pciP, pciL, pci;
1976 ULONG fl = SWP_ACTIVATE;
[1444]1977 INT x;
[2]1978
[551]1979 if (fFollowTree)
1980 fl = 0;
1981 SetShiftState();
1982 pci = (PCNRITEM) mp1;
1983 if (pci &&
1984 (INT) pci != -1 &&
1985 !(pci->rc.flRecordAttr & CRA_INUSE) &&
[1455]1986 !(pci->flags & RECFLAGS_ENV) && IsFullName(pci->pszFileName)) {
1987 x = (INT) (toupper(*pci->pszFileName) - 'A');
[1444]1988 if (driveflags[x] & DRIVE_INVALID) {
[1411]1989 if (!fAlertBeepOff)
[1395]1990 DosBeep(50, 100);
[551]1991 if (hwndStatus)
[1498]1992 WinSetWindowText(hwndStatus, (CHAR *) GetPString(IDS_RESCANSUGTEXT));
[551]1993 return 0;
1994 }
1995 DosError(FERR_DISABLEHARDERR);
1996 if (!DosQCurDisk(&ulDriveNum, &ulDriveMap)) {
[1444]1997 if (!(ulDriveMap & 1 << x)) {
[176]1998 pciL = pciP = pci;
[551]1999 for (;;) {
[176]2000 pciP = WinSendMsg(hwnd,
2001 CM_QUERYRECORD,
2002 MPFROMP(pciL),
[551]2003 MPFROM2SHORT(CMA_PARENT, CMA_ITEMORDER));
2004 if (pciP && (INT) pciP != -1)
[176]2005 pciL = pciP;
2006 else {
2007 pciP = pciL;
2008 break;
2009 }
[751]2010 } // for
[1455]2011 RemoveCnrItems(hwnd, pciP, 1, CMA_FREE | CMA_INVALIDATE);
[551]2012 return 0;
2013 }
2014 }
[1444]2015 if (driveflags[x] & (DRIVE_REMOVABLE | DRIVE_NOPRESCAN)) {
[551]2016
2017 struct
2018 {
2019 ULONG serial;
2020 CHAR volumelength;
2021 CHAR volumelabel[CCHMAXPATH];
2022 }
[1455]2023 volser;
2024 CHAR FileSystem[CCHMAXPATH];
2025 CHAR szBuf[CCHMAXPATH];
[551]2026
2027 pciL = pciP = pci;
2028 for (;;) {
2029 pciP = WinSendMsg(hwnd,
2030 CM_QUERYRECORD,
2031 MPFROMP(pciL),
2032 MPFROM2SHORT(CMA_PARENT, CMA_ITEMORDER));
2033 if (pciP && (INT) pciP != -1)
2034 pciL = pciP;
2035 else {
2036 pciP = pciL;
2037 break;
[176]2038 }
[551]2039 }
[1444]2040 if ((driveflags[x] & DRIVE_NOPRESCAN) || (toupper(*pci->pszFileName) > 'B' &&
2041 !(driveflags[x] & DRIVE_CDROM))) {
[1455]2042 DriveFlagsOne(x, FileSystem, &volser);
2043 SelectDriveIcon(pciP);
[1444]2044 if (hwndMain)
2045 PostMsg(hwndMain, UM_BUILDDRIVEBAR, MPVOID, MPVOID);
[551]2046 }
2047 memset(&volser, 0, sizeof(volser));
2048 DosError(FERR_DISABLEHARDERR);
[1856]2049 rc = DosQueryFSInfo(toupper(*pci->pszFileName) - '@',
2050 FSIL_VOLSER, &volser,
2051 (ULONG) sizeof(volser));
2052 if (!rc) {
[1444]2053 if (!volser.serial || driveserial[x] != volser.serial) {
[1856]2054 AddFleshWorkRequest(hwnd, pciP, eFlesh); // forceFlesh
[1444]2055 driveserial[x] = volser.serial;
[551]2056 }
[1876]2057 if (!pciP->fleshed) {
[1856]2058 AddFleshWorkRequest(hwnd, pciP, eFlesh); // forceFlesh
2059 }
[1455]2060 if ((fShowFSTypeInTree || fShowDriveLabelInTree) &&
2061 strlen(pciP->pszFileName) < 4) {
2062 strcpy(szBuf, pciP->pszFileName);
2063 strcat(szBuf, " [");
2064 strcat(szBuf, fShowFSTypeInTree ? FileSystem : volser.volumelabel);
2065 strcat(szBuf, "]");
2066 pciP->pszDisplayName = xstrdup(szBuf, pszSrcFile, __LINE__);
2067 pciP->rc.pszIcon = pciP->pszDisplayName;
2068 }
2069 WinSendMsg(hwnd,
2070 CM_INVALIDATERECORD,
2071 MPFROMP(&pciP),
2072 MPFROM2SHORT(1, CMA_ERASE | CMA_REPOSITION));
2073 }
[551]2074 else {
[1444]2075 driveserial[x] = -1;
[1875]2076 PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
2077 if (dcd)
2078 PostMsg(dcd->hwndObject, UM_SETUP2, MPFROMP(pci), MPFROMLONG(rc));
[551]2079 return 0;
2080 }
2081 }
[1856]2082 rc = 0;
[730]2083 IsOk = (IsRoot(pci->pszFileName) &&
2084 IsValidDrive(toupper(*pci->pszFileName)));
[551]2085 if (!IsOk) {
2086 DosError(FERR_DISABLEHARDERR);
[1856]2087 rc = DosFindFirst(pci->pszFileName, &hDir,
2088 FILE_NORMAL | FILE_DIRECTORY |
2089 FILE_ARCHIVED | FILE_READONLY |
2090 FILE_HIDDEN | FILE_SYSTEM,
2091 &ffb, sizeof(ffb), &nm, FIL_STANDARD);
[551]2092 priority_bumped();
2093 }
[1856]2094 if (!rc) {
[551]2095 if (!IsOk)
2096 DosFindClose(hDir);
2097 if (IsOk || (ffb.attrFile & FILE_DIRECTORY)) {
2098 if ((shiftstate & (KC_CTRL | KC_ALT)) == (KC_CTRL | KC_ALT)) {
[176]2099 PostMsg(hwnd,
[1455]2100 WM_COMMAND, MPFROM2SHORT(IDM_SHOWALLFILES, 0), MPVOID);
[176]2101 return 0;
2102 }
[551]2103 if ((shiftstate & (KC_CTRL | KC_SHIFT)) == (KC_CTRL | KC_SHIFT)) {
[1455]2104 OpenObject(pci->pszFileName, Settings, dcd->hwndFrame);
[551]2105 return 0;
2106 }
2107 if (!(shiftstate & (KC_CTRL | KC_SHIFT))) {
2108 if (!ParentIsDesktop(hwnd, dcd->hwndParent)) {
[1455]2109 if (FindDirCnrByName(pci->pszFileName, TRUE)) {
2110 return 0;
2111 }
[176]2112 }
2113 }
[551]2114 if ((shiftstate & KC_CTRL) ||
2115 (!(shiftstate & KC_SHIFT) &&
2116 ParentIsDesktop(hwnd, dcd->hwndParent) && fVTreeOpensWPS)) {
[2]2117
[551]2118 ULONG size = sizeof(ULONG), flWindowAttr = CV_ICON;
2119 CHAR s[33];
[2]2120
[1402]2121 strcpy(s, PCSZ_ICON);
[551]2122 PrfQueryProfileData(fmprof,
2123 appname,
2124 "DirflWindowAttr",
2125 (PVOID) & flWindowAttr, &size);
2126 if (flWindowAttr & CV_DETAIL) {
[730]2127 if (IsRoot(pci->pszFileName))
[1402]2128 strcpy(s, PCSZ_TREE);
[551]2129 else
[1402]2130 strcpy(s, Details);
[176]2131 }
[730]2132 OpenObject(pci->pszFileName, s, dcd->hwndFrame);
[551]2133 return 0;
[176]2134 }
[551]2135 if (!ParentIsDesktop(hwnd, dcd->hwndParent) &&
2136 !fDCOpens && !LastDir && !(shiftstate & KC_SHIFT))
2137 LastDir = FindDirCnr(dcd->hwndParent);
2138 if (LastDir && !fDCOpens && !(shiftstate & KC_SHIFT)) {
2139 WinSendMsg(LastDir,
[730]2140 UM_SETDIR, MPFROMP(pci->pszFileName), MPVOID);
[551]2141 WinSetWindowPos(WinQueryWindow(WinQueryWindow(LastDir,
2142 QW_PARENT),
2143 QW_PARENT),
2144 HWND_TOP, 0, 0, 0, 0, SWP_ZORDER | fl);
2145 }
2146 else
2147 OpenDirCnr(hwnd,
2148 dcd->hwndParent,
[730]2149 dcd->hwndFrame, FALSE, pci->pszFileName);
[176]2150 }
2151 else {
[1444]2152 if (!(driveflags[x] & DRIVE_INCLUDEFILES))
[751]2153 RemoveCnrItems(hwnd, pci, 1, CMA_FREE | CMA_INVALIDATE);
[551]2154 else {
2155
2156 SWP swp;
2157
2158 WinQueryWindowPos(dcd->hwndFrame, &swp);
2159 DefaultViewKeys(hwnd,
2160 dcd->hwndFrame,
[730]2161 dcd->hwndParent, &swp, pci->pszFileName);
[176]2162 }
2163 }
2164 }
[551]2165 else {
[1875]2166 if (!IsRoot(pci->pszFileName)) {
2167 NotifyError(pci->pszFileName, rc);
[751]2168 RemoveCnrItems(hwnd, pci, 1, CMA_FREE | CMA_INVALIDATE);
[551]2169 }
2170 }
[2]2171 }
[551]2172 else if (!pci)
2173 PostMsg(hwnd, WM_COMMAND, MPFROM2SHORT(IDM_MKDIR, 0), MPVOID);
2174 if (fFollowTree)
[1455]2175 WinSetFocus(HWND_DESKTOP, hwnd);
[551]2176 }
2177 return 0;
[2]2178
[551]2179 case WM_MENUEND:
2180 if (dcd) {
[2]2181
[551]2182 HWND hwndMenu = (HWND) mp2;
[2]2183
[551]2184 if (hwndMenu == TreeCnrMenu || hwndMenu == TreeMenu ||
2185 hwndMenu == DirMenu) {
2186 MarkAll(hwnd, TRUE, FALSE, TRUE);
2187 if (dcd->cnremphasized) {
2188 WinSendMsg(hwnd,
2189 CM_SETRECORDEMPHASIS,
2190 MPVOID, MPFROM2SHORT(FALSE, CRA_SOURCE));
2191 dcd->cnremphasized = FALSE;
[176]2192 }
[2]2193 }
[551]2194 }
2195 break;
[2]2196
[551]2197 case UM_OPENWINDOWFORME:
2198 if (dcd) {
[1009]2199 if (mp1 && !IsFile((CHAR *)mp1))
[551]2200 OpenDirCnr(hwnd, dcd->hwndParent, dcd->hwndFrame, FALSE, (char *)mp1);
2201 }
2202 return 0;
[2]2203
[551]2204 case MM_PORTHOLEINIT:
2205 if (dcd) {
2206 switch (SHORT1FROMMP(mp1)) {
2207 case 0:
2208 case 1:
2209 {
2210 ULONG wmsg;
[2]2211
[551]2212 wmsg = ((SHORT1FROMMP(mp1) == 0) ? UM_FILESMENU : UM_VIEWSMENU);
2213 PortholeInit((HWND) WinSendMsg(dcd->hwndClient,
2214 wmsg, MPVOID, MPVOID), mp1, mp2);
[176]2215 }
[551]2216 break;
[2]2217 }
[551]2218 }
2219 break;
[2]2220
[551]2221 case UM_INITMENU:
2222 case WM_INITMENU:
2223 if (dcd) {
[1360]2224
[551]2225 switch (SHORT1FROMMP(mp1)) {
2226 case IDM_FILESMENU:
2227 {
2228 PCNRITEM pci;
[2]2229
[551]2230 pci = (PCNRITEM) CurrentRecord(hwnd);
2231 if (pci && (INT) pci != -1) {
2232 BOOL rdy;
2233 BOOL writeable;
2234 BOOL removable;
[1360]2235 BOOL local;
[551]2236 BOOL underenv;
2237 CHAR chDrvU;
2238 CHAR szDrv[CCHMAXPATH];
[305]2239
[1871]2240 strcpy(szDrv, pci->pszFileName);
[730]2241 chDrvU = *pci->pszFileName;
[1871]2242 chDrvU = toupper(chDrvU);
[551]2243 MakeValidDir(szDrv);
2244 rdy = *szDrv == chDrvU; // Drive not ready if MakeValidDir changes drive letter
2245 removable = rdy
2246 && (driveflags[chDrvU - 'A'] & DRIVE_REMOVABLE) != 0;
2247 writeable = rdy
2248 && !(driveflags[chDrvU - 'A'] & DRIVE_NOTWRITEABLE);
[1394]2249 local = rdy && (!(driveflags[chDrvU - 'A'] & (DRIVE_REMOTE | DRIVE_VIRTUAL)));
[551]2250 underenv = (pci->flags & RECFLAGS_UNDERENV) != 0;
[877]2251 CopyPresParams((HWND) mp2, hwndMainMenu);
[907]2252 WinEnableMenuItem((HWND) mp2, IDM_INFO, rdy);
[305]2253
[551]2254 WinEnableMenuItem((HWND) mp2, IDM_ATTRS, writeable);
2255 WinEnableMenuItem((HWND) mp2, IDM_EAS, writeable);
2256 WinEnableMenuItem((HWND) mp2, IDM_SUBJECT, writeable);
2257 WinEnableMenuItem((HWND) mp2, IDM_DRVFLAGS, 1); // fixme to allow if not ready
[305]2258
[551]2259 WinEnableMenuItem((HWND) mp2, IDM_ARCHIVE, rdy);
[305]2260
[551]2261 WinEnableMenuItem((HWND) mp2, IDM_UPDATE, !underenv);
2262 WinEnableMenuItem((HWND) mp2, IDM_EXPANDSUBMENU, !underenv);
2263 WinEnableMenuItem((HWND) mp2, IDM_EXPAND, !underenv);
2264 WinEnableMenuItem((HWND) mp2, IDM_COLLAPSE, !underenv);
[305]2265
[551]2266 WinEnableMenuItem((HWND) mp2, IDM_SIZES, rdy);
2267 WinEnableMenuItem((HWND) mp2, IDM_MKDIR, writeable);
2268 WinEnableMenuItem((HWND) mp2, IDM_SHOWALLFILES, rdy);
2269 WinEnableMenuItem((HWND) mp2, IDM_UNDELETE, writeable);
[305]2270
[1360]2271 WinEnableMenuItem((HWND) mp2, IDM_CHKDSK, writeable && local);
2272 WinEnableMenuItem((HWND) mp2, IDM_FORMAT, writeable && local);
2273 WinEnableMenuItem((HWND) mp2, IDM_OPTIMIZE, writeable && local);
[1394]2274 WinEnableMenuItem((HWND) mp2, IDM_PARTITIONSMENU, local);
2275 WinEnableMenuItem((HWND) mp2, IDM_PARTITION, fMiniLVM);
2276 WinEnableMenuItem((HWND) mp2, IDM_PARTITIONDF, fDFSee);
[1856]2277 WinEnableMenuItem((HWND) mp2, IDM_PARTITIONLVMG, fLVMGui);
2278 WinEnableMenuItem((HWND) mp2, IDM_PARTITIONLVM, fLVM);
[1394]2279 WinEnableMenuItem((HWND) mp2, IDM_PARTITIONFD, fFDisk);
[305]2280
[1360]2281 WinEnableMenuItem((HWND) mp2, IDM_DETACH, !local);
[305]2282
[551]2283 WinEnableMenuItem((HWND) mp2, IDM_EJECT, removable);
[305]2284
[551]2285 WinEnableMenuItem((HWND) mp2, IDM_LOCK, removable);
2286 WinEnableMenuItem((HWND) mp2, IDM_UNLOCK, removable);
[305]2287
[551]2288 WinEnableMenuItem((HWND) mp2, IDM_DELETE, !underenv && writeable);
2289 WinEnableMenuItem((HWND) mp2, IDM_PERMDELETE, !underenv
2290 && writeable);
2291 WinEnableMenuItem((HWND) mp2, IDM_DELETESUBMENU, !underenv
2292 && writeable);
2293 WinEnableMenuItem((HWND) mp2, IDM_MOVEMENU, !underenv
2294 && writeable);
[907]2295 WinEnableMenuItem((HWND) mp2, IDM_RENAME, !underenv && writeable);
[2]2296
[551]2297 }
2298 }
2299 break;
[2]2300
[551]2301 case IDM_VIEWSMENU:
2302 WinCheckMenuItem((HWND) mp2,
2303 IDM_MINIICONS, ((dcd->flWindowAttr & CV_MINI) != 0));
[907]2304 CopyPresParams((HWND) mp2, hwndMainMenu);
[877]2305 WinEnableMenuItem((HWND) mp2, IDM_RESELECT, FALSE);
[1394]2306 WinEnableMenuItem((HWND) mp2, IDM_PARTITION, fMiniLVM);
2307 WinEnableMenuItem((HWND) mp2, IDM_PARTITIONDF, fDFSee);
[1856]2308 WinEnableMenuItem((HWND) mp2, IDM_PARTITIONLVMG, fLVMGui);
2309 WinEnableMenuItem((HWND) mp2, IDM_PARTITIONLVM, fLVM);
[1394]2310 WinEnableMenuItem((HWND) mp2, IDM_PARTITIONFD, fFDisk);
[907]2311 break;
[2]2312
[551]2313 case IDM_COMMANDSMENU:
[907]2314 SetupCommandMenu((HWND) mp2, hwnd);
2315 CopyPresParams((HWND) mp2, hwndMainMenu);
[551]2316 break;
[2]2317
[551]2318 case IDM_SORTSUBMENU:
2319 SetSortChecks((HWND) mp2, TreesortFlags);
[907]2320 CopyPresParams((HWND) mp2, hwndMainMenu);
2321 break;
[2]2322
[551]2323 case IDM_WINDOWSMENU:
2324 SetupWinList((HWND) mp2,
[907]2325 (hwndMain) ? hwndMain : (HWND) 0, dcd->hwndFrame);
2326 CopyPresParams((HWND) mp2, hwndMainMenu);
[551]2327 break;
2328 }
2329 dcd->hwndLastMenu = (HWND) mp2;
2330 }
2331 if (msg == WM_INITMENU)
2332 break;
2333 return 0;
2334
2335 case UM_COMMAND:
2336 if (!mp1)
[1398]2337 Runtime_Error(pszSrcFile, __LINE__, NULL);
[551]2338 else {
2339 if (!dcd) {
[1398]2340 Runtime_Error(pszSrcFile, __LINE__, NULL);
[551]2341 FreeListInfo((LISTINFO *) mp1);
2342 }
[352]2343 else {
[551]2344 if (!PostMsg(dcd->hwndObject, UM_COMMAND, mp1, mp2)) {
[1400]2345 Runtime_Error(pszSrcFile, __LINE__, PCSZ_POSTMSG);
[551]2346 FreeListInfo((LISTINFO *) mp1);
[352]2347 }
[551]2348 else
2349 return (MRESULT) TRUE;
[2]2350 }
[551]2351 }
2352 return 0;
[2]2353
[551]2354 case UM_LOADFILE:
2355 if (dcd && mp2) {
[2]2356
[1037]2357 HWND hwnd;
[2]2358
[1037]2359 if ((INT)mp1 == 5 || (INT)mp1 == 13 || (INT)mp1 == 21)
[1077]2360 hwnd = StartViewer(HWND_DESKTOP, (INT)mp1,
2361 (CHAR *)mp2, dcd->hwndFrame);
[1037]2362 else
[1077]2363 hwnd = StartMLEEditor(dcd->hwndParent,
2364 (INT)mp1, (CHAR *)mp2, dcd->hwndFrame);
[1039]2365 free((CHAR *)mp2);
[1037]2366 return MRFROMLONG(hwnd);
[551]2367 }
2368 return 0;
[2]2369
[551]2370 case UM_FIXCNRMLE:
2371 case UM_FIXEDITNAME:
2372 return CommonCnrProc(hwnd, msg, mp1, mp2);
[2]2373
[551]2374 case UM_NOTIFY:
2375 if (mp2)
[1009]2376 Notify((CHAR *)mp2);
[551]2377 return 0;
[2]2378
[551]2379 case UM_FILTER:
2380 if (dcd) {
[2]2381
[551]2382 BOOL tempsusp = dcd->suspendview;
[2]2383
[1572]2384 if (mp1)
[1009]2385 SetMask((CHAR *)mp1, &dcd->mask);
[1572]2386
[551]2387 dcd->suspendview = TRUE;
2388 dcd->mask.attrFile |= FILE_DIRECTORY;
2389 WinSendMsg(hwnd, CM_FILTER, MPFROMP(Filter), MPFROMP(&dcd->mask));
[1533]2390 dcd->suspendview = (USHORT) tempsusp;
[551]2391 PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
2392 }
2393 return 0;
[2]2394
[551]2395 case UM_DRIVECMD:
[1444]2396 if (mp1) {
[1009]2397 ShowTreeRec(hwnd, (CHAR *)mp1, FALSE, TRUE);
[1444]2398 PostMsg(hwndTree, WM_COMMAND, MPFROM2SHORT(IDM_UPDATE, 0), MPVOID);
2399 }
[551]2400 return 0;
[2]2401
[551]2402 case WM_APPTERMINATENOTIFY:
2403 {
2404 APPNOTIFY *info;
2405 PCNRITEM pci;
2406 CHAR s[] = " :\\";
[2]2407
[551]2408 if (!mp2) {
2409 if (hwndMain)
2410 PostMsg(hwndMain, UM_BUILDDRIVEBAR, MPVOID, MPVOID);
2411 }
2412 info = apphead;
2413 while (info) {
2414 if (info->happ == (HAPP) mp1) {
2415 *s = info->device;
2416 pci = FindCnrRecord(hwnd, s, NULL, FALSE, FALSE, TRUE);
[1455]2417 if (pci && (INT) pci != -1) {
2418 INT x = info->device - 'A';
2419 CHAR FileSystem[CCHMAXPATH];
[1444]2420
2421 driveserial[x] = -1;
2422 DriveFlagsOne(x, FileSystem, NULL);
2423 if (driveflags[x] &
[551]2424 (DRIVE_INVALID | DRIVE_IGNORE))
[751]2425 RemoveCnrItems(hwnd, pci, 1, CMA_FREE);
[551]2426 else
[1856]2427 AddFleshWorkRequest(hwnd, pci, eFlesh);
[176]2428 }
[551]2429 if (info->prev)
2430 info->prev->next = info->next;
2431 if (info->next)
2432 info->next->prev = info->prev;
2433 if (apphead == info)
2434 apphead = info->next;
2435 if (apptail == info)
2436 apptail = info->prev;
[1039]2437 free(info);
[551]2438 break;
[176]2439 }
[551]2440 info = info->next;
[2]2441 }
[551]2442 }
2443 break;
[2]2444
[551]2445 case WM_COMMAND:
2446 DosError(FERR_DISABLEHARDERR);
2447 if (dcd) {
2448 if (SwitchCommand(dcd->hwndLastMenu, SHORT1FROMMP(mp1)))
2449 return 0;
2450 switch (SHORT1FROMMP(mp1)) {
2451 case IDM_SETTARGET:
[1675]2452 SetTargetDir(hwnd, FALSE, NULL);
[551]2453 break;
[2]2454
[551]2455 case IDM_DETACH:
2456 {
2457 CHAR d[3] = " :";
2458 PCNRITEM pci;
2459 PROGDETAILS pgd;
2460 CHAR params[368], *p;
2461 HAPP happ;
[2]2462
[551]2463 pci = (PCNRITEM) CurrentRecord(hwnd);
[730]2464 if (pci && (INT) pci != -1 && isalpha(*pci->pszFileName)) {
2465 *d = toupper(*pci->pszFileName);
[551]2466 p = GetCmdSpec(FALSE);
2467 memset(&pgd, 0, sizeof(pgd));
2468 pgd.Length = sizeof(pgd);
2469 pgd.progt.progc = PROG_WINDOWABLEVIO;
2470 pgd.progt.fbVisible = SHE_VISIBLE;
[1394]2471 pgd.pszTitle = (PSZ)GetPString(IDS_DETACHREQUESTTEXT);
[551]2472 pgd.pszExecutable = p;
2473 pgd.pszParameters = params;
2474 pgd.pszStartupDir = NULL;
2475 pgd.pszIcon = NULL;
2476 pgd.pszEnvironment = NULL;
2477 pgd.swpInitial.hwndInsertBehind = HWND_TOP;
2478 pgd.swpInitial.hwnd = hwnd;
2479 pgd.swpInitial.fl = SWP_SHOW | SWP_ACTIVATE;
2480 sprintf(params, "/C NET USE %s /D", d);
2481 happ = WinStartApp(hwnd, &pgd, pgd.pszParameters,
2482 NULL, SAF_MAXIMIZED);
2483 if (!happ) {
2484 saymsg(MB_CANCEL | MB_ICONEXCLAMATION, hwnd,
2485 GetPString(IDS_ERRORTEXT),
2486 GetPString(IDS_CANTSTARTTEXT), p, params);
2487 }
2488 else {
2489 APPNOTIFY *info;
[2]2490
[551]2491 info = xmallocz(sizeof(APPNOTIFY), pszSrcFile, __LINE__);
2492 if (info) {
2493 info->happ = happ;
2494 info->device = *d;
2495 if (!apphead)
2496 apphead = info;
[352]2497 else {
[551]2498 apptail->next = info;
2499 info->prev = apptail;
[176]2500 }
[551]2501 apptail = info;
[1856]2502 }
2503 PostMsg(hwndTree, WM_COMMAND, MPFROM2SHORT(IDM_RESCAN, 0), MPVOID);
[176]2504 }
[551]2505 }
2506 }
2507 break;
[2]2508
[551]2509 case IDM_REMAP:
2510 WinDlgBox(HWND_DESKTOP, hwnd, RemapDlgProc,
2511 FM3ModHandle, MAP_FRAME, NULL);
2512 break;
[2]2513
[551]2514 case IDM_CONTEXTMENU:
2515 {
2516 PCNRITEM pci;
[2]2517
[551]2518 pci = (PCNRITEM) CurrentRecord(hwnd);
2519 PostMsg(hwnd, WM_CONTROL, MPFROM2SHORT(DIR_CNR, CN_CONTEXTMENU),
2520 MPFROMP(pci));
2521 }
2522 break;
[2]2523
[551]2524 case IDM_FINDINTREE:
2525 {
[1102]2526 PSZ pszTempDir;
[551]2527 PCNRITEM pci;
[2]2528
[551]2529 pci = (PCNRITEM) CurrentRecord(hwnd);
2530 if (pci && (INT) pci != -1) {
[1335]2531 pszTempDir = xstrdup(pci->pszFileName, pszSrcFile, __LINE__);
2532 if (pszTempDir)
[1102]2533 MakeValidDir(pszTempDir);
[551]2534 }
2535 else
[1335]2536 pszTempDir = xstrdup(pFM2SaveDirectory, pszSrcFile, __LINE__);
2537 if (pszTempDir) {
2538 if (WinDlgBox(HWND_DESKTOP, dcd->hwndParent,
2539 WalkAllDlgProc,
2540 FM3ModHandle, WALK_FRAME, MPFROMP(pszTempDir))) {
2541 if (!WinSendMsg(hwnd, UM_SHOWME, MPFROMP(pszTempDir), MPFROMLONG(1)))
2542 free(pszTempDir);
2543 }
2544 else
2545 free(pszTempDir);
2546 }
[551]2547 }
2548 break;
[2]2549
[551]2550 case IDM_BEGINEDIT:
2551 OpenEdit(hwnd);
2552 break;
[2]2553
[551]2554 case IDM_ENDEDIT:
2555 WinSendMsg(hwnd, CM_CLOSEEDIT, MPVOID, MPVOID);
2556 break;
[2]2557
[551]2558 case IDM_FILTER:
2559 {
2560 BOOL empty = FALSE;
2561 PCNRITEM pci;
[2]2562
[551]2563 pci = (PCNRITEM) CurrentRecord(hwnd);
2564 if (!*dcd->mask.szMask)
2565 empty = TRUE;
2566 dcd->mask.fIsTree = TRUE;
2567 *dcd->mask.prompt = 0;
2568 if (pci && (INT) pci != -1)
2569 dcd->mask.fFilesIncluded =
[730]2570 ((driveflags[toupper(*pci->pszFileName) - 'A'] &
[551]2571 DRIVE_INCLUDEFILES) != 0);
2572 else
2573 dcd->mask.fFilesIncluded = FALSE;
2574 if (WinDlgBox(HWND_DESKTOP, hwnd, PickMaskDlgProc,
2575 FM3ModHandle, MSK_FRAME, MPFROMP(&dcd->mask)))
2576 WinSendMsg(hwnd, UM_FILTER, MPVOID, MPVOID);
2577 else if (empty)
2578 *dcd->mask.szMask = 0;
2579 PrfWriteProfileData(fmprof, appname, "TreeFilter", &dcd->mask,
2580 sizeof(MASK));
2581 }
2582 break;
[2]2583
[551]2584 case IDM_SHOWSORT:
[875]2585 QuickPopup(hwnd, dcd, CheckMenu(hwndMainMenu, &TreeCnrMenu, TREECNR_POPUP),
[551]2586 IDM_SORTSUBMENU);
2587 break;
[2]2588
[551]2589 case IDM_SHOWSELECT:
[875]2590 QuickPopup(hwnd, dcd, CheckMenu(hwndMainMenu, &TreeCnrMenu, TREECNR_POPUP),
[551]2591 IDM_SELECTSUBMENU);
2592 break;
[2]2593
[953]2594 case IDM_TREECNRVIEWSETTINGS:
[908]2595 if (!ParentIsDesktop(dcd->hwndParent, dcd->hwndParent))
[953]2596 PostMsg(dcd->hwndParent, msg, MPFROMLONG(IDM_TREECNRVIEWSETTINGS), mp2);
[917]2597 else {
2598 WinDlgBox(HWND_DESKTOP,
2599 hwnd,
2600 CfgDlgProc,
2601 FM3ModHandle,
2602 CFG_FRAME,
[953]2603 MPFROMLONG(IDM_TREECNRVIEWSETTINGS));
[917]2604 }
[551]2605 break;
[2]2606
[551]2607 case IDM_WALKDIR:
2608 case IDM_OPENWALK:
2609 {
2610 CHAR newpath[CCHMAXPATH];
2611 PCNRITEM pci;
[2]2612
[551]2613 pci = (PCNRITEM) CurrentRecord(hwnd);
2614 if (pci && (INT) pci != -1) {
[730]2615 strcpy(newpath, pci->pszFileName);
[551]2616 MakeValidDir(newpath);
2617 }
2618 else
[1102]2619 strcpy(newpath, pFM2SaveDirectory);
[551]2620 if (!WinDlgBox(HWND_DESKTOP, dcd->hwndParent, WalkAllDlgProc,
2621 FM3ModHandle, WALK_FRAME,
2622 MPFROMP(newpath)) || !*newpath)
[176]2623 break;
[551]2624 WinSendMsg(hwnd, UM_OPENWINDOWFORME, MPFROMP(newpath), MPVOID);
2625 }
2626 break;
[2]2627
[551]2628 case IDM_HELP:
2629 if (hwndHelp) {
2630 if (!ParentIsDesktop(dcd->hwndFrame, dcd->hwndParent))
2631 PostMsg(dcd->hwndParent, UM_COMMAND, mp1, mp2);
2632 else
2633 WinSendMsg(hwndHelp, HM_HELP_CONTENTS, MPVOID, MPVOID);
2634 }
2635 break;
[2]2636
[551]2637 case IDM_PARTITION:
[907]2638 runemf2(SEPARATE | WINDOWED, HWND_DESKTOP, pszSrcFile, __LINE__,
2639 NULL, NULL,
[1400]2640 "%s", PCSZ_MINILVMEXE);
[551]2641 break;
[2]2642
[551]2643 case IDM_PARTITIONDF:
[907]2644 runemf2(SEPARATE | WINDOWED, HWND_DESKTOP, pszSrcFile, __LINE__,
2645 NULL, NULL,
[1400]2646 "%s", PCSZ_DFSOS2EXE);
[551]2647 break;
[472]2648
[551]2649 case IDM_PARTITIONLVMG:
[907]2650 runemf2(SEPARATE | WINDOWED, HWND_DESKTOP, pszSrcFile, __LINE__,
2651 NULL, NULL,
[1400]2652 "%s", PCSZ_LVMGUICMD);
[1856]2653 break;
[1480]2654
2655 case IDM_PARTITIONLVM:
2656 runemf2(SEPARATE | WINDOWED, HWND_DESKTOP, pszSrcFile, __LINE__,
2657 NULL, NULL,
2658 "%s", PCSZ_LVMEXE);
[551]2659 break;
[472]2660
[551]2661 case IDM_PARTITIONFD:
[907]2662 runemf2(SEPARATE | WINDOWED, HWND_DESKTOP, pszSrcFile, __LINE__,
2663 NULL, NULL,
[1400]2664 "%s", PCSZ_FDISKPMEXE);
[551]2665 break;
[472]2666
[1359]2667 case IDM_REFRESHREMOVABLES:
[1856]2668 {
2669 PFN Rediscover_PRMs;
2670 HMODULE hmod = 0;
2671 CHAR objerr[CCHMAXPATH];
[1359]2672
[1856]2673 rc = DosLoadModule(objerr, sizeof(objerr), "LVM", &hmod);
2674 if (!rc) {
2675 rc = DosQueryProcAddr(hmod, 70, NULL, &Rediscover_PRMs);
2676 if (!rc)
[1674]2677 Rediscover_PRMs(&rc);
[1856]2678 DosFreeModule(hmod);
2679 }
2680 if (!rc)
[1674]2681 PostMsg(hwndTree, WM_COMMAND, MPFROM2SHORT(IDM_RESCAN, 0), MPVOID);
[1856]2682 break;
2683 }
[1674]2684
[551]2685 case IDM_SORTNAME:
2686 case IDM_SORTFILENAME:
2687 case IDM_SORTSIZE:
2688 case IDM_SORTEASIZE:
2689 case IDM_SORTFIRST:
2690 case IDM_SORTLAST:
2691 case IDM_SORTLWDATE:
2692 case IDM_SORTLADATE:
2693 case IDM_SORTCRDATE:
2694 TreesortFlags &= (SORT_REVERSE | SORT_DIRSFIRST | SORT_DIRSLAST);
2695 case IDM_SORTDIRSFIRST:
2696 case IDM_SORTDIRSLAST:
2697 case IDM_SORTREVERSE:
2698 switch (SHORT1FROMMP(mp1)) {
2699 case IDM_SORTFILENAME:
2700 TreesortFlags |= SORT_FILENAME;
2701 break;
2702 case IDM_SORTSIZE:
2703 TreesortFlags |= SORT_SIZE;
2704 break;
2705 case IDM_SORTEASIZE:
2706 TreesortFlags |= SORT_EASIZE;
2707 break;
2708 case IDM_SORTFIRST:
2709 TreesortFlags |= SORT_FIRSTEXTENSION;
2710 break;
2711 case IDM_SORTLAST:
2712 TreesortFlags |= SORT_LASTEXTENSION;
2713 break;
2714 case IDM_SORTLWDATE:
2715 TreesortFlags |= SORT_LWDATE;
2716 break;
2717 case IDM_SORTLADATE:
2718 TreesortFlags |= SORT_LADATE;
2719 break;
2720 case IDM_SORTCRDATE:
2721 TreesortFlags |= SORT_CRDATE;
2722 break;
2723 case IDM_SORTDIRSFIRST:
2724 if (TreesortFlags & SORT_DIRSFIRST)
2725 TreesortFlags &= (~SORT_DIRSFIRST);
2726 else {
2727 TreesortFlags |= SORT_DIRSFIRST;
2728 TreesortFlags &= (~SORT_DIRSLAST);
2729 }
2730 break;
2731 case IDM_SORTDIRSLAST:
2732 if (TreesortFlags & SORT_DIRSLAST)
2733 TreesortFlags &= (~SORT_DIRSLAST);
2734 else {
2735 TreesortFlags |= SORT_DIRSLAST;
2736 TreesortFlags &= (~SORT_DIRSFIRST);
2737 }
2738 break;
2739 case IDM_SORTREVERSE:
2740 if (TreesortFlags & SORT_REVERSE)
2741 TreesortFlags &= (~SORT_REVERSE);
2742 else
2743 TreesortFlags |= SORT_REVERSE;
2744 break;
2745 }
2746 PrfWriteProfileData(fmprof, appname, "TreeSort", &TreesortFlags,
2747 sizeof(INT));
2748 WinSendMsg(hwnd, CM_SORTRECORD, MPFROMP(SortTreeCnr), MPVOID);
2749 break;
[2]2750
[551]2751 case IDM_COLLECT:
[1352]2752 case IDM_GREP:
[551]2753 if (!Collector) {
[2]2754
[551]2755 HWND hwndC;
2756 SWP swp;
[2]2757
[551]2758 if (!ParentIsDesktop(hwnd, dcd->hwndParent) &&
2759 !fAutoTile &&
2760 (!fExternalCollector && *(ULONG *) realappname == FM3UL))
2761 GetNextWindowPos(dcd->hwndParent, &swp, NULL, NULL);
2762 hwndC = StartCollector((fExternalCollector ||
2763 *(ULONG *) realappname != FM3UL) ?
2764 HWND_DESKTOP : dcd->hwndParent, 4);
2765 if (hwndC) {
2766 if (!ParentIsDesktop(hwnd,
2767 dcd->hwndParent) &&
2768 !fAutoTile &&
2769 (!fExternalCollector && *(ULONG *) realappname == FM3UL))
[176]2770 WinSetWindowPos(hwndC,
2771 HWND_TOP,
[551]2772 swp.x,
2773 swp.y,
2774 swp.cx,
2775 swp.cy,
2776 SWP_MOVE | SWP_SIZE | SWP_SHOW | SWP_ZORDER);
2777 else if (!ParentIsDesktop(hwnd,
2778 dcd->hwndParent) &&
2779 fAutoTile && *(ULONG *) realappname == FM3UL)
2780 TileChildren(dcd->hwndParent, TRUE);
2781 }
2782 WinSetWindowPos(hwndC, HWND_TOP, 0, 0, 0, 0, SWP_ACTIVATE);
[1880]2783 DosSleep(100);
[551]2784 }
2785 else
2786 StartCollector(dcd->hwndParent, 4);
[1394]2787 if (SHORT1FROMMP(mp1) == IDM_GREP) {
2788 PCNRITEM pci = NULL;
[1366]2789
[1394]2790 pci = WinSendMsg(hwnd,
2791 CM_QUERYRECORDEMPHASIS,
2792 MPFROMLONG(CMA_FIRST), MPFROMSHORT(CRA_CURSORED));
2793 if (pci && (INT) pci != -1)
2794 PostMsg(Collector, WM_COMMAND,
[1456]2795 MPFROM2SHORT(UM_GREP, 0), MPFROMP(pci->pszFileName));
[1394]2796 else
2797 PostMsg(Collector, WM_COMMAND,
2798 MPFROM2SHORT(IDM_GREP, 0), MPVOID);
2799 }
2800 else
[551]2801 PostMsg(hwnd, WM_COMMAND, MPFROM2SHORT(IDM_COLLECTOR, 0), MPVOID);
2802 break;
[2]2803
[551]2804 case IDM_COLLECTOR:
[1880]2805 DosSleep(32);
[551]2806 {
2807 CHAR **list;
[2]2808
[551]2809 list = BuildList(hwnd);
2810 if (list) {
2811 if (Collector) {
2812 if (!PostMsg(Collector, WM_COMMAND,
2813 MPFROM2SHORT(IDM_COLLECTOR, 0), MPFROMP(list)))
2814 FreeList(list);
[176]2815 }
[551]2816 else
2817 FreeList(list);
2818 }
2819 }
2820 break;
[2]2821
[551]2822 case IDM_COLLAPSEALL:
2823 WinSendMsg(hwnd, CM_COLLAPSETREE, MPVOID, MPVOID);
2824 break;
[2]2825
[551]2826 case IDM_COLLAPSE:
2827 case IDM_EXPAND:
2828 {
2829 PCNRITEM pci = NULL;
[2]2830
[551]2831 pci = (PCNRITEM) CurrentRecord(hwnd);
2832 if (pci && (INT) pci != -1) {
2833 if (pci->flags & RECFLAGS_UNDERENV)
2834 break;
2835 PostMsg(dcd->hwndObject, UM_EXPAND, mp1, MPFROMP(pci));
2836 }
2837 }
2838 break;
[2]2839
[551]2840 case IDM_UPDATE:
[1455]2841 {
[1856]2842 // 2015-08-07 SHL FIXME select
2843 PCNRITEM pci;
2844 if (!IsFleshWorkListEmpty())
2845 break; // 2015-08-07 SHL hold off until stable
2846 pci = (PCNRITEM)CurrentRecord(hwnd);
[1455]2847 if (pci && (INT)pci != -1) {
2848 struct
2849 {
2850 ULONG serial;
2851 CHAR volumelength;
2852 CHAR volumelabel[CCHMAXPATH];
2853 }
2854 volser;
2855 INT x = toupper(*pci->pszFileName) - 'A';
2856 CHAR FileSystem[CCHMAXPATH], szBuf[CCHMAXPATH];
[1444]2857
2858 UINT driveflag = driveflags[x];
[551]2859 if (pci->attrFile & FILE_DIRECTORY) {
2860 if (pci->flags & RECFLAGS_UNDERENV)
[1875]2861 break;
[1876]2862 if (pci->fleshed) {
2863 if (x > 1) {
2864 AddFleshWorkRequest(hwnd, pci, eUnFlesh);
2865 }
2866 else
2867 UnFlesh(hwnd, pci);
2868 }
[1856]2869
[557]2870 // Check if drive type might need update
2871 if ((driveflag & (DRIVE_INVALID | DRIVE_NOPRESCAN)) ||
[1876]2872 (~driveflag & DRIVE_NOPRESCAN && pci->rc.hptrIcon == hptrDunno)) {
[1444]2873 DriveFlagsOne(x, FileSystem, &volser);
2874 driveflag = driveflags[x];
[1876]2875 if (driveflag & DRIVE_INVALID)
2876 if (driveflag & DRIVE_REMOVABLE) {
2877 pci->rc.hptrIcon = hptrRemovable;
2878 if (fShowFSTypeInTree || fShowDriveLabelInTree) {
2879 strcpy(szBuf, pci->pszFileName);
2880 strcat(szBuf, " [");
2881 strcat(szBuf, "]");
2882 pci->pszDisplayName = xstrdup(szBuf, pszSrcFile, __LINE__);
2883 pci->rc.pszIcon = pci->pszDisplayName;
2884 }
2885 }
2886 else
2887 pci->rc.hptrIcon = hptrDunno;
[1856]2888 else if (strlen(pci->pszFileName) < 4) {
[618]2889 SelectDriveIcon(pci);
[1856]2890 if (fShowFSTypeInTree || fShowDriveLabelInTree) {
2891 strcpy(szBuf, pci->pszFileName);
2892 strcat(szBuf, " [");
2893 strcat(szBuf, fShowFSTypeInTree ? FileSystem : volser.volumelabel);
2894 strcat(szBuf, "]");
2895 pci->pszDisplayName = xstrdup(szBuf, pszSrcFile, __LINE__);
2896 pci->rc.pszIcon = pci->pszDisplayName;
2897 }
2898 }
[551]2899 WinSendMsg(hwnd,
2900 CM_INVALIDATERECORD,
2901 MPFROMP(&pci),
2902 MPFROM2SHORT(1, CMA_ERASE | CMA_REPOSITION));
2903 if (hwndMain)
2904 PostMsg(hwndMain, UM_BUILDDRIVEBAR, MPVOID, MPVOID);
[1876]2905 }
2906 if (~driveflag & DRIVE_INVALID) {
2907 if (x > 1) {
2908 // Note the UnFlesh above may not have completed when this is called
2909 // We need to keep it behind the UnFlesh in line
2910 AddFleshWorkRequest(hwnd, pci, eFlesh);
2911 }
2912 else
2913 Flesh(hwnd, pci);
2914 }
[176]2915 }
[551]2916 }
2917 }
2918 break;
[2]2919
[551]2920 case IDM_RESCAN:
2921 PostMsg(dcd->hwndObject, UM_RESCAN, MPVOID, MPVOID);
2922 break;
[2]2923
[551]2924 case IDM_RESORT:
2925 WinSendMsg(hwnd, CM_SORTRECORD, MPFROMP(SortTreeCnr), MPVOID);
2926 break;
[2]2927
[551]2928 case IDM_TEXT:
2929 case IDM_MINIICONS:
2930 {
2931 CNRINFO cnri;
2932
2933 memset(&cnri, 0, sizeof(CNRINFO));
2934 cnri.cb = sizeof(CNRINFO);
2935 WinSendMsg(hwnd,
2936 CM_QUERYCNRINFO,
2937 MPFROMP(&cnri), MPFROMLONG(sizeof(CNRINFO)));
2938 if (SHORT1FROMMP(mp1) == IDM_MINIICONS) {
2939 if (cnri.flWindowAttr & CV_MINI)
2940 cnri.flWindowAttr &= (~CV_MINI);
2941 else
2942 cnri.flWindowAttr |= CV_MINI;
2943 }
2944 else {
2945 if (cnri.flWindowAttr & CV_TEXT) {
2946 cnri.flWindowAttr &= (~CV_TEXT);
2947 cnri.flWindowAttr |= CV_ICON;
[176]2948 }
[551]2949 else {
2950 cnri.flWindowAttr &= (~CV_ICON);
2951 cnri.flWindowAttr |= CV_TEXT;
2952 }
2953 }
2954 dcd->flWindowAttr = cnri.flWindowAttr;
2955 PrfWriteProfileData(fmprof,
2956 appname,
2957 "TreeflWindowAttr",
2958 &cnri.flWindowAttr, sizeof(ULONG));
2959 WinSendMsg(hwnd,
2960 CM_SETCNRINFO,
2961 MPFROMP(&cnri),
2962 MPFROMLONG(CMA_FLWINDOWATTR | CMA_TREEICON |
2963 CMA_SLTREEBITMAPORICON));
2964 }
2965 break;
[2]2966
[551]2967 case IDM_SIZES:
2968 case IDM_DRVFLAGS:
2969 case IDM_SHOWALLFILES:
2970 case IDM_UNDELETE:
2971 case IDM_OPTIMIZE:
2972 case IDM_CHKDSK:
2973 case IDM_FORMAT:
2974 case IDM_MKDIR:
2975 case IDM_LOCK:
2976 case IDM_UNLOCK:
2977 case IDM_EJECT:
2978 case IDM_CLOSETRAY:
2979 {
2980 PCNRITEM pci;
[2]2981
[551]2982 pci = (PCNRITEM) CurrentRecord(hwnd);
2983 if (pci && (INT) pci != -1)
[730]2984 CommonDriveCmd(hwnd, pci->pszFileName, SHORT1FROMMP(mp1));
[551]2985 }
2986 break;
[2]2987
[551]2988 case IDM_SAVETOLIST:
2989 WinDlgBox(HWND_DESKTOP,
2990 hwnd,
2991 SaveListDlgProc, FM3ModHandle, SAV_FRAME, MPFROMP(&hwnd));
2992 break;
[2]2993
[551]2994 case IDM_DELETE:
2995 case IDM_PERMDELETE:
2996 case IDM_MOVE:
2997 case IDM_WPSMOVE:
2998 case IDM_WILDMOVE:
2999 case IDM_RENAME:
3000 {
3001 PCNRITEM pci;
[2]3002
[551]3003 pci = (PCNRITEM) CurrentRecord(hwnd);
3004 if (pci && (INT) pci != -1) {
3005 if (pci->flags & RECFLAGS_UNDERENV)
3006 break;
3007 }
3008 }
[1673]3009 // else intentional fallthru
[551]3010 case IDM_ATTRS:
3011 case IDM_INFO:
3012 case IDM_COPY:
3013 case IDM_WPSCOPY:
3014 case IDM_WILDCOPY:
3015 case IDM_DOITYOURSELF:
3016 case IDM_OPENWINDOW:
3017 case IDM_OPENSETTINGS:
3018 case IDM_OPENDEFAULT:
3019 case IDM_OPENICON:
3020 case IDM_OPENDETAILS:
3021 case IDM_OPENTREE:
3022 case IDM_SHADOW:
3023 case IDM_SHADOW2:
3024 case IDM_COMPARE:
3025 case IDM_VIEW:
3026 case IDM_VIEWTEXT:
3027 case IDM_VIEWBINARY:
3028 case IDM_EDIT:
3029 case IDM_EDITTEXT:
3030 case IDM_EDITBINARY:
3031 case IDM_EAS:
3032 case IDM_SUBJECT:
3033 case IDM_APPENDTOCLIP:
3034 case IDM_SAVETOCLIP:
3035 case IDM_ARCHIVE:
3036 case IDM_MCIPLAY:
3037 case IDM_UUDECODE:
3038 {
3039 LISTINFO *li;
3040 ULONG action = UM_ACTION;
[1077]3041# ifdef FORTIFY
3042 Fortify_EnterScope();
3043# endif
[551]3044 li = xmallocz(sizeof(LISTINFO), pszSrcFile, __LINE__);
3045 if (li) {
3046 li->type = SHORT1FROMMP(mp1);
3047 li->hwnd = hwnd;
3048 li->list = BuildList(hwnd);
3049 if (!li->list || !li->list[0]) {
[1039]3050 free(li);
[551]3051 break;
[176]3052 }
[551]3053 if (IsRoot(li->list[0])) {
3054 switch (SHORT1FROMMP(mp1)) {
3055 case IDM_MOVE:
3056 case IDM_COPY:
3057 case IDM_WILDCOPY:
3058 case IDM_WILDMOVE:
3059 case IDM_WPSMOVE:
3060 case IDM_WPSCOPY:
3061 case IDM_RENAME:
3062 case IDM_DELETE:
3063 case IDM_PERMDELETE:
3064 mp1 = MPFROM2SHORT(IDM_INFO, SHORT2FROMMP(mp1));
3065 li->type = IDM_INFO;
[176]3066 }
3067 }
[551]3068 switch (SHORT1FROMMP(mp1)) {
3069 case IDM_APPENDTOCLIP:
3070 case IDM_SAVETOCLIP:
3071 case IDM_ARCHIVE:
3072 case IDM_DELETE:
3073 case IDM_PERMDELETE:
3074 case IDM_ATTRS:
3075 case IDM_SHADOW:
3076 case IDM_SHADOW2:
3077 case IDM_DOITYOURSELF:
3078 case IDM_EAS:
3079 case IDM_VIEW:
3080 case IDM_VIEWTEXT:
3081 case IDM_VIEWBINARY:
3082 case IDM_EDIT:
3083 case IDM_EDITTEXT:
3084 case IDM_EDITBINARY:
3085 case IDM_MCIPLAY:
3086 action = UM_MASSACTION;
[1856]3087 }
3088 if (li->type == IDM_DELETE)
3089 ignorereadonly = FALSE;
[551]3090 if (SHORT1FROMMP(mp1) == IDM_SHADOW ||
3091 SHORT1FROMMP(mp1) == IDM_SHADOW2)
3092 *li->targetpath = 0;
3093 if (!PostMsg(dcd->hwndObject, action, MPFROMP(li), MPVOID)) {
[1400]3094 Runtime_Error(pszSrcFile, __LINE__, PCSZ_POSTMSG);
[551]3095 FreeListInfo(li);
3096 }
3097 }
[1077]3098# ifdef FORTIFY
3099 Fortify_LeaveScope();
3100# endif
[551]3101 }
3102 break;
[2]3103
[551]3104 default:
3105 if (SHORT1FROMMP(mp1) >= IDM_COMMANDSTART &&
3106 SHORT1FROMMP(mp1) < IDM_QUICKTOOLSTART) {
[2]3107
[551]3108 INT x;
[2]3109
[551]3110 if (!cmdloaded)
3111 load_commands();
[1880]3112 x = SHORT1FROMMP(mp1);
[551]3113 if (x >= 0) {
3114 RunCommand(hwnd, x);
3115 if (fUnHilite)
[672]3116 UnHilite(hwnd, TRUE, &dcd->lastselection, 0);
[551]3117 }
[176]3118 }
[551]3119 break;
[2]3120 }
[551]3121 }
3122 return 0;
[2]3123
[551]3124 case WM_SAVEAPPLICATION:
3125 if (dcd && !ParentIsDesktop(hwnd, dcd->hwndParent)) {
[2]3126
[551]3127 SWP swp, swpP;
3128 INT ratio;
[2]3129
[551]3130 WinQueryWindowPos(dcd->hwndFrame, &swp);
3131 if (!(swp.fl & (SWP_MINIMIZE | SWP_MAXIMIZE | SWP_HIDE))) {
3132 WinQueryWindowPos(dcd->hwndParent, &swpP);
[954]3133 if (swp.cx) {
3134 ratio = (swpP.cx * 100) / swp.cx;
3135 if (ratio > 0)
3136 PrfWriteProfileData(fmprof, appname, "TreeWindowRatio",
3137 &ratio, sizeof(INT));
3138 }
[2]3139 }
[551]3140 }
3141 else if (dcd && ParentIsDesktop(hwnd, dcd->hwndParent)) {
[2]3142
[551]3143 SWP swp;
[2]3144
[551]3145 WinQueryWindowPos(dcd->hwndFrame, &swp);
3146 if (!(swp.fl & (SWP_HIDE | SWP_MINIMIZE | SWP_MAXIMIZE)))
[1498]3147 WinStoreWindowPos((CHAR *) FM2Str, "VTreeWindowPos", dcd->hwndFrame);
[551]3148 }
3149 break;
[2]3150
[551]3151 case UM_MINIMIZE:
3152 if (dcd && hwndMain) {
3153 fOkayMinimize = TRUE;
[1868]3154 if (dcd->hwndObject) {
[1880]3155 DosSleep(50);
[551]3156 fOkayMinimize = FALSE;
3157 WinSetWindowPos(((hwndMain) ? WinQueryWindow(hwndMain, QW_PARENT) :
3158 dcd->hwndFrame), HWND_TOP, 0, 0, 0, 0,
3159 SWP_MINIMIZE | SWP_DEACTIVATE);
[2]3160 }
[551]3161 }
3162 return 0;
[2]3163
[551]3164 case UM_MAXIMIZE:
3165 if (dcd || hwndMain)
3166 WinSetWindowPos(((hwndMain) ? WinQueryWindow(hwndMain, QW_PARENT) :
3167 dcd->hwndFrame), HWND_TOP, 0, 0, 0, 0, SWP_MAXIMIZE |
3168 SWP_SHOW);
3169 return 0;
[2]3170
[551]3171 case UM_CLOSE:
3172 {
3173 HWND hwndParent = WinQueryWindow(WinQueryWindow(WinQueryWindow(hwnd,
3174 QW_PARENT),
3175 QW_PARENT), QW_PARENT);
[2]3176
[551]3177 if (!mp1) {
3178 if (!PostMsg((HWND) 0, WM_QUIT, MPVOID, MPVOID))
3179 WinSendMsg((HWND) 0, WM_QUIT, MPVOID, MPVOID);
3180 if (hwndParent && !ParentIsDesktop(hwnd, hwndParent))
3181 WinDestroyWindow(hwndParent);
[2]3182 }
3183 else
[551]3184 WinDestroyWindow(WinQueryWindow(WinQueryWindow(hwnd, QW_PARENT),
3185 QW_PARENT));
3186 }
3187 return 0;
[2]3188
[551]3189 case WM_CLOSE:
3190 WinSendMsg(hwnd, WM_SAVEAPPLICATION, MPVOID, MPVOID);
3191 if (dcd)
3192 dcd->stopflag++;
3193 if (dcd && dcd->hwndObject) {
[1673]3194 // kill object window
[1340]3195 if (WinIsWindow((HAB) 0, dcd->hwndObject)) {
[1394]3196 if (!PostMsg(dcd->hwndObject, WM_CLOSE, MPVOID, MPVOID))
3197 WinSendMsg(dcd->hwndObject, WM_CLOSE, MPVOID, MPVOID);
[1340]3198 }
[551]3199 }
3200 else
[766]3201 WinSendMsg(hwnd, UM_CLOSE, MPFROMLONG(1), MPVOID);
[551]3202 return 0;
[2]3203
[551]3204 case WM_DESTROY:
[1335]3205# ifdef FORTIFY
[1856]3206 DbgMsg(pszSrcFile, __LINE__, "WM_DESTROY hwnd %x TID %u", hwnd, GetTidForThread()); // 18 Jul 08 SHL FIXME
[1335]3207# endif
[551]3208 if (TreeCnrMenu)
3209 WinDestroyWindow(TreeCnrMenu);
3210 if (DirMenu)
3211 WinDestroyWindow(DirMenu);
3212 if (FileMenu)
3213 WinDestroyWindow(FileMenu);
3214 TreeCnrMenu = FileMenu = DirMenu = (HWND) 0;
3215 EmptyCnr(hwnd);
3216 if (apphead) {
3217 APPNOTIFY *info, *next;
[1650]3218
[551]3219 info = apphead;
3220 while (info) {
3221 next = info->next;
[1039]3222 free(info);
[551]3223 info = next;
[2]3224 }
[551]3225 apphead = apptail = NULL;
3226 }
[1077]3227# ifdef FORTIFY
3228 Fortify_LeaveScope();
3229# endif
3230 break; // WM_DESTROY
3231 } // switch
[705]3232 if (dcd && dcd->oldproc){
[1650]3233 return dcd->oldproc(hwnd, msg, mp1, mp2);
[705]3234 }
3235 else
[1650]3236 return PFNWPCnr(hwnd, msg, mp1, mp2);
[2]3237}
3238
[1778]3239/**
3240 * Start drive tree container
3241 * @returns tree handle or NULLHANDLE
3242 */
3243
[551]3244HWND StartTreeCnr(HWND hwndParent, ULONG flags)
[352]3245{
[1673]3246 /**
3247 * bitmapped flags:
[2]3248 * 0x00000001 = don't close app when window closes
3249 * 0x00000002 = no frame controls
[947]3250 * 0x00000004 = no close or move button
[2]3251 */
3252
[947]3253 HWND hwndFrame = NULLHANDLE;
3254 HWND hwndSysMenu = NULLHANDLE;
3255 HWND hwndClient;
[551]3256 ULONG FrameFlags = FCF_TITLEBAR | FCF_SYSMENU |
3257 FCF_SIZEBORDER | FCF_MINMAX | FCF_ICON | FCF_NOBYTEALIGN | FCF_ACCELTABLE;
3258 DIRCNRDATA *dcd;
[2]3259
[551]3260 if (!hwndParent)
[2]3261 hwndParent = HWND_DESKTOP;
[551]3262 if (ParentIsDesktop(hwndParent, hwndParent))
[2]3263 FrameFlags |= (FCF_TASKLIST | FCF_MENU);
[551]3264 if (flags & 2)
[2]3265 FrameFlags &= (~(FCF_TITLEBAR | FCF_SYSMENU | FCF_SIZEBORDER |
[551]3266 FCF_MINMAX | FCF_ICON));
[2]3267 hwndFrame = WinCreateStdWindow(hwndParent,
[176]3268 WS_VISIBLE,
3269 &FrameFlags,
[1498]3270 (CHAR *) WC_TREECONTAINER,
[176]3271 NULL,
3272 WS_VISIBLE | fwsAnimate,
[953]3273 FM3ModHandle, TREE_FRAME, &hwndClient);
[950]3274 if (hwndParent != HWND_DESKTOP) {
[947]3275 hwndSysMenu = WinWindowFromID(hwndFrame, FID_SYSMENU);
3276 if (hwndSysMenu != NULLHANDLE)
3277 WinSendMsg(hwndSysMenu, MM_SETITEMATTR,
[953]3278 MPFROM2SHORT(SC_CLOSE, TRUE),
3279 MPFROM2SHORT(MIA_DISABLED, MIA_DISABLED));
[947]3280 if (!fFreeTree)
3281 WinSendMsg(hwndSysMenu, MM_SETITEMATTR,
[953]3282 MPFROM2SHORT(SC_MOVE, TRUE),
3283 MPFROM2SHORT(MIA_DISABLED, MIA_DISABLED));
[947]3284 }
[551]3285 if (hwndFrame && hwndClient) {
[1063]3286# ifdef FORTIFY
3287 Fortify_EnterScope();
[1077]3288# endif
[1017]3289 dcd = xmallocz(sizeof(DIRCNRDATA), pszSrcFile, __LINE__);
[352]3290 if (!dcd) {
[551]3291 Runtime_Error(pszSrcFile, __LINE__, GetPString(IDS_OUTOFMEMORY));
3292 PostMsg(hwndClient, WM_CLOSE, MPVOID, MPVOID);
3293 hwndFrame = (HWND) 0;
[352]3294 }
3295 else {
[2]3296 SWP swp;
[551]3297 WinQueryWindowPos(hwndFrame, &swp);
3298 if (*(ULONG *) realappname == FM3UL) {
[377]3299 if (!WinCreateWindow(hwndFrame,
[1498]3300 (CHAR *) WC_TREEOPENBUTTON,
[1335]3301 "#303",
[1277]3302 WS_VISIBLE | BS_PUSHBUTTON | BS_NOPOINTERFOCUS | BS_BITMAP,
[551]3303 ((swp.cx -
3304 WinQuerySysValue(HWND_DESKTOP,
3305 SV_CXMINMAXBUTTON)) -
3306 WinQuerySysValue(HWND_DESKTOP,
3307 SV_CXMINMAXBUTTON) / 2) -
[739]3308 WinQuerySysValue(HWND_DESKTOP, SV_CXSIZEBORDER),
[551]3309 (swp.cy -
3310 WinQuerySysValue(HWND_DESKTOP,
3311 SV_CYMINMAXBUTTON)) -
[739]3312 WinQuerySysValue(HWND_DESKTOP, SV_CYSIZEBORDER),
[551]3313 WinQuerySysValue(HWND_DESKTOP,
3314 SV_CXMINMAXBUTTON) / 2,
3315 WinQuerySysValue(HWND_DESKTOP,
3316 SV_CYMINMAXBUTTON), hwndFrame,
[739]3317 HWND_TOP, IDM_OPENWINDOW, NULL, NULL)) {
[1395]3318 Win_Error(hwndFrame, hwndParent, pszSrcFile, __LINE__,
3319 PCSZ_WINCREATEWINDOW);
[377]3320 }
3321 }
3322 else {
3323 if (!WinCreateWindow(hwndFrame,
[1498]3324 (CHAR *) WC_TREESTATUS,
3325 (CHAR *) GetPString(IDS_YOUAREHERETEXT),
[551]3326 WS_VISIBLE | SS_TEXT | DT_LEFT | DT_VCENTER,
3327 swp.x + 4 + WinQuerySysValue(HWND_DESKTOP,
3328 SV_CXSIZEBORDER),
3329 swp.cy - (22 + WinQuerySysValue(HWND_DESKTOP,
3330 SV_CYSIZEBORDER)),
3331 (swp.cx - 8) - (WinQuerySysValue(HWND_DESKTOP,
3332 SV_CXSIZEBORDER)
3333 * 2), 22, hwndFrame, HWND_TOP,
3334 MAIN_STATUS, NULL, NULL)) {
[1395]3335 Win_Error(hwndFrame, hwndParent, pszSrcFile, __LINE__,
3336 PCSZ_WINCREATEWINDOW);
[377]3337 }
3338 }
[551]3339 memset(dcd, 0, sizeof(DIRCNRDATA));
[2]3340 dcd->size = sizeof(DIRCNRDATA);
3341 dcd->type = TREE_FRAME;
[1778]3342 dcd->dontclose = (flags & 1) != 0;
3343 dcd->hwndParent = hwndParent ? hwndParent : HWND_DESKTOP;
[2]3344 dcd->hwndClient = hwndClient;
[551]3345 dcd->hwndFrame = hwndFrame;
[2]3346 {
[176]3347 PFNWP oldproc;
[2]3348
[551]3349 oldproc = WinSubclassWindow(hwndFrame, TreeFrameWndProc);
3350 WinSetWindowPtr(hwndFrame, QWL_USER, (PVOID) oldproc);
3351 oldproc = WinSubclassWindow(WinWindowFromID(hwndFrame, FID_TITLEBAR),
3352 (PFNWP) TreeTitleWndProc);
3353 WinSetWindowPtr(WinWindowFromID(hwndFrame, FID_TITLEBAR),
3354 QWL_USER, (PVOID) oldproc);
[2]3355 }
3356 dcd->hwndCnr = WinCreateWindow(hwndClient,
[176]3357 WC_CONTAINER,
3358 NULL,
3359 CCS_AUTOPOSITION | CCS_MINIICONS |
[1455]3360 CCS_MINIRECORDCORE,
[176]3361 0,
3362 0,
3363 0,
3364 0,
3365 hwndClient,
[551]3366 HWND_TOP, (ULONG) TREE_CNR, NULL, NULL);
[377]3367 if (!dcd->hwndCnr) {
[1395]3368 Win_Error(hwndClient, hwndClient, pszSrcFile, __LINE__,
3369 PCSZ_WINCREATEWINDOW);
[551]3370 PostMsg(hwndClient, WM_CLOSE, MPVOID, MPVOID);
[1077]3371 free(dcd);
[1813]3372 dcd = NULL;
[551]3373 hwndFrame = (HWND) 0;
[377]3374 }
3375 else {
[551]3376 WinSetWindowPtr(dcd->hwndCnr, QWL_USER, (PVOID) dcd);
3377 if (ParentIsDesktop(hwndFrame, hwndParent)) {
3378 WinSetWindowText(WinWindowFromID(hwndFrame, FID_TITLEBAR), "VTree");
[1455]3379 FixSwitchList(hwndFrame, "VTree");
[176]3380 }
3381 else {
[1498]3382 WinSetWindowText(hwndFrame, (CHAR *) GetPString(IDS_TREETEXT));
[551]3383 WinSetWindowText(WinWindowFromID(hwndFrame, FID_TITLEBAR),
[1498]3384 (CHAR *) GetPString(IDS_TREETEXT));
[176]3385 }
[726]3386 dcd->oldproc = WinSubclassWindow(dcd->hwndCnr, TreeCnrWndProc);
3387 // fixme to document 01 test?
[766]3388 if (dcd->oldproc == 0)
[947]3389 Win_Error(HWND_DESKTOP, HWND_DESKTOP, pszSrcFile, __LINE__,
[953]3390 "WinSubclassWindow");
[551]3391 if (!PostMsg(dcd->hwndCnr, UM_SETUP, MPVOID, MPVOID))
3392 WinSendMsg(dcd->hwndCnr, UM_SETUP, MPVOID, MPVOID);
[2]3393 }
3394 }
[1077]3395# ifdef FORTIFY
3396 if (dcd)
3397 Fortify_ChangeScope(dcd, -1);
3398 Fortify_LeaveScope();
3399 if (dcd)
3400 Fortify_ChangeScope(dcd, +1);
3401# endif
[2]3402 }
[1771]3403 WinShowWindow(hwndFrame, FALSE);
[2]3404 return hwndFrame;
3405}
[793]3406
[1871]3407static VOID ExpandTreeThread(VOID *args)
3408{
3409 QMSG qmsg;
3410 DIRCNRDATA *dcd;
3411 HAB hab = WinInitialize(0);
3412# ifdef FORTIFY
3413 Fortify_EnterScope();
3414# endif
3415 if (hab) {
3416 hmqExpandTree = WinCreateMsgQueue(hab, 0);
3417 if (hmqExpandTree) {
3418 while (WinGetMsg(hab, &qmsg, (HWND) 0, UM_COLLAPSETREE, UM_EXPANDTREE)) {
3419 dcd = (DIRCNRDATA *) qmsg.mp2;
3420 if (!dcd)
3421 Runtime_Error(pszSrcFile, __LINE__, NULL);
3422 else {
3423 PCNRITEM pci = (PCNRITEM) qmsg.mp1;
3424
3425 if (pci && (INT) pci != -1 && !(pci->flags & RECFLAGS_ENV)) {
3426 if (driveflags[toupper(*pci->pszFileName) - 'A'] & DRIVE_REMOVABLE) {
3427
3428 struct
3429 {
3430 ULONG serial;
3431 CHAR volumelength;
3432 CHAR volumelabel[CCHMAXPATH];
3433 }
3434 volser;
3435
3436 memset(&volser, 0, sizeof(volser));
3437 DosError(FERR_DISABLEHARDERR);
3438 if (!DosQueryFSInfo(toupper(*pci->pszFileName) - '@',
3439 FSIL_VOLSER, &volser,
3440 (ULONG) sizeof(volser))) {
3441 if (qmsg.msg == UM_COLLAPSETREE &&
3442 !volser.serial ||
3443 driveserial[toupper(*pci->pszFileName) - 'A'] !=
3444 volser.serial)
[1874]3445 {
[1876]3446 if (pci->fleshed) {
3447 WaitFleshWorkListEmpty(pci->pszFileName, 10); // 2015-08-19 SHL in case pci still in work list
3448 AddFleshWorkRequest(dcd->hwndCnr, pci, eUnFlesh);
3449 }
[1871]3450 }
3451 if (qmsg.msg != UM_COLLAPSETREE ||
3452 (!volser.serial ||
3453 driveserial[toupper(*pci->pszFileName) - 'A'] !=
3454 volser.serial)) {
[1874]3455 WaitFleshWorkListEmpty(pci->pszFileName, 10); // 2015-08-19 SHL in case pci still in work list
[1871]3456 if (qmsg.msg == UM_EXPANDTREE && AddFleshWorkRequest(dcd->hwndCnr, pci, eFlesh)
[1874]3457 && !dcd->suspendview && fTopDir) {
[1871]3458 PostMsg(dcd->hwndCnr, UM_TOPDIR, MPFROMP(pci), MPVOID);
3459 }
3460 }
3461 driveserial[toupper(*pci->pszFileName) - 'A'] = volser.serial;
3462 }
3463 else {
3464 driveserial[toupper(*pci->pszFileName) - 'A'] = -1;
[1876]3465 if (pci->fleshed) {
3466 WaitFleshWorkListEmpty(pci->pszFileName, 10); // 2015-08-19 SHL in case pci still in work list
3467 AddFleshWorkRequest(dcd->hwndCnr, pci, eUnFlesh);
3468 }
[1871]3469 PostMsg(dcd->hwndCnr, UM_RESCAN, MPVOID, MPVOID);
3470 if (!fAlertBeepOff)
3471 DosBeep(250, 100);
3472 }
3473 }
3474 else if (qmsg.msg == UM_EXPANDTREE) {
3475 if (fExpandAll)
3476 DosSleep(1);
3477 else {
[1874]3478 WaitFleshWorkListEmpty(pci->pszFileName, 10); // 2015-08-19 SHL in case pci still in work list
[1871]3479 }
3480 AddFleshWorkRequest(dcd->hwndCnr, pci, eFlesh); // forceFlesh
[1874]3481 if (!dcd->suspendview && fTopDir) {
[1871]3482 PostMsg(dcd->hwndCnr, UM_TOPDIR, MPFROMP(pci), MPVOID);
3483 }
3484 }
3485 if (qmsg.msg == UM_EXPANDTREE && !dcd->suspendview) {
3486 WinSendMsg(dcd->hwndCnr, UM_FILTER, MPVOID, MPVOID);
3487 }
3488 }
3489 }
3490 }
3491 }
3492 WinDestroyMsgQueue(hmqExpandTree);
3493 }
3494 WinTerminate(hab);
3495# ifdef FORTIFY
3496 Fortify_LeaveScope();
3497# endif
3498}
3499
[1879]3500BOOL StartExpandTreeThread(VOID)
[1871]3501{
3502 TID tid;
3503 tid = xbeginthread(ExpandTreeThread,
3504 65536,
3505 NULL,
3506 pszSrcFile, __LINE__);
3507 return tid != -1;
3508
3509}
3510
[793]3511#pragma alloc_text(TREECNR,TreeCnrWndProc,TreeObjWndProc,TreeClientWndProc)
3512#pragma alloc_text(TREECNR,TreeFrameWndProc,TreeTitleWndProc,ShowTreeRec)
3513#pragma alloc_text(TREECNR,TreeStatProc,OpenButtonProc)
3514#pragma alloc_text(STARTUP,StartTreeCnr)
Note: See TracBrowser for help on using the repository browser.