Skip to content

Commit a444572

Browse files
authored
[SHIMGVW] Display error message on delete failure (reactos#7776)
CORE-20019
1 parent 70422cd commit a444572

File tree

5 files changed

+73
-44
lines changed

5 files changed

+73
-44
lines changed

dll/win32/shimgvw/resource.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,9 @@
1010
/* Cursors */
1111
#define IDC_HANDDRAG 100
1212

13+
/* Control IDs */
14+
#define IDC_TOOLBAR 40
15+
1316
/* Toolbar images */
1417
#define IDB_PREV_PIC 50
1518
#define IDB_NEXT_PIC 51

dll/win32/shimgvw/shimgvw.c

Lines changed: 57 additions & 41 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@ HINSTANCE g_hInstance = NULL;
3131
HWND g_hMainWnd = NULL;
3232
HWND g_hwndFullscreen = NULL;
3333
SHIMGVW_FILENODE * g_pCurrentFile = NULL;
34+
WCHAR g_szFile[MAX_PATH];
3435
GpImage * g_pImage = NULL;
3536
SHIMGVW_SETTINGS g_Settings;
3637
UINT g_ImageId;
@@ -119,7 +120,6 @@ typedef struct tagPREVIEW_DATA
119120
UINT m_nTimerInterval;
120121
BOOL m_bHideCursor;
121122
POINT m_ptOrigin;
122-
WCHAR m_szFile[MAX_PATH];
123123
} PREVIEW_DATA, *PPREVIEW_DATA;
124124

125125
static VOID Preview_ToggleSlideShowEx(PPREVIEW_DATA pData, BOOL StartTimer);
@@ -374,18 +374,20 @@ Preview_pFreeImage(PPREVIEW_DATA pData)
374374
GdipDisposeImage(g_pImage);
375375
g_pImage = NULL;
376376
}
377-
378-
pData->m_szFile[0] = UNICODE_NULL;
379377
}
380378

381379
static VOID
382380
Preview_pLoadImage(PPREVIEW_DATA pData, LPCWSTR szOpenFileName)
383381
{
384382
HRESULT hr;
383+
BOOL bCanDel;
385384
Preview_pFreeImage(pData);
386385
InvalidateRect(pData->m_hwnd, NULL, FALSE); /* Schedule redraw in case we change to "No preview" */
387386

387+
GetFullPathNameW(szOpenFileName, _countof(g_szFile), g_szFile, NULL);
388388
hr = LoadImageFromPath(szOpenFileName, &g_pImage);
389+
bCanDel = hr != HRESULT_FROM_WIN32(ERROR_FILE_NOT_FOUND) && hr != HRESULT_FROM_WIN32(ERROR_PATH_NOT_FOUND);
390+
SendDlgItemMessageW(g_hMainWnd, IDC_TOOLBAR, TB_ENABLEBUTTON, IDC_DELETE, bCanDel);
389391
if (FAILED(hr))
390392
{
391393
DPRINT1("GdipLoadImageFromStream() failed, %d\n", hr);
@@ -396,17 +398,14 @@ Preview_pLoadImage(PPREVIEW_DATA pData, LPCWSTR szOpenFileName)
396398

397399
Anime_LoadInfo(&pData->m_Anime);
398400

399-
GetFullPathNameW(szOpenFileName, _countof(pData->m_szFile), pData->m_szFile, NULL);
400-
SHAddToRecentDocs(SHARD_PATHW, pData->m_szFile);
401-
402401
/* Reset zoom and redraw display */
403402
Preview_ResetZoom(pData);
404-
405-
Preview_UpdateTitle(pData, szOpenFileName);
403+
SHAddToRecentDocs(SHARD_PATHW, g_szFile);
404+
Preview_UpdateTitle(pData, g_szFile);
406405

407406
++g_ImageId;
408-
EnableCommandIfVerbExists(g_ImageId, g_hMainWnd, IDC_PRINT, L"print", pData->m_szFile);
409-
EnableCommandIfVerbExists(g_ImageId, g_hMainWnd, IDC_MODIFY, L"edit", pData->m_szFile);
407+
EnableCommandIfVerbExists(g_ImageId, g_hMainWnd, IDC_PRINT, L"print", g_szFile);
408+
EnableCommandIfVerbExists(g_ImageId, g_hMainWnd, IDC_MODIFY, L"edit", g_szFile);
410409
}
411410

412411
static VOID
@@ -562,7 +561,7 @@ Preview_pSaveImageAs(PPREVIEW_DATA pData)
562561
static VOID
563562
Preview_pPrintImage(PPREVIEW_DATA pData)
564563
{
565-
ShellExecuteVerb(g_hMainWnd, L"print", pData->m_szFile, FALSE);
564+
ShellExecuteVerb(g_hMainWnd, L"print", g_szFile, FALSE);
566565
}
567566

568567
static VOID
@@ -584,6 +583,14 @@ Preview_UpdateImage(PPREVIEW_DATA pData)
584583
ZoomWnd_UpdateScroll(pData, TRUE);
585584
}
586585

586+
static VOID
587+
Preview_LoadImage(PPREVIEW_DATA pData, SHIMGVW_FILENODE *pNode)
588+
{
589+
Preview_pLoadImageFromNode(pData, pNode);
590+
Preview_UpdateImage(pData);
591+
Preview_UpdateUI(pData);
592+
}
593+
587594
static SHIMGVW_FILENODE*
588595
pBuildFileList(LPCWSTR szFirstFile)
589596
{
@@ -948,7 +955,7 @@ Preview_CreateToolBar(PPREVIEW_DATA pData)
948955

949956
style |= CCS_BOTTOM;
950957
hwndToolBar = CreateWindowExW(0, TOOLBARCLASSNAMEW, NULL, style,
951-
0, 0, 0, 0, pData->m_hwnd, NULL, g_hInstance, NULL);
958+
0, 0, 0, 0, pData->m_hwnd, (HMENU)IDC_TOOLBAR, g_hInstance, NULL);
952959
if (!hwndToolBar)
953960
return FALSE;
954961

@@ -1217,8 +1224,8 @@ ZoomWndProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
12171224
break;
12181225
}
12191226
case WM_CONTEXTMENU:
1220-
if (Preview_IsMainWnd(pData->m_hwnd))
1221-
DoShellContextMenuOnFile(hwnd, pData->m_szFile, lParam);
1227+
if (Preview_IsMainWnd(pData->m_hwnd) && *g_szFile)
1228+
DoShellContextMenuOnFile(hwnd, g_szFile, lParam);
12221229
break;
12231230
case WM_HSCROLL:
12241231
case WM_VSCROLL:
@@ -1302,9 +1309,7 @@ Preview_OnCreate(HWND hwnd, LPCREATESTRUCT pCS)
13021309
PathUnquoteSpacesW(szFile);
13031310

13041311
g_pCurrentFile = pBuildFileList(szFile);
1305-
Preview_pLoadImageFromNode(pData, g_pCurrentFile);
1306-
Preview_UpdateImage(pData);
1307-
Preview_UpdateUI(pData);
1312+
Preview_LoadImage(pData, g_pCurrentFile);
13081313
}
13091314

13101315
return TRUE;
@@ -1368,14 +1373,11 @@ static VOID
13681373
Preview_Delete(PPREVIEW_DATA pData)
13691374
{
13701375
WCHAR szCurFile[MAX_PATH + 1], szNextFile[MAX_PATH];
1371-
HWND hwnd = pData->m_hwnd;
1372-
SHFILEOPSTRUCTW FileOp = { hwnd, FO_DELETE };
1373-
1374-
if (!pData->m_szFile[0])
1375-
return;
1376+
SHFILEOPSTRUCTW FileOp = { pData->m_hwnd, FO_DELETE };
1377+
UINT error;
13761378

13771379
/* FileOp.pFrom must be double-null-terminated */
1378-
GetFullPathNameW(pData->m_szFile, _countof(szCurFile) - 1, szCurFile, NULL);
1380+
GetFullPathNameW(g_szFile, _countof(szCurFile) - 1, szCurFile, NULL);
13791381
szCurFile[_countof(szCurFile) - 2] = UNICODE_NULL; /* Avoid buffer overrun */
13801382
szCurFile[lstrlenW(szCurFile) + 1] = UNICODE_NULL;
13811383

@@ -1388,24 +1390,27 @@ Preview_Delete(PPREVIEW_DATA pData)
13881390

13891391
/* Confirm file deletion and delete if allowed */
13901392
FileOp.pFrom = szCurFile;
1391-
FileOp.fFlags = FOF_ALLOWUNDO;
1392-
if (SHFileOperationW(&FileOp) != 0)
1393+
FileOp.fFlags = GetKeyState(VK_SHIFT) < 0 ? 0 : FOF_ALLOWUNDO;
1394+
error = g_szFile[0] ? SHFileOperationW(&FileOp) : ERROR_FILE_NOT_FOUND;
1395+
if (error != 0)
13931396
{
1394-
DPRINT("Preview_Delete: SHFileOperationW() failed or canceled\n");
1397+
enum { SHFO_FIRSTCUSTOMERROR = 0x71 /* DE_SAMEFILE */ };
1398+
if (!FileOp.fAnyOperationsAborted && error != ERROR_CANCELLED)
1399+
ErrorBox(FileOp.hwnd, error < SHFO_FIRSTCUSTOMERROR ? error : E_FAIL);
13951400
return;
13961401
}
13971402

13981403
/* Reload the file list and go next file */
13991404
pFreeFileList(g_pCurrentFile);
14001405
g_pCurrentFile = pBuildFileList(szNextFile);
1401-
Preview_pLoadImageFromNode(pData, g_pCurrentFile);
1406+
Preview_LoadImage(pData, g_pCurrentFile);
14021407
}
14031408

14041409
static VOID
14051410
Preview_Edit(HWND hwnd)
14061411
{
14071412
PPREVIEW_DATA pData = Preview_GetData(g_hMainWnd);
1408-
ShellExecuteVerb(pData->m_hwnd, L"edit", pData->m_szFile, TRUE);
1413+
ShellExecuteVerb(pData->m_hwnd, L"edit", g_szFile, TRUE);
14091414
}
14101415

14111416
static VOID
@@ -1452,16 +1457,28 @@ Preview_GoNextPic(PPREVIEW_DATA pData, BOOL bNext)
14521457
g_pCurrentFile = g_pCurrentFile->Next;
14531458
else
14541459
g_pCurrentFile = g_pCurrentFile->Prev;
1455-
Preview_pLoadImageFromNode(pData, g_pCurrentFile);
1456-
Preview_UpdateImage(pData);
1457-
Preview_UpdateUI(pData);
1460+
Preview_LoadImage(pData, g_pCurrentFile);
14581461
}
14591462
}
14601463

1464+
static HRESULT
1465+
IsCommandEnabled(UINT nCmdId)
1466+
{
1467+
HWND hToolbar = GetDlgItem(g_hMainWnd, IDC_TOOLBAR);
1468+
LRESULT Ok = SendMessageW(hToolbar, TB_ISBUTTONENABLED, nCmdId, 0);
1469+
return Ok ? S_OK : SendMessageW(hToolbar, TB_COMMANDTOINDEX, nCmdId, 0) != -1 ? S_FALSE : E_FAIL;
1470+
}
1471+
14611472
static VOID
1462-
Preview_OnCommand(HWND hwnd, UINT nCommandID)
1473+
Preview_OnCommand(HWND hwnd, WPARAM wParam, LPARAM lParam)
14631474
{
14641475
PPREVIEW_DATA pData = Preview_GetData(hwnd);
1476+
UINT nCommandID = LOWORD(wParam);
1477+
if ((!HIWORD(wParam) || !lParam) && IsCommandEnabled(nCommandID) == S_FALSE)
1478+
{
1479+
MessageBeep(MB_ICONWARNING);
1480+
return;
1481+
}
14651482

14661483
switch (nCommandID)
14671484
{
@@ -1544,7 +1561,7 @@ Preview_OnCommand(HWND hwnd, UINT nCommandID)
15441561
if (g_pImage)
15451562
{
15461563
GdipImageRotateFlip(g_pImage, Rotate270FlipNone);
1547-
Preview_pSaveImage(pData, pData->m_szFile);
1564+
Preview_pSaveImage(pData, g_szFile);
15481565
Preview_UpdateImage(pData);
15491566
}
15501567
break;
@@ -1553,15 +1570,13 @@ Preview_OnCommand(HWND hwnd, UINT nCommandID)
15531570
if (g_pImage)
15541571
{
15551572
GdipImageRotateFlip(g_pImage, Rotate90FlipNone);
1556-
Preview_pSaveImage(pData, pData->m_szFile);
1573+
Preview_pSaveImage(pData, g_szFile);
15571574
Preview_UpdateImage(pData);
15581575
}
15591576
break;
15601577

15611578
case IDC_DELETE:
15621579
Preview_Delete(pData);
1563-
Preview_UpdateImage(pData);
1564-
Preview_UpdateUI(pData);
15651580
break;
15661581

15671582
case IDC_MODIFY:
@@ -1629,7 +1644,7 @@ Preview_OnDropFiles(HWND hwnd, HDROP hDrop)
16291644

16301645
pFreeFileList(g_pCurrentFile);
16311646
g_pCurrentFile = pBuildFileList(szFile);
1632-
Preview_pLoadImageFromNode(pData, g_pCurrentFile);
1647+
Preview_LoadImage(pData, g_pCurrentFile);
16331648

16341649
DragFinish(hDrop);
16351650
}
@@ -1647,7 +1662,7 @@ PreviewWndProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
16471662
}
16481663
case WM_COMMAND:
16491664
{
1650-
Preview_OnCommand(hwnd, LOWORD(wParam));
1665+
Preview_OnCommand(hwnd, wParam, lParam);
16511666
break;
16521667
}
16531668
case WM_NOTIFY:
@@ -1732,14 +1747,15 @@ ImageView_Main(HWND hwnd, LPCWSTR szFileName)
17321747
HACCEL hAccel;
17331748
HRESULT hrCoInit;
17341749
INITCOMMONCONTROLSEX Icc = { .dwSize = sizeof(Icc), .dwICC = ICC_WIN95_CLASSES };
1750+
g_szFile[0] = UNICODE_NULL;
17351751

17361752
InitCommonControlsEx(&Icc);
17371753
SetThreadPriority(GetCurrentThread(), THREAD_PRIORITY_ABOVE_NORMAL); // Give UI higher priority than background threads
17381754

17391755
/* Initialize COM */
1740-
hrCoInit = CoInitializeEx(NULL, COINIT_APARTMENTTHREADED | COINIT_DISABLE_OLE1DDE);
1756+
hrCoInit = OleInitialize(NULL);
17411757
if (FAILED(hrCoInit))
1742-
DPRINT1("Warning, CoInitializeEx failed with code=%08X\n", (int)hrCoInit);
1758+
DPRINT1("Warning, OleInitialize failed with code=%08X\n", (int)hrCoInit);
17431759

17441760
if (!ImageView_LoadSettings())
17451761
ImageView_ResetSettings();
@@ -1807,7 +1823,7 @@ ImageView_Main(HWND hwnd, LPCWSTR szFileName)
18071823

18081824
/* Release COM resources */
18091825
if (SUCCEEDED(hrCoInit))
1810-
CoUninitialize();
1826+
OleUninitialize();
18111827

18121828
return 0;
18131829
}

dll/win32/shimgvw/shimgvw.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -76,6 +76,7 @@ BOOL Anime_OnTimer(PANIME pAnime, WPARAM wParam);
7676
void DoShellContextMenuOnFile(HWND hwnd, PCWSTR File, LPARAM lParam);
7777
void EnableCommandIfVerbExists(UINT ImageId, HWND hwnd, UINT CmdId, PCWSTR Verb, PCWSTR File);
7878
void ShellExecuteVerb(HWND hwnd, PCWSTR Verb, PCWSTR File, BOOL Quit);
79+
UINT ErrorBox(HWND hwnd, UINT Error);
7980
void DisplayHelp(HWND hwnd);
8081

8182
static inline LPVOID QuickAlloc(SIZE_T cbSize, BOOL bZero)

dll/win32/shimgvw/shimgvw.rc

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,7 @@ BEGIN
5959
"K", IDC_ROT_CLOCKW, VIRTKEY, CONTROL
6060
"L", IDC_ROT_COUNCW, VIRTKEY, CONTROL
6161
VK_DELETE, IDC_DELETE, VIRTKEY
62+
VK_DELETE, IDC_DELETE, VIRTKEY, SHIFT
6263
"P", IDC_PRINT, VIRTKEY, CONTROL
6364
"S", IDC_SAVEAS, VIRTKEY, CONTROL
6465
"E", IDC_MODIFY, VIRTKEY, CONTROL

dll/win32/shimgvw/util.c

Lines changed: 11 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -62,7 +62,8 @@ ModifyShellContextMenu(IContextMenu *pCM, HMENU hMenu, UINT CmdIdFirst, PCWSTR A
6262
UINT remove = FALSE;
6363
if (IsSelfShellVerb(Assoc, buf))
6464
++remove;
65-
else if (!lstrcmpiW(L"cut", buf) || !lstrcmpiW(L"copy", buf) || !lstrcmpiW(L"link", buf))
65+
else if (!lstrcmpiW(L"cut", buf) || !lstrcmpiW(L"paste", buf) || !lstrcmpiW(L"pastelink", buf) ||
66+
!lstrcmpiW(L"delete", buf) || !lstrcmpiW(L"link", buf))
6667
++remove;
6768

6869
if (remove && DeleteMenu(hMenu, i, MF_BYPOSITION))
@@ -133,10 +134,11 @@ DoShellContextMenu(HWND hwnd, IContextMenu *pCM, PCWSTR File, LPARAM lParam)
133134
HRESULT
134135
GetUIObjectOfPath(HWND hwnd, PCWSTR File, REFIID riid, void **ppv)
135136
{
136-
HRESULT hr;
137+
HRESULT hr = HRESULT_FROM_WIN32(ERROR_FILE_NOT_FOUND);
137138
IShellFolder *pSF;
138139
PCUITEMID_CHILD pidlItem;
139140
PIDLIST_ABSOLUTE pidl = ILCreateFromPath(File);
141+
*ppv = NULL;
140142
if (pidl && SUCCEEDED(SHBindToParent(pidl, IID_PPV_ARG(IShellFolder, &pSF), &pidlItem)))
141143
{
142144
hr = IShellFolder_GetUIObjectOf(pSF, hwnd, 1, &pidlItem, riid, NULL, ppv);
@@ -241,8 +243,14 @@ ShellExecuteVerb(HWND hwnd, PCWSTR Verb, PCWSTR File, BOOL Quit)
241243
}
242244
}
243245

246+
UINT
247+
ErrorBox(HWND hwnd, UINT Error)
248+
{
249+
return SHELL_ErrorBox(hwnd, Error);
250+
}
251+
244252
void
245253
DisplayHelp(HWND hwnd)
246254
{
247-
SHELL_ErrorBox(hwnd, ERROR_NOT_SUPPORTED);
255+
ErrorBox(hwnd, ERROR_NOT_SUPPORTED);
248256
}

0 commit comments

Comments
 (0)