Commit 87b81de0 authored by Francois Boisvert's avatar Francois Boisvert Committed by Alexandre Julliard

Implemented the Win95 file open/save dialogs.

parent 4d088fa9
......@@ -13,6 +13,8 @@ C_SRCS = \
cdlg32.c \
colordlg.c \
filedlg.c \
filedlg95.c \
filedlgbrowser.c \
finddlg.c \
finddlg32.c \
filetitle.c \
......
......@@ -36,5 +36,16 @@ typedef struct {
} user_fr;
} COMDLG32_FR_Data;
#include "commctrl.h"
extern HDPA (WINAPI* COMDLG32_DPA_Create) (INT);
extern LPVOID (WINAPI* COMDLG32_DPA_GetPtr) (const HDPA, INT);
extern LPVOID (WINAPI* COMDLG32_DPA_DeleteAllPtrs) (const HDPA hdpa);
extern LPVOID (WINAPI* COMDLG32_DPA_DeletePtr) (const HDPA hdpa, INT i);
extern INT (WINAPI* COMDLG32_DPA_InsertPtr) (const HDPA, INT, LPVOID);
extern BOOL (WINAPI* COMDLG32_DPA_Destroy) (const HDPA);
extern HICON (WINAPI* COMDLG32_ImageList_GetIcon) (HIMAGELIST, INT, UINT);
extern HIMAGELIST (WINAPI *COMDLG32_ImageList_LoadImageA) (HINSTANCE, LPCSTR, INT, INT, COLORREF, UINT, UINT);
extern BOOL (WINAPI* COMDLG32_ImageList_Draw) (HIMAGELIST himl, int i, HDC hdcDest, int x, int y, UINT fStyle);
#endif
......@@ -21,6 +21,18 @@ HINSTANCE16 COMDLG32_hInstance16 = 0;
static DWORD COMDLG32_TlsIndex;
static int COMDLG32_Attach = 0;
HINSTANCE COMCTL32_hInstance = 0;
HDPA (WINAPI* COMDLG32_DPA_Create) (INT);
LPVOID (WINAPI* COMDLG32_DPA_GetPtr) (const HDPA, INT);
LPVOID (WINAPI* COMDLG32_DPA_DeletePtr) (const HDPA hdpa, INT i);
LPVOID (WINAPI* COMDLG32_DPA_DeleteAllPtrs) (const HDPA hdpa);
INT (WINAPI* COMDLG32_DPA_InsertPtr) (const HDPA, INT, LPVOID);
BOOL (WINAPI* COMDLG32_DPA_Destroy) (const HDPA);
HICON (WINAPI* COMDLG32_ImageList_GetIcon) (HIMAGELIST, INT, UINT);
HIMAGELIST (WINAPI *COMDLG32_ImageList_LoadImageA) (HINSTANCE, LPCSTR, INT, INT, COLORREF, UINT, UINT);
BOOL (WINAPI* COMDLG32_ImageList_Draw) (HIMAGELIST himl, int i, HDC hdcDest, int x, int y, UINT fStyle);
/***********************************************************************
* COMDLG32_DllEntryPoint (COMDLG32.entry)
*
......@@ -66,6 +78,19 @@ BOOL WINAPI COMDLG32_DllEntryPoint(HINSTANCE hInstance, DWORD Reason, LPVOID Res
ERR("No space for COMDLG32 TLS\n");
return FALSE;
}
COMCTL32_hInstance = LoadLibraryA("COMCTL32.DLL");
COMDLG32_DPA_Create=(void*)GetProcAddress(COMCTL32_hInstance, (LPCSTR)328L);
COMDLG32_DPA_Destroy=(void*)GetProcAddress(COMCTL32_hInstance, (LPCSTR)329L);
COMDLG32_DPA_GetPtr=(void*)GetProcAddress(COMCTL32_hInstance, (LPCSTR)332L);
COMDLG32_DPA_InsertPtr=(void*)GetProcAddress(COMCTL32_hInstance, (LPCSTR)334L);
COMDLG32_DPA_DeletePtr=(void*)GetProcAddress(COMCTL32_hInstance, (LPCSTR)336L);
COMDLG32_DPA_DeleteAllPtrs=(void*)GetProcAddress(COMCTL32_hInstance, (LPCSTR)337L);
COMDLG32_ImageList_GetIcon=(void*)GetProcAddress(COMCTL32_hInstance,"ImageList_GetIcon");
COMDLG32_ImageList_LoadImageA=(void*)GetProcAddress(COMCTL32_hInstance,"ImageList_LoadImageA");
COMDLG32_ImageList_Draw=(void*)GetProcAddress(COMCTL32_hInstance,"ImageList_Draw");
break;
case DLL_PROCESS_DETACH:
......@@ -75,6 +100,8 @@ BOOL WINAPI COMDLG32_DllEntryPoint(HINSTANCE hInstance, DWORD Reason, LPVOID Res
COMDLG32_hInstance = 0;
if(COMDLG32_hInstance16)
FreeLibrary16(COMDLG32_hInstance16);
FreeLibrary(COMCTL32_hInstance);
}
break;
}
......
......@@ -195,7 +195,6 @@ FONT 8, "Helv"
}
PRINT32 DIALOG LOADONCALL MOVEABLE DISCARDABLE 32, 32, 288, 186
STYLE DS_MODALFRAME | WS_POPUP | WS_VISIBLE | WS_CAPTION | WS_SYSMENU |
DS_CONTEXTHELP | DS_3DLOOK
......@@ -236,3 +235,124 @@ FONT 8, "Helv"
RTEXT "&to:", stc3, 100,124, 16,8
}
IDD_OPENDIALOG DIALOG LOADONCALL MOVEABLE DISCARDABLE 0, 0, 280, 159
STYLE DS_MODALFRAME | DS_CONTEXTHELP | WS_POPUP | WS_CAPTION | WS_SYSMENU
CAPTION "Open"
FONT 8, "helv"
{
DEFPUSHBUTTON "&Open", IDOK,219,111,50,14
PUSHBUTTON "Cancel", IDCANCEL,219,128,50,14
CONTROL "Open as &read-only",IDC_OPENREADONLY,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,54,145,109,9
COMBOBOX IDC_FILETYPE,54,128,157,102,CBS_DROPDOWN | WS_VSCROLL | WS_TABSTOP
EDITTEXT IDC_FILENAME,54,110,158,15,ES_AUTOHSCROLL
LTEXT "File &name:",IDC_FILENAMESTATIC,3,111,36,10
LTEXT "Files of &type",IDC_FILETYPESTATIC,3,128,41,10
LTEXT "", IDC_SHELLSTATIC,3,21,273,84,SS_SUNKEN | NOT WS_VISIBLE | NOT WS_GROUP |WS_EX_TRANSPARENT
LTEXT "Look &in",IDC_LOOKINSTATIC,3,5,29,10
COMBOBOX IDC_LOOKIN,50,1,137,93,CBS_DROPDOWNLIST | CBS_OWNERDRAWFIXED | CBS_HASSTRINGS | WS_VSCROLL | WS_TABSTOP
PUSHBUTTON "Up",IDC_UPFOLDER,194,1,15,15,BS_ICON | BS_CENTER | BS_VCENTER
PUSHBUTTON "New",IDC_NEWFOLDER,213,1,15,15,BS_ICON | BS_CENTER | BS_VCENTER
CONTROL "I",IDC_LIST,"Button",BS_AUTORADIOBUTTON | BS_ICON | BS_CENTER | BS_VCENTER | BS_PUSHLIKE,233,1,15,15
CONTROL "L",IDC_DETAILS,"Button",BS_AUTORADIOBUTTON | BS_ICON | BS_CENTER | BS_VCENTER | BS_PUSHLIKE,249,1,15,15
}
IDD_SAVEDIALOG DIALOG LOADONCALL MOVEABLE DISCARDABLE 0, 0, 280, 159
STYLE DS_MODALFRAME | DS_CONTEXTHELP | WS_POPUP | WS_CAPTION | WS_SYSMENU
CAPTION "Save As"
FONT 8, "helv"
{
DEFPUSHBUTTON "&Save", IDOK,219,111,50,14
PUSHBUTTON "Cancel", IDCANCEL,219,128,50,14
CONTROL "Open as &read-only",IDC_OPENREADONLY,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,54,145,109,9
COMBOBOX IDC_FILETYPE,54,128,157,102,CBS_DROPDOWN | WS_VSCROLL | WS_TABSTOP
EDITTEXT IDC_FILENAME,54,110,158,15,ES_AUTOHSCROLL
LTEXT "File &name:",IDC_FILENAMESTATIC,3,111,36,10
LTEXT "Save as &type",IDC_FILETYPESTATIC,3,128,41,10
LTEXT "", IDC_SHELLSTATIC,3,21,273,84,SS_SUNKEN | NOT WS_VISIBLE | NOT WS_GROUP |WS_EX_TRANSPARENT
LTEXT "Save &in",IDC_LOOKINSTATIC,3,5,29,10
COMBOBOX IDC_LOOKIN,50,1,137,93,CBS_DROPDOWNLIST | CBS_OWNERDRAWFIXED | CBS_HASSTRINGS | WS_VSCROLL | WS_TABSTOP
PUSHBUTTON "Up",IDC_UPFOLDER,194,1,15,15,BS_ICON | BS_CENTER | BS_VCENTER
PUSHBUTTON "New",IDC_NEWFOLDER,213,1,15,15,BS_ICON | BS_CENTER | BS_VCENTER
CONTROL "I",IDC_LIST,"Button",BS_AUTORADIOBUTTON | BS_ICON | BS_CENTER | BS_VCENTER | BS_PUSHLIKE,233,1,15,15
CONTROL "L",IDC_DETAILS,"Button",BS_AUTORADIOBUTTON | BS_ICON | BS_CENTER | BS_VCENTER | BS_PUSHLIKE,249,1,15,15
}
STRINGTABLE DISCARDABLE
{
IDS_ABOUTBOX "&About FolderPicker Test"
IDS_DOCUMENTFOLDERS "Document Folders"
IDS_PERSONAL "My Documents"
IDS_FAVORITES "My Favorites"
IDS_PATH "System Path"
IDS_DESKTOP "Desktop"
IDS_FONTS "Fonts"
IDS_MYCOMPUTER "My Computer"
}
STRINGTABLE DISCARDABLE
{
IDS_SYSTEMFOLDERS "System Folders"
IDS_LOCALHARDRIVES "Local Hard Drives"
IDS_FILENOTFOUND "File not found"
IDS_VERIFYFILE "Please verify if the correct file name was given"
IDS_CREATEFILE "File does not exist\nDo you want to create file"
}
/******************
* Bitmap
*/
IDB_TOOLBAR BITMAP DISCARDABLE
{'
42 4d b6 02 00 00 00 00 00 00 76 00 00 00 28 00
00 00 41 00 00 00 10 00 00 00 01 00 04 00 00 00
00 00 40 02 00 00 00 00 00 00 00 00 00 00 00 00
00 00 00 00 00 00 00 00 00 00 00 00 80 00 00 80
00 00 00 80 80 00 80 00 00 00 80 00 80 00 80 80
00 00 c0 c0 c0 00 80 80 80 00 00 00 ff 00 00 ff
00 00 00 ff ff 00 ff 00 00 00 ff 00 ff 00 ff ff
00 00 ff ff ff 00 aa aa aa aa aa aa aa aa aa aa
aa aa aa aa aa aa aa aa aa aa aa aa aa aa aa aa
aa aa aa aa aa aa a3 00 b6 01 aa aa aa 88 88 8a
aa aa 00 00 00 00 00 0a aa aa 44 4a aa aa aa aa
aa aa 88 80 00 0f 00 0f 00 0f ab 00 db 02 aa aa
a0 00 00 8a aa aa 0b bb bb bb bb 0a aa aa 4f 4a
00 0a aa aa aa aa f7 8f ff ff ff ff ff ff a9 02
2a 02 aa aa a0 77 70 8a aa aa 0b bb bb bb bb 9a
aa aa 44 aa aa aa aa aa aa aa f7 80 00 0f 00 0f
00 0f a2 00 02 00 aa aa a0 77 70 8a aa aa 0b bb
bb bb bb 9a aa aa aa aa aa aa aa aa aa aa f7 8f
ff ff ff ff ff ff a4 f8 15 00 aa aa a0 77 70 8a
aa aa 0b bb bb b9 bb 9a a9 aa aa aa aa aa aa aa
aa aa f7 80 00 0f 00 0f 00 0f a2 00 02 00 aa aa
a0 77 70 8a aa aa 0b bb bb bb 9b 9a 9a aa 44 4a
aa aa 44 4a aa aa f7 8f ff ff ff ff ff ff a0 00
ad 00 aa aa a0 77 70 8a aa aa 0b bb bb bb b9 99
aa aa 4f 4a 00 0a 4f 4a 00 0a f7 80 00 0f 00 0f
00 0f a1 00 b5 00 aa aa a0 77 70 88 8a aa 00 00
00 99 99 99 99 9a 44 aa aa aa 44 aa aa aa f7 8f
ff ff ff ff ff ff ad 01 0b 02 aa 00 00 77 70 00
0a aa a0 bb bb 0a a9 99 aa aa aa aa aa aa aa aa
aa aa f7 80 00 0f 00 0f 00 0f a9 01 5d 01 aa a0
f7 77 77 70 aa aa aa 00 00 aa 9a 9a 9a aa aa aa
aa aa aa aa aa aa f7 8f ff ff ff ff ff ff a0 01
63 01 aa aa 0f 77 77 0a aa aa aa aa aa a9 aa 9a
a9 aa 44 4a aa aa 44 4a aa aa 88 88 88 88 88 88
88 88 ab 01 0f 01 aa aa a0 f7 70 aa aa aa aa aa
aa aa aa 9a aa aa 4f 4a 00 0a 4f 4a 00 0a f7 8f
77 78 f7 78 f7 78 a8 01 7d 01 aa aa aa 0f 0a aa
aa aa aa aa aa aa aa 9a aa aa 44 aa aa aa 44 aa
aa aa f7 8f 77 78 f7 78 f7 78 ae 01 62 02 aa aa
aa a0 aa aa aa aa aa aa aa aa aa 9a aa aa aa aa
aa aa aa aa aa aa ff ff ff ff ff ff ff f7 a2 01
b9 01 aa aa aa aa aa aa aa aa aa aa aa aa aa aa
aa aa aa aa aa aa aa aa aa aa aa aa aa aa aa aa
aa aa a2 00 43 02'}
......@@ -4,7 +4,6 @@
* Copyright 1994 Martin Ayotte
* Copyright 1996 Albrecht Kleine
*/
#include <ctype.h>
#include <stdlib.h>
#include <string.h>
......@@ -22,6 +21,7 @@
#include "debugtools.h"
#include "winproc.h"
#include "cderr.h"
#include "tweak.h"
DEFAULT_DEBUG_CHANNEL(commdlg)
......@@ -39,6 +39,11 @@ static int fldrWidth = 0;
static const char defaultfilter[]=" \0\0";
/***********************************************************************
*
* Windows 3.1 OpenFileName/SaveFileName dialog
*
*/
/***********************************************************************
* FileDlg_Init [internal]
*/
static BOOL FileDlg_Init(void)
......@@ -1033,9 +1038,8 @@ static LRESULT FILEDLG_WMCommand(HWND16 hWnd, WPARAM16 wParam, LPARAM lParam)
return FALSE;
}
/***********************************************************************
* FileOpenDlgProc (COMMDLG.6)
* FileOpenDlgProc16 (COMMDLG.6)
*/
LRESULT WINAPI FileOpenDlgProc16(HWND16 hWnd, UINT16 wMsg, WPARAM16 wParam,
LPARAM lParam)
......@@ -1077,9 +1081,8 @@ LRESULT WINAPI FileOpenDlgProc16(HWND16 hWnd, UINT16 wMsg, WPARAM16 wParam,
return FALSE;
}
/***********************************************************************
* FileSaveDlgProc (COMMDLG.7)
* FileSaveDlgProc16 (COMMDLG.7)
*/
LRESULT WINAPI FileSaveDlgProc16(HWND16 hWnd, UINT16 wMsg, WPARAM16 wParam,
LPARAM lParam)
......@@ -1125,8 +1128,6 @@ LRESULT WINAPI FileSaveDlgProc16(HWND16 hWnd, UINT16 wMsg, WPARAM16 wParam,
return FALSE;
}
static BOOL Commdlg_GetFileNameA( BOOL16 (CALLBACK *dofunction)(SEGPTR x),
LPOPENFILENAMEA ofn )
{
......@@ -1352,7 +1353,6 @@ static BOOL Commdlg_GetFileNameW( BOOL16 (CALLBACK *dofunction)(SEGPTR x),
SEGPTR_FREE(ofn16);
return ret;
}
/***********************************************************************
* GetOpenFileNameA (COMDLG32.10)
*
......@@ -1369,9 +1369,16 @@ BOOL WINAPI GetOpenFileNameA(
LPOPENFILENAMEA ofn /* address of init structure */
)
{
if(TWEAK_WineLook > WIN31_LOOK)
{
return GetFileDialog95A(ofn, OPEN_DIALOG);
}
else
{
BOOL16 (CALLBACK * dofunction)(SEGPTR ofn16) = GetOpenFileName16;
return Commdlg_GetFileNameA(dofunction,ofn);
}
}
/***********************************************************************
* GetOpenFileNameW (COMDLG32.11)
......@@ -1389,9 +1396,16 @@ BOOL WINAPI GetOpenFileNameW(
LPOPENFILENAMEW ofn /* address of init structure */
)
{
if(TWEAK_WineLook > WIN31_LOOK)
{
return GetFileDialog95W(ofn, OPEN_DIALOG);
}
else
{
BOOL16 (CALLBACK * dofunction)(SEGPTR ofn16) = GetOpenFileName16;
return Commdlg_GetFileNameW(dofunction,ofn);
}
}
/***********************************************************************
* GetSaveFileNameA (COMDLG32.12)
......@@ -1409,10 +1423,18 @@ BOOL WINAPI GetSaveFileNameA(
LPOPENFILENAMEA ofn /* address of init structure */
)
{
if(TWEAK_WineLook > WIN31_LOOK)
{
return GetFileDialog95A(ofn, SAVE_DIALOG);
}
else
{
BOOL16 (CALLBACK * dofunction)(SEGPTR ofn16) = GetSaveFileName16;
return Commdlg_GetFileNameA(dofunction,ofn);
}
}
/***********************************************************************
* GetSaveFileNameW (COMDLG32.13)
*
......@@ -1429,7 +1451,14 @@ BOOL WINAPI GetSaveFileNameW(
LPOPENFILENAMEW ofn /* address of init structure */
)
{
if(TWEAK_WineLook > WIN31_LOOK)
{
return GetFileDialog95W(ofn, SAVE_DIALOG);
}
else
{
BOOL16 (CALLBACK * dofunction)(SEGPTR ofn16) = GetSaveFileName16;
return Commdlg_GetFileNameW(dofunction,ofn);
}
}
/*
* COMMDLG - File Open Dialogs Win95 look and feel
*
*/
#include <ctype.h>
#include <stdlib.h>
#include <string.h>
#include "winbase.h"
#include "ldt.h"
#include "heap.h"
#include "commdlg.h"
#include "dlgs.h"
#include "debugtools.h"
#include "cderr.h"
#include "tweak.h"
#include "winnls.h"
#include "shellapi.h"
#include "commctrl.h"
#include "tchar.h"
#include "filedlgbrowser.h"
#include "wine/undocshell.h"
#include "wine/obj_contextmenu.h"
DEFAULT_DEBUG_CHANNEL(commdlg)
#include "cdlg.h"
/***********************************************************************
* Data structure and global variables
*/
typedef struct SFolder
{
int m_iImageIndex; /* Index of picture in image list */
HIMAGELIST hImgList;
int m_iIndent; /* Indentation index */
LPITEMIDLIST pidlItem; /* absolute pidl of the item */
} SFOLDER,*LPSFOLDER;
typedef struct tagLookInInfo
{
int iMaxIndentation;
UINT uSelectedItem;
} LookInInfos;
/***********************************************************************
* Defines and global variables
*/
/* Draw item constant */
#define ICONWIDTH 18
#define YTEXTOFFSET 2
#define XTEXTOFFSET 3
/* AddItem flags*/
#define LISTEND -1
/* SearchItem methods */
#define SEARCH_PIDL 1
#define SEARCH_EXP 2
#define ITEM_NOTFOUND -1
/* Undefined windows message sent by CreateViewObject*/
#define WM_GETISHELLBROWSER WM_USER+7
/* NOTE
* Those macros exist in windowsx.h. However, you can't really use them since
* they rely on the UNICODE defines and can't be use inside Wine itself.
*/
/* Combo box macros */
#define CBAddString(hwnd,str) \
SendMessageA(hwnd,CB_ADDSTRING,0,(LPARAM)str);
#define CBInsertString(hwnd,str,pos) \
SendMessageA(hwnd,CB_INSERTSTRING,(WPARAM)pos,(LPARAM)str);
#define CBDeleteString(hwnd,pos) \
SendMessageA(hwnd,CB_DELETESTRING,(WPARAM)pos,0);
#define CBSetItemDataPtr(hwnd,iItemId,dataPtr) \
SendMessageA(hwnd,CB_SETITEMDATA,(WPARAM)iItemId,(LPARAM)dataPtr);
#define CBGetItemDataPtr(hwnd,iItemId) \
SendMessageA(hwnd,CB_GETITEMDATA,(WPARAM)iItemId,0)
#define CBGetLBText(hwnd,iItemId,str) \
SendMessageA(hwnd,CB_GETLBTEXT,(WPARAM)iItemId,(LPARAM)str);
#define CBGetCurSel(hwnd) \
SendMessageA(hwnd,CB_GETCURSEL,0,0);
#define CBSetCurSel(hwnd,pos) \
SendMessageA(hwnd,CB_SETCURSEL,(WPARAM)pos,0);
#define CBGetCount(hwnd) \
SendMessageA(hwnd,CB_GETCOUNT,0,0);
#define CBShowDropDown(hwnd,show) \
SendMessageA(hwnd,CB_SHOWDROPDOWN,(WPARAM)show,0);
const char *FileOpenDlgInfosStr = "FileOpenDlgInfos"; /* windows property description string */
const char *LookInInfosStr = "LookInInfos"; /* LOOKIN combo box property */
static const char defaultFilter[] = "*.*";
/***********************************************************************
* Prototypes
*/
/* Internal functions used by the dialog */
static LRESULT FILEDLG95_OnWMInitDialog(HWND hwnd, WPARAM wParam, LPARAM lParam);
static LRESULT FILEDLG95_OnWMCommand(HWND hwnd, WPARAM wParam, LPARAM lParam);
static LRESULT FILEDLG95_OnWMGetIShellBrowser(HWND hwnd);
BOOL FILEDLG95_OnOpen(HWND hwnd);
static LRESULT FILEDLG95_InitUI(HWND hwnd);
static void FILEDLG95_Clean(HWND hwnd);
/* Functions used by the shell object */
static LRESULT FILEDLG95_SHELL_Init(HWND hwnd);
static BOOL FILEDLG95_SHELL_UpFolder(HWND hwnd);
static BOOL FILEDLG95_SHELL_ExecuteCommand(HWND hwnd, LPCSTR lpVerb);
static BOOL FILEDLG95_SHELL_NewFolder(HWND hwnd);
BOOL FILEDLG95_SHELL_FillIncludedItemList(HWND hwnd,
LPITEMIDLIST pidlCurrentFolder,
LPSTR lpstrMask);
static void FILEDLG95_SHELL_Clean(HWND hwnd);
/* Functions used by the filetype combo box */
static HRESULT FILEDLG95_FILETYPE_Init(HWND hwnd);
static BOOL FILEDLG95_FILETYPE_OnCommand(HWND hwnd, WORD wNotifyCode);
static int FILEDLG95_FILETYPE_SearchExt(HWND hwnd,LPSTR lpstrExt);
static void FILEDLG95_FILETYPE_Clean(HWND hwnd);
/* Functions used by the Look In combo box */
static HRESULT FILEDLG95_LOOKIN_Init(HWND hwndCombo);
static LRESULT FILEDLG95_LOOKIN_DrawItem(LPDRAWITEMSTRUCT pDIStruct);
static BOOL FILEDLG95_LOOKIN_OnCommand(HWND hwnd, WORD wNotifyCode);
static int FILEDLG95_LOOKIN_AddItem(HWND hwnd,LPITEMIDLIST pidl, int iInsertId);
static int FILEDLG95_LOOKIN_SearchItem(HWND hwnd,WPARAM searchArg,int iSearchMethod);
static int FILEDLG95_LOOKIN_InsertItemAfterParent(HWND hwnd,LPITEMIDLIST pidl);
static int FILEDLG95_LOOKIN_RemoveMostExpandedItem(HWND hwnd);
int FILEDLG95_LOOKIN_SelectItem(HWND hwnd,LPITEMIDLIST pidl);
static void FILEDLG95_LOOKIN_Clean(HWND hwnd);
/* Miscellaneous tool functions */
HRESULT GetName(LPSHELLFOLDER lpsf, LPITEMIDLIST pidl,DWORD dwFlags,LPSTR lpstrFileName);
HRESULT GetFileName(HWND hwnd, LPITEMIDLIST pidl, LPSTR lpstrFileName);
IShellFolder* GetShellFolderFromPidl(LPITEMIDLIST pidlAbs);
LPITEMIDLIST GetParentPidl(LPITEMIDLIST pidl);
LPITEMIDLIST GetPidlFromName(IShellFolder *psf,LPCSTR lpcstrFileName);
/* Shell memory allocation */
void *MemAlloc(UINT size);
void MemFree(void *mem);
BOOL WINAPI GetOpenFileName95(FileOpenDlgInfos *fodInfos);
BOOL WINAPI GetSaveFileName95(FileOpenDlgInfos *fodInfos);
HRESULT WINAPI FileOpenDlgProc95(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
/***********************************************************************
* GetOpenFileName95
*
* Creates an Open common dialog box that lets the user select
* the drive, directory, and the name of a file or set of files to open.
*
* IN : The FileOpenDlgInfos structure associated with the dialog
* OUT : TRUE on success
* FALSE on cancel, error, close or filename-does-not-fit-in-buffer.
*/
BOOL WINAPI GetOpenFileName95(FileOpenDlgInfos *fodInfos)
{
LRESULT lRes;
LPCVOID template;
HRSRC hRes;
HANDLE hDlgTmpl = 0;
/* Create the dialog from a template */
if (fodInfos->ofnInfos.Flags & OFN_ENABLETEMPLATEHANDLE)
{
if (!(template = LockResource( MapHModuleSL(fodInfos->ofnInfos.hInstance ))))
{
COMDLG32_SetCommDlgExtendedError(CDERR_LOADRESFAILURE);
return FALSE;
}
}
else if (fodInfos->ofnInfos.Flags & OFN_ENABLETEMPLATE)
{
if (!(hRes = FindResourceA(MapHModuleSL(fodInfos->ofnInfos.hInstance),
(fodInfos->ofnInfos.lpTemplateName), RT_DIALOGA)))
{
COMDLG32_SetCommDlgExtendedError(CDERR_FINDRESFAILURE);
return FALSE;
}
if (!(hDlgTmpl = LoadResource( MapHModuleSL(fodInfos->ofnInfos.hInstance),
hRes )) ||
!(template = LockResource( hDlgTmpl )))
{
COMDLG32_SetCommDlgExtendedError(CDERR_LOADRESFAILURE);
return FALSE;
}
}
else
{
if(!(hRes = FindResourceA(COMMDLG_hInstance32,MAKEINTRESOURCEA(IDD_OPENDIALOG),RT_DIALOGA)))
{
COMDLG32_SetCommDlgExtendedError(CDERR_FINDRESFAILURE);
return FALSE;
}
if (!(hDlgTmpl = LoadResource(COMMDLG_hInstance32, hRes )) ||
!(template = LockResource( hDlgTmpl )))
{
COMDLG32_SetCommDlgExtendedError(CDERR_LOADRESFAILURE);
return FALSE;
}
}
lRes = DialogBoxIndirectParamA(COMMDLG_hInstance32,
(LPDLGTEMPLATEA) template,
fodInfos->ofnInfos.hwndOwner,
(DLGPROC) FileOpenDlgProc95,
(LPARAM) fodInfos);
/* Unable to create the dialog*/
if( lRes == -1)
return FALSE;
return lRes;
}
/***********************************************************************
* GetSaveFileName95
*
* Creates an Save as common dialog box that lets the user select
* the drive, directory, and the name of a file or set of files to open.
*
* IN : The FileOpenDlgInfos structure associated with the dialog
* OUT : TRUE on success
* FALSE on cancel, error, close or filename-does-not-fit-in-buffer.
*/
BOOL WINAPI GetSaveFileName95(FileOpenDlgInfos *fodInfos)
{
LRESULT lRes;
LPCVOID template;
HRSRC hRes;
HANDLE hDlgTmpl = 0;
/* Create the dialog from a template */
if (fodInfos->ofnInfos.Flags & OFN_ENABLETEMPLATEHANDLE)
{
if (!(template = LockResource( MapHModuleSL(fodInfos->ofnInfos.hInstance ))))
{
COMDLG32_SetCommDlgExtendedError(CDERR_LOADRESFAILURE);
return FALSE;
}
}
else if (fodInfos->ofnInfos.Flags & OFN_ENABLETEMPLATE)
{
if (!(hRes = FindResourceA(MapHModuleSL(fodInfos->ofnInfos.hInstance),
(fodInfos->ofnInfos.lpTemplateName), RT_DIALOGA)))
{
COMDLG32_SetCommDlgExtendedError(CDERR_FINDRESFAILURE);
return FALSE;
}
if (!(hDlgTmpl = LoadResource( MapHModuleSL(fodInfos->ofnInfos.hInstance),
hRes )) ||
!(template = LockResource( hDlgTmpl )))
{
COMDLG32_SetCommDlgExtendedError(CDERR_LOADRESFAILURE);
return FALSE;
}
}
else
{
if(!(hRes = FindResourceA(COMMDLG_hInstance32,MAKEINTRESOURCEA(IDD_SAVEDIALOG),RT_DIALOGA)))
{
COMDLG32_SetCommDlgExtendedError(CDERR_FINDRESFAILURE);
return FALSE;
}
if (!(hDlgTmpl = LoadResource(COMMDLG_hInstance32, hRes )) ||
!(template = LockResource( hDlgTmpl )))
{
COMDLG32_SetCommDlgExtendedError(CDERR_LOADRESFAILURE);
return FALSE;
}
}
lRes = DialogBoxIndirectParamA(COMMDLG_hInstance32,
(LPDLGTEMPLATEA) template,
fodInfos->ofnInfos.hwndOwner,
(DLGPROC) FileOpenDlgProc95,
(LPARAM) fodInfos);
/* Unable to create the dialog*/
if( lRes == -1)
return FALSE;
return lRes;
}
/***********************************************************************
* GetFileDialog95A
*
* Copy the OPENFILENAMEA structure in a FileOpenDlgInfos structure.
* Call GetOpenFileName95 with this structure and clean the memory.
*
* IN : The OPENFILENAMEA initialisation structure passed to
* GetOpenFileNameA win api function (see filedlg.c)
*/
BOOL WINAPI GetFileDialog95A(LPOPENFILENAMEA ofn,UINT iDlgType)
{
BOOL ret;
FileOpenDlgInfos *fodInfos;
/* Initialise FileOpenDlgInfos structure*/
fodInfos = (FileOpenDlgInfos*)MemAlloc(sizeof(FileOpenDlgInfos));
memset(&fodInfos->ofnInfos,'\0',sizeof(*ofn)); fodInfos->ofnInfos.lStructSize = sizeof(*ofn);
fodInfos->ofnInfos.hwndOwner = ofn->hwndOwner;
fodInfos->ofnInfos.hInstance = MapHModuleLS(ofn->hInstance);
if (ofn->lpstrFilter)
{
LPSTR s,x;
/* filter is a list... title\0ext\0......\0\0 */
s = (LPSTR)ofn->lpstrFilter;
while (*s)
s = s+strlen(s)+1;
s++;
x = (LPSTR)MemAlloc(s-ofn->lpstrFilter);
memcpy(x,ofn->lpstrFilter,s-ofn->lpstrFilter);
fodInfos->ofnInfos.lpstrFilter = (LPSTR)x;
}
if (ofn->lpstrCustomFilter)
{
LPSTR s,x;
/* filter is a list... title\0ext\0......\0\0 */
s = (LPSTR)ofn->lpstrCustomFilter;
while (*s)
s = s+strlen(s)+1;
s++;
x = MemAlloc(s-ofn->lpstrCustomFilter);
memcpy(x,ofn->lpstrCustomFilter,s-ofn->lpstrCustomFilter);
fodInfos->ofnInfos.lpstrCustomFilter = (LPSTR)x;
}
fodInfos->ofnInfos.nMaxCustFilter = ofn->nMaxCustFilter;
if(ofn->nFilterIndex)
fodInfos->ofnInfos.nFilterIndex = --ofn->nFilterIndex;
if (ofn->nMaxFile)
{
fodInfos->ofnInfos.lpstrFile = (LPSTR)MemAlloc(ofn->nMaxFile);
strcpy((LPSTR)fodInfos->ofnInfos.lpstrFile,ofn->lpstrFile);
}
fodInfos->ofnInfos.nMaxFile = ofn->nMaxFile;
fodInfos->ofnInfos.nMaxFileTitle = ofn->nMaxFileTitle;
if (fodInfos->ofnInfos.nMaxFileTitle)
fodInfos->ofnInfos.lpstrFileTitle = (LPSTR)MemAlloc(ofn->nMaxFileTitle);
if (ofn->lpstrInitialDir)
{
fodInfos->ofnInfos.lpstrInitialDir = (LPSTR)MemAlloc(strlen(ofn->lpstrInitialDir));
strcpy((LPSTR)fodInfos->ofnInfos.lpstrInitialDir,ofn->lpstrInitialDir);
}
if (ofn->lpstrTitle)
{
fodInfos->ofnInfos.lpstrTitle = (LPSTR)MemAlloc(strlen(ofn->lpstrTitle));
strcpy((LPSTR)fodInfos->ofnInfos.lpstrTitle,ofn->lpstrTitle);
}
fodInfos->ofnInfos.Flags = ofn->Flags|OFN_WINE;
fodInfos->ofnInfos.nFileOffset = ofn->nFileOffset;
fodInfos->ofnInfos.nFileExtension = ofn->nFileExtension;
if (ofn->lpstrDefExt)
{
fodInfos->ofnInfos.lpstrDefExt = MemAlloc(strlen(ofn->lpstrDefExt));
strcpy((LPSTR)fodInfos->ofnInfos.lpstrDefExt,ofn->lpstrDefExt);
}
fodInfos->ofnInfos.lCustData = ofn->lCustData;
fodInfos->ofnInfos.lpfnHook = (LPOFNHOOKPROC)ofn->lpfnHook;
if (ofn->lpTemplateName)
{
/* template don't work - using normal dialog */
/* fodInfos->ofnInfos.lpTemplateName = MemAlloc(strlen(ofn->lpTemplateName));
strcpy((LPSTR)fodInfos->ofnInfos.lpTemplateName,ofn->lpTemplateName);*/
fodInfos->ofnInfos.Flags &= ~OFN_ENABLETEMPLATEHANDLE;
fodInfos->ofnInfos.Flags &= ~OFN_ENABLETEMPLATE;
FIXME("File dialog 95 template not implemented\n");
}
/* Replace the NULL lpstrInitialDir by the current folder */
if(!ofn->lpstrInitialDir)
{
fodInfos->ofnInfos.lpstrInitialDir = MemAlloc(MAX_PATH);
GetCurrentDirectoryA(MAX_PATH,(LPSTR)fodInfos->ofnInfos.lpstrInitialDir);
}
switch(iDlgType)
{
case OPEN_DIALOG :
ret = GetOpenFileName95(fodInfos);
break;
case SAVE_DIALOG :
ret = GetSaveFileName95(fodInfos);
break;
default :
ret = 0;
}
ofn->nFileOffset = fodInfos->ofnInfos.nFileOffset;
ofn->nFileExtension = fodInfos->ofnInfos.nFileExtension;
if (fodInfos->ofnInfos.lpstrFilter)
MemFree((LPVOID)(fodInfos->ofnInfos.lpstrFilter));
if (fodInfos->ofnInfos.lpTemplateName)
MemFree((LPVOID)(fodInfos->ofnInfos.lpTemplateName));
if (fodInfos->ofnInfos.lpstrDefExt)
MemFree((LPVOID)(fodInfos->ofnInfos.lpstrDefExt));
if (fodInfos->ofnInfos.lpstrTitle)
MemFree((LPVOID)(fodInfos->ofnInfos.lpstrTitle));
if (fodInfos->ofnInfos.lpstrInitialDir)
MemFree((LPVOID)(fodInfos->ofnInfos.lpstrInitialDir));
if (fodInfos->ofnInfos.lpstrCustomFilter)
MemFree((LPVOID)(fodInfos->ofnInfos.lpstrCustomFilter));
if (fodInfos->ofnInfos.lpstrFile)
{
strcpy(ofn->lpstrFile,fodInfos->ofnInfos.lpstrFile);
MemFree((LPVOID)fodInfos->ofnInfos.lpstrFile);
}
if (fodInfos->ofnInfos.lpstrFileTitle)
{
if (ofn->lpstrFileTitle)
strcpy(ofn->lpstrFileTitle,
fodInfos->ofnInfos.lpstrFileTitle);
MemFree((LPVOID)fodInfos->ofnInfos.lpstrFileTitle);
}
MemFree((LPVOID)(fodInfos));
return ret;
}
/***********************************************************************
* GetFileDialog95W
*
* Copy the OPENFILENAMEW structure in a FileOpenDlgInfos structure.
* Call GetOpenFileName95 with this structure and clean the memory.
*
* IN : The OPENFILENAMEW initialisation structure passed to
* GetOpenFileNameW win api function (see filedlg.c)
*/
BOOL WINAPI GetFileDialog95W(LPOPENFILENAMEW ofn,UINT iDlgType)
{
BOOL ret;
FileOpenDlgInfos *fodInfos;
/* Initialise FileOpenDlgInfos structure*/
fodInfos = (FileOpenDlgInfos*)MemAlloc(sizeof(FileOpenDlgInfos));
memset(&fodInfos->ofnInfos,'\0',sizeof(*ofn));
fodInfos->ofnInfos.lStructSize = sizeof(*ofn);
fodInfos->ofnInfos.hwndOwner = ofn->hwndOwner;
fodInfos->ofnInfos.hInstance = MapHModuleLS(ofn->hInstance);
if (ofn->lpstrFilter)
{
LPWSTR s;
LPSTR x,y;
int n;
/* filter is a list... title\0ext\0......\0\0 */
s = (LPWSTR)ofn->lpstrFilter;
while (*s)
s = s+lstrlenW(s)+1;
s++;
n = s - ofn->lpstrFilter; /* already divides by 2. ptr magic */
x = y = (LPSTR)MemAlloc(n);
s = (LPWSTR)ofn->lpstrFilter;
while (*s) {
lstrcpyWtoA(x,s);
x+=lstrlenA(x)+1;
s+=lstrlenW(s)+1;
}
*x=0;
fodInfos->ofnInfos.lpstrFilter = (LPSTR)y;
}
if (ofn->lpstrCustomFilter) {
LPWSTR s;
LPSTR x,y;
int n;
/* filter is a list... title\0ext\0......\0\0 */
s = (LPWSTR)ofn->lpstrCustomFilter;
while (*s)
s = s+lstrlenW(s)+1;
s++;
n = s - ofn->lpstrCustomFilter;
x = y = (LPSTR)MemAlloc(n);
s = (LPWSTR)ofn->lpstrCustomFilter;
while (*s) {
lstrcpyWtoA(x,s);
x+=lstrlenA(x)+1;
s+=lstrlenW(s)+1;
}
*x=0;
fodInfos->ofnInfos.lpstrCustomFilter = (LPSTR)y;
}
fodInfos->ofnInfos.nMaxCustFilter = ofn->nMaxCustFilter;
fodInfos->ofnInfos.nFilterIndex = ofn->nFilterIndex;
if (ofn->nMaxFile)
fodInfos->ofnInfos.lpstrFile = (LPSTR)MemAlloc(ofn->nMaxFile);
fodInfos->ofnInfos.nMaxFile = ofn->nMaxFile;
fodInfos->ofnInfos.nMaxFileTitle = ofn->nMaxFileTitle;
if (ofn->nMaxFileTitle)
fodInfos->ofnInfos.lpstrFileTitle = (LPSTR)MemAlloc(ofn->nMaxFileTitle);
if (ofn->lpstrInitialDir)
fodInfos->ofnInfos.lpstrInitialDir = (LPSTR)MemAlloc(lstrlenW(ofn->lpstrInitialDir));
if (ofn->lpstrTitle)
fodInfos->ofnInfos.lpstrTitle = (LPSTR)MemAlloc(lstrlenW(ofn->lpstrTitle));
fodInfos->ofnInfos.Flags = ofn->Flags|OFN_WINE|OFN_UNICODE;
fodInfos->ofnInfos.nFileOffset = ofn->nFileOffset;
fodInfos->ofnInfos.nFileExtension = ofn->nFileExtension;
if (ofn->lpstrDefExt)
fodInfos->ofnInfos.lpstrDefExt = (LPSTR)MemAlloc(lstrlenW(ofn->lpstrDefExt));
fodInfos->ofnInfos.lCustData = ofn->lCustData;
fodInfos->ofnInfos.lpfnHook = (LPOFNHOOKPROC)ofn->lpfnHook;
if (ofn->lpTemplateName)
fodInfos->ofnInfos.lpTemplateName = (LPSTR)MemAlloc(lstrlenW(ofn->lpTemplateName));
switch(iDlgType)
{
case OPEN_DIALOG :
ret = GetOpenFileName95(fodInfos);
break;
case SAVE_DIALOG :
ret = GetSaveFileName95(fodInfos);
break;
default :
ret = 0;
}
/* Cleaning */
ofn->nFileOffset = fodInfos->ofnInfos.nFileOffset;
ofn->nFileExtension = fodInfos->ofnInfos.nFileExtension;
if (fodInfos->ofnInfos.lpstrFilter)
MemFree((LPVOID)(fodInfos->ofnInfos.lpstrFilter));
if (fodInfos->ofnInfos.lpTemplateName)
MemFree((LPVOID)(fodInfos->ofnInfos.lpTemplateName));
if (fodInfos->ofnInfos.lpstrDefExt)
MemFree((LPVOID)(fodInfos->ofnInfos.lpstrDefExt));
if (fodInfos->ofnInfos.lpstrTitle)
MemFree((LPVOID)(fodInfos->ofnInfos.lpstrTitle));
if (fodInfos->ofnInfos.lpstrInitialDir)
MemFree((LPVOID)(fodInfos->ofnInfos.lpstrInitialDir));
if (fodInfos->ofnInfos.lpstrCustomFilter)
MemFree((LPVOID)(fodInfos->ofnInfos.lpstrCustomFilter));
if (fodInfos->ofnInfos.lpstrFile) {
lstrcpyAtoW(ofn->lpstrFile,(fodInfos->ofnInfos.lpstrFile));
MemFree((LPVOID)(fodInfos->ofnInfos.lpstrFile));
}
if (fodInfos->ofnInfos.lpstrFileTitle) {
if (ofn->lpstrFileTitle)
lstrcpyAtoW(ofn->lpstrFileTitle,
(fodInfos->ofnInfos.lpstrFileTitle));
MemFree((LPVOID)(fodInfos->ofnInfos.lpstrFileTitle));
}
MemFree((LPVOID)(fodInfos));
return ret;
}
/***********************************************************************
* FileOpenDlgProc95
*
* File open dialog procedure
*/
HRESULT WINAPI FileOpenDlgProc95(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
switch(uMsg)
{
case WM_INITDIALOG :
return FILEDLG95_OnWMInitDialog(hwnd, wParam, lParam);
case WM_COMMAND:
return FILEDLG95_OnWMCommand(hwnd, wParam, lParam);
case WM_DRAWITEM:
{
switch(((LPDRAWITEMSTRUCT)lParam)->CtlID)
{
case IDC_LOOKIN:
FILEDLG95_LOOKIN_DrawItem((LPDRAWITEMSTRUCT) lParam);
return TRUE;
}
}
return FALSE;
case WM_GETISHELLBROWSER:
return FILEDLG95_OnWMGetIShellBrowser(hwnd);
case WM_DESTROY:
RemovePropA(hwnd, FileOpenDlgInfosStr);
default :
return FALSE;
}
}
/***********************************************************************
* FILEDLG95_OnWMInitDialog
*
* WM_INITDIALOG message handler
*/
static LRESULT FILEDLG95_OnWMInitDialog(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
LPITEMIDLIST pidlItemId;
FileOpenDlgInfos *fodInfos = (FileOpenDlgInfos *) lParam;
TRACE("\n");
/* Adds the FileOpenDlgInfos in the property list of the dialog
so it will be easily accessible through a GetPropA(...) */
SetPropA(hwnd, FileOpenDlgInfosStr, (HANDLE) fodInfos);
/* Make sure the common control DLL is loaded */
InitCommonControls();
/* Initialise shell objects */
FILEDLG95_SHELL_Init(hwnd);
/* Initialise dialog UI */
FILEDLG95_InitUI(hwnd);
/* Initialize the Look In combo box*/
FILEDLG95_LOOKIN_Init(fodInfos->DlgInfos.hwndLookInCB);
/* Initialize the filter combo box */
FILEDLG95_FILETYPE_Init(hwnd);
/* Get the initial directory pidl */
if(!(pidlItemId = GetPidlFromName(fodInfos->Shell.FOIShellFolder,fodInfos->ofnInfos.lpstrInitialDir)))
{
char path[MAX_PATH];
GetCurrentDirectoryA(MAX_PATH,path);
pidlItemId = GetPidlFromName(fodInfos->Shell.FOIShellFolder,
path);
}
/* Browse to the initial directory */
IShellBrowser_BrowseObject(fodInfos->Shell.FOIShellBrowser,pidlItemId,SBSP_RELATIVE);
/* Free pidlItem memory */
SHFree(pidlItemId);
return TRUE;
}
/***********************************************************************
* FILEDLG95_Clean
*
* Regroups all the cleaning functions of the filedlg
*/
void FILEDLG95_Clean(HWND hwnd)
{
FILEDLG95_FILETYPE_Clean(hwnd);
FILEDLG95_LOOKIN_Clean(hwnd);
FILEDLG95_SHELL_Clean(hwnd);
}
/***********************************************************************
* FILEDLG95_OnWMCommand
*
* WM_COMMAND message handler
*/
static LRESULT FILEDLG95_OnWMCommand(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
WORD wNotifyCode = HIWORD(wParam); // notification code
WORD wID = LOWORD(wParam); // item, control, or accelerator identifier
switch(wID)
{
/* OK button */
case IDOK:
FILEDLG95_OnOpen(hwnd);
break;
/* Cancel button */
case IDCANCEL:
FILEDLG95_Clean(hwnd);
EndDialog(hwnd, FALSE);
break;
/* Filetype combo box */
case IDC_FILETYPE:
FILEDLG95_FILETYPE_OnCommand(hwnd,wNotifyCode);
break;
/* LookIn combo box */
case IDC_LOOKIN:
FILEDLG95_LOOKIN_OnCommand(hwnd,wNotifyCode);
break;
/* Up folder button */
case IDC_UPFOLDER:
FILEDLG95_SHELL_UpFolder(hwnd);
break;
/* List option button */
case IDC_LIST:
FILEDLG95_SHELL_ExecuteCommand(hwnd,CMDSTR_VIEWLIST);
break;
/* Details option button */
case IDC_DETAILS:
FILEDLG95_SHELL_ExecuteCommand(hwnd,CMDSTR_VIEWDETAILS);
break;
/* New folder button */
case IDC_NEWFOLDER:
FILEDLG95_SHELL_NewFolder(hwnd);
break;
case IDC_FILENAME:
break;
}
return 0;
}
/***********************************************************************
* FILEDLG95_OnWMGetIShellBrowser
*
* WM_GETISHELLBROWSER message handler
*/
static LRESULT FILEDLG95_OnWMGetIShellBrowser(HWND hwnd)
{
FileOpenDlgInfos *fodInfos = (FileOpenDlgInfos *) GetPropA(hwnd,FileOpenDlgInfosStr);
TRACE("\n");
SetWindowLongA(hwnd,DWL_MSGRESULT,(LONG)fodInfos->Shell.FOIShellBrowser);
return TRUE;
}
/***********************************************************************
* FILEDLG95_InitUI
*
*/
static LRESULT FILEDLG95_InitUI(HWND hwnd)
{
HIMAGELIST himlToolbar;
HICON hicon;
FileOpenDlgInfos *fodInfos = (FileOpenDlgInfos *) GetPropA(hwnd,FileOpenDlgInfosStr);
TRACE("%p\n", fodInfos);
/* Get the hwnd of the controls */
fodInfos->DlgInfos.hwndFileName = GetDlgItem(hwnd,IDC_FILENAME);
fodInfos->DlgInfos.hwndFileTypeCB = GetDlgItem(hwnd,IDC_FILETYPE);
fodInfos->DlgInfos.hwndLookInCB = GetDlgItem(hwnd,IDC_LOOKIN);
ShowWindow(GetDlgItem(hwnd,IDC_SHELLSTATIC),SW_HIDE);
/* Load the icons bitmaps */
if((himlToolbar = COMDLG32_ImageList_LoadImageA(COMMDLG_hInstance32,
MAKEINTRESOURCEA(IDB_TOOLBAR),
0,
1,
CLR_DEFAULT,
IMAGE_BITMAP,
0)))
{
/* Up folder icon */
if((hicon = COMDLG32_ImageList_GetIcon(himlToolbar,0,ILD_NORMAL)))
SendDlgItemMessageA(hwnd,IDC_UPFOLDER,BM_SETIMAGE,(WPARAM)IMAGE_ICON,(LPARAM)hicon);
/* New folder icon */
if((hicon = COMDLG32_ImageList_GetIcon(himlToolbar,1,ILD_NORMAL)))
SendDlgItemMessageA(hwnd,IDC_NEWFOLDER,BM_SETIMAGE,(WPARAM)IMAGE_ICON,(LPARAM)hicon);
/* List view icon */
if((hicon = COMDLG32_ImageList_GetIcon(himlToolbar,2,ILD_NORMAL)))
SendDlgItemMessageA(hwnd,IDC_LIST,BM_SETIMAGE,(WPARAM)IMAGE_ICON,(LPARAM)hicon);
/* Detail view icon */
if((hicon = COMDLG32_ImageList_GetIcon(himlToolbar,3,ILD_NORMAL)))
SendDlgItemMessageA(hwnd,IDC_DETAILS,BM_SETIMAGE,(WPARAM)IMAGE_ICON,(LPARAM)hicon);
}
/* Set the window text with the text specified in the OPENFILENAME structure */
if(fodInfos->ofnInfos.lpstrTitle)
SetWindowTextA(hwnd,fodInfos->ofnInfos.lpstrTitle);
/* Initialise the file name edit control */
if(strlen(fodInfos->ofnInfos.lpstrFile))
{
SetDlgItemTextA(hwnd,IDC_FILENAME,fodInfos->ofnInfos.lpstrFile);
}
/* Must the open as read only check box be checked ?*/
if(fodInfos->ofnInfos.Flags & OFN_READONLY)
{
SendDlgItemMessageA(hwnd,IDC_OPENREADONLY,BM_SETCHECK,(WPARAM)TRUE,0);
}
/* Must the open as read only check box be hid ?*/
if(fodInfos->ofnInfos.Flags & OFN_HIDEREADONLY)
{
ShowWindow(GetDlgItem(hwnd,IDC_OPENREADONLY),SW_HIDE);
}
return 0;
}
/***********************************************************************
* FILEDLG95_OnOpen
*
* Ok button WM_COMMAND message handler
*
* If the function succeeds, the return value is nonzero.
*/
BOOL FILEDLG95_OnOpen(HWND hwnd)
{
char lpstrFileName[MAX_PATH];
FileOpenDlgInfos *fodInfos = (FileOpenDlgInfos *) GetPropA(hwnd,FileOpenDlgInfosStr);
TRACE("\n");
if(GetDlgItemTextA(hwnd,IDC_FILENAME,lpstrFileName,MAX_PATH))
{
char *tmp;
char lpstrFile[MAX_PATH];
/* Get the selected file name and path */
SHGetPathFromIDListA(fodInfos->ShellInfos.pidlAbsCurrent,
lpstrFile);
if(strcmp(&lpstrFile[strlen(lpstrFile)-1],"\\"))
strcat(lpstrFile,"\\");
strcat(lpstrFile,lpstrFileName);
/* Check if this is a search */
if(strchr(lpstrFileName,'*') || strchr(lpstrFileName,'?'))
{
int iPos;
/* Set the current filter with the current selection */
if(fodInfos->ShellInfos.lpstrCurrentFilter)
MemFree((LPVOID)fodInfos->ShellInfos.lpstrCurrentFilter);
fodInfos->ShellInfos.lpstrCurrentFilter = MemAlloc((strlen(lpstrFileName)+1)*2);
lstrcpyAtoW(fodInfos->ShellInfos.lpstrCurrentFilter,(LPSTR)strlwr((LPSTR)lpstrFileName));
IShellView_Refresh(fodInfos->Shell.FOIShellView);
if(-1 < (iPos = FILEDLG95_FILETYPE_SearchExt(fodInfos->DlgInfos.hwndFileTypeCB,lpstrFileName)))
CBSetCurSel(fodInfos->DlgInfos.hwndFileTypeCB,iPos);
return FALSE;
}
/* Check file extension */
if(!strrchr(lpstrFile,'.'))
{
/* if the file has no extension, append the selected
extension of the filetype combo box */
int iExt;
LPSTR lpstrExt;
LPSTR lpstrTmp;
iExt = CBGetCurSel(fodInfos->DlgInfos.hwndFileTypeCB);
lpstrTmp = (LPSTR) CBGetItemDataPtr(fodInfos->DlgInfos.hwndFileTypeCB,iExt);
if((lpstrExt = strchr(lpstrTmp,';')))
{
int i = lpstrExt - lpstrTmp;
lpstrExt = MemAlloc(i);
strncpy(lpstrExt,&lpstrTmp[1],i-1);
}
else
{
lpstrExt = MemAlloc(strlen(lpstrTmp)-1);
strcpy(lpstrExt,&lpstrTmp[1]);
}
if(!strcmp(&lpstrExt[1],"*") && fodInfos->ofnInfos.lpstrDefExt)
{
lpstrExt = MemAlloc(strlen(fodInfos->ofnInfos.lpstrDefExt)+1);
strcat(lpstrExt,".");
strcat(lpstrExt,(LPSTR) fodInfos->ofnInfos.lpstrDefExt);
}
strcat(lpstrFile,lpstrExt);
}
/* Check if the selected file exist */
if(strlen(lpstrFile) > fodInfos->ofnInfos.nMaxFile)
{
/* set error FNERR_BUFFERTOSMALL */
FILEDLG95_Clean(hwnd);
return EndDialog(hwnd,FALSE);
}
strcpy(fodInfos->ofnInfos.lpstrFile,lpstrFile);
/* Set the lpstrFileTitle of the OPENFILENAME structure */
if(fodInfos->ofnInfos.lpstrFileTitle)
strncpy(fodInfos->ofnInfos.lpstrFileTitle,
lpstrFileName,
fodInfos->ofnInfos.nMaxFileTitle);
/* Check if the file is to be opened as read only */
if(BST_CHECKED == SendDlgItemMessageA(hwnd,IDC_OPENREADONLY,BM_GETSTATE,0,0))
SetFileAttributesA(fodInfos->ofnInfos.lpstrFile,FILE_ATTRIBUTE_READONLY);
/* nFileExtension and nFileOffset of OPENFILENAME structure */
tmp = strrchr(fodInfos->ofnInfos.lpstrFile,'\\');
fodInfos->ofnInfos.nFileOffset = tmp - fodInfos->ofnInfos.lpstrFile + 1;
tmp = strrchr(fodInfos->ofnInfos.lpstrFile,'.');
fodInfos->ofnInfos.nFileExtension = tmp - fodInfos->ofnInfos.lpstrFile + 1;
/* Check if selected file exists */
if(!GetPidlFromName(fodInfos->Shell.FOIShellFolder, lpstrFileName))
{
/* Tell the user the selected does not exist */
if(fodInfos->ofnInfos.Flags & OFN_FILEMUSTEXIST)
{
char lpstrNotFound[100];
char lpstrMsg[100];
char tmp[400];
LoadStringA(COMMDLG_hInstance32,IDS_FILENOTFOUND,lpstrNotFound,100);
LoadStringA(COMMDLG_hInstance32,IDS_VERIFYFILE,lpstrMsg,100);
strcpy(tmp,fodInfos->ofnInfos.lpstrFile);
strcat(tmp,"\n");
strcat(tmp,lpstrNotFound);
strcat(tmp,"\n");
strcat(tmp,lpstrMsg);
MessageBoxA(hwnd,tmp,fodInfos->ofnInfos.lpstrTitle,MB_OK | MB_ICONEXCLAMATION);
return FALSE;
}
/* Ask the user if he wants to create the file*/
if(fodInfos->ofnInfos.Flags & OFN_CREATEPROMPT)
{
char tmp[100];
LoadStringA(COMMDLG_hInstance32,IDS_CREATEFILE,tmp,100);
if(IDYES == MessageBoxA(hwnd,tmp,fodInfos->ofnInfos.lpstrTitle,MB_YESNO | MB_ICONQUESTION))
{
/* Create the file, clean and exit */
FILEDLG95_Clean(hwnd);
return EndDialog(hwnd,TRUE);
}
return FALSE;
}
}
/* clean and exit */
FILEDLG95_Clean(hwnd);
return EndDialog(hwnd,TRUE);
}
return FALSE;
}
/***********************************************************************
* FILEDLG95_SHELL_Init
*
* Initialisation of the shell objects
*/
static HRESULT FILEDLG95_SHELL_Init(HWND hwnd)
{
FileOpenDlgInfos *fodInfos = (FileOpenDlgInfos *) GetPropA(hwnd,FileOpenDlgInfosStr);
TRACE("\n");
/*
* Initialisation of the FileOpenDialogInfos structure
*/
/* Shell */
fodInfos->Shell.FOIShellView = NULL;
if(FAILED(SHGetDesktopFolder(&fodInfos->Shell.FOIShellFolder)))
return E_FAIL;
/*ShellInfos */
fodInfos->ShellInfos.hwndOwner = hwnd;
fodInfos->ShellInfos.folderSettings.fFlags = FWF_AUTOARRANGE | FWF_ALIGNLEFT;
fodInfos->ShellInfos.folderSettings.ViewMode = FVM_LIST;
GetWindowRect(GetDlgItem(hwnd,IDC_SHELLSTATIC),&fodInfos->ShellInfos.rectView);
ScreenToClient(hwnd,(LPPOINT)&fodInfos->ShellInfos.rectView.left);
ScreenToClient(hwnd,(LPPOINT)&fodInfos->ShellInfos.rectView.right);
/* Construct the IShellBrowser interface */
fodInfos->Shell.FOIShellBrowser = IShellBrowserImpl_Construct(hwnd);
return NOERROR;
}
/***********************************************************************
* FILEDLG95_SHELL_ExecuteCommand
*
* Change the folder option and refresh the view
* If the function succeeds, the return value is nonzero.
*/
static BOOL FILEDLG95_SHELL_ExecuteCommand(HWND hwnd, LPCSTR lpVerb)
{
FileOpenDlgInfos *fodInfos = (FileOpenDlgInfos *) GetPropA(hwnd,FileOpenDlgInfosStr);
IContextMenu * pcm;
CMINVOKECOMMANDINFO ci;
TRACE("\n");
if(SUCCEEDED(IShellView_GetItemObject(fodInfos->Shell.FOIShellView,
SVGIO_BACKGROUND,
&IID_IContextMenu,
(LPVOID*)&pcm)))
{
ci.cbSize = sizeof(CMINVOKECOMMANDINFO);
ci.lpVerb = lpVerb;
ci.hwnd = hwnd;
IContextMenu_InvokeCommand(pcm, &ci);
IContextMenu_Release(pcm);
}
return FALSE;
}
/***********************************************************************
* FILEDLG95_SHELL_UpFolder
*
* Browse to the specified object
* If the function succeeds, the return value is nonzero.
*/
static BOOL FILEDLG95_SHELL_UpFolder(HWND hwnd)
{
FileOpenDlgInfos *fodInfos = (FileOpenDlgInfos *) GetPropA(hwnd,FileOpenDlgInfosStr);
TRACE("\n");
if(SUCCEEDED(IShellBrowser_BrowseObject(fodInfos->Shell.FOIShellBrowser,
NULL,
SBSP_PARENT)))
{
return TRUE;
}
return FALSE;
}
/***********************************************************************
* FILEDLG95_SHELL_NewFolder
*
* Creates a new directory with New folder as name
* If the function succeeds, the return value is nonzero.
* FIXME: let the contextmenu (CMDSTR_NEWFOLDER) do this thing
*/
static BOOL FILEDLG95_SHELL_NewFolder(HWND hwnd)
{
char lpstrDirName[MAX_PATH] = "New folder";
BOOL bRes;
FileOpenDlgInfos *fodInfos = (FileOpenDlgInfos *) GetPropA(hwnd,FileOpenDlgInfosStr);
TRACE("\n");
if((bRes = CreateDirectoryA(lpstrDirName,NULL)))
{
LPITEMIDLIST pidl = GetPidlFromName(fodInfos->Shell.FOIShellFolder,lpstrDirName);
IShellView_Refresh(fodInfos->Shell.FOIShellView);
IShellView_SelectItem(fodInfos->Shell.FOIShellView,
pidl,
(SVSI_DESELECTOTHERS | SVSI_EDIT | SVSI_ENSUREVISIBLE
|SVSI_FOCUSED|SVSI_SELECT));
}
return bRes;
}
/***********************************************************************
* FILEDLG95_SHELL_Clean
*
* Cleans the memory used by shell objects
*/
static void FILEDLG95_SHELL_Clean(HWND hwnd)
{
FileOpenDlgInfos *fodInfos = (FileOpenDlgInfos *) GetPropA(hwnd,FileOpenDlgInfosStr);
TRACE("\n");
/* clean Shell interfaces */
IShellView_DestroyViewWindow(fodInfos->Shell.FOIShellView);
IShellView_Release(fodInfos->Shell.FOIShellView);
IShellFolder_Release(fodInfos->Shell.FOIShellFolder);
IShellBrowser_Release(fodInfos->Shell.FOIShellBrowser);
}
/***********************************************************************
* FILEDLG95_FILETYPE_Init
*
* Initialisation of the file type combo box
*/
static HRESULT FILEDLG95_FILETYPE_Init(HWND hwnd)
{
FileOpenDlgInfos *fodInfos = (FileOpenDlgInfos *) GetPropA(hwnd,FileOpenDlgInfosStr);
TRACE("\n");
if(fodInfos->ofnInfos.lpstrFilter)
{
int iStrIndex = 0;
int iPos = 0;
LPSTR lpstrFilter;
LPSTR lpstrTmp;
for(;;)
{
/* filter is a list... title\0ext\0......\0\0 */
/* Set the combo item text to the title and the item data
to the ext */
char *lpstrExt = NULL;
LPSTR lpstrExtTmp = NULL;
/* Get the title */
lpstrTmp = (&((LPBYTE)fodInfos->ofnInfos.lpstrFilter)[iStrIndex]);
if(!strlen(lpstrTmp))
break;
iStrIndex += strlen(lpstrTmp) +1;
/* Get the extension */
lpstrExtTmp = (&((LPBYTE)fodInfos->ofnInfos.lpstrFilter)[iStrIndex]);
if(!lpstrExtTmp)
break;
lpstrExt = (LPSTR) MemAlloc(strlen(lpstrExtTmp));
if(!lpstrExt)
break;
strcpy(lpstrExt,lpstrExtTmp);
iStrIndex += strlen(lpstrExt) +1;
/* Add the item at the end of the combo */
CBAddString(fodInfos->DlgInfos.hwndFileTypeCB,lpstrTmp);
CBSetItemDataPtr(fodInfos->DlgInfos.hwndFileTypeCB,iPos++,lpstrExt);
}
/* Set the current filter to the one specified
in the initialisation structure */
CBSetCurSel(fodInfos->DlgInfos.hwndFileTypeCB,
fodInfos->ofnInfos.nFilterIndex);
lpstrFilter = (LPSTR) CBGetItemDataPtr(fodInfos->DlgInfos.hwndFileTypeCB,
fodInfos->ofnInfos.nFilterIndex);
if(lpstrFilter)
{
fodInfos->ShellInfos.lpstrCurrentFilter = MemAlloc((strlen(lpstrFilter)+1)*2);
lstrcpyAtoW(fodInfos->ShellInfos.lpstrCurrentFilter,strlwr(lpstrFilter));
}
}
return NOERROR;
}
/***********************************************************************
* FILEDLG95_FILETYPE_OnCommand
*
* WM_COMMAND of the file type combo box
* If the function succeeds, the return value is nonzero.
*/
static BOOL FILEDLG95_FILETYPE_OnCommand(HWND hwnd, WORD wNotifyCode)
{
FileOpenDlgInfos *fodInfos = (FileOpenDlgInfos *) GetPropA(hwnd,FileOpenDlgInfosStr);
switch(wNotifyCode)
{
case CBN_CLOSEUP:
{
LPSTR lpstrFilter;
/* Get the current item of the filetype combo box */
int iItem = CBGetCurSel(fodInfos->DlgInfos.hwndFileTypeCB);
/* Set the current filter with the current selection */
if(fodInfos->ShellInfos.lpstrCurrentFilter)
MemFree((LPVOID)fodInfos->ShellInfos.lpstrCurrentFilter);
lpstrFilter = (LPSTR) CBGetItemDataPtr(fodInfos->DlgInfos.hwndFileTypeCB,
iItem);
if(lpstrFilter)
{
fodInfos->ShellInfos.lpstrCurrentFilter = MemAlloc((strlen(lpstrFilter)+1)*2);
lstrcpyAtoW(fodInfos->ShellInfos.lpstrCurrentFilter,(LPSTR)strlwr((LPSTR)lpstrFilter));
}
/* Refresh the actual view to display the included items*/
IShellView_Refresh(fodInfos->Shell.FOIShellView);
}
}
return FALSE;
}
/***********************************************************************
* FILEDLG95_FILETYPE_SearchExt
*
* Search for pidl in the lookin combo box
* returns the index of the found item
*/
static int FILEDLG95_FILETYPE_SearchExt(HWND hwnd,LPSTR lpstrExt)
{
int i = 0;
int iCount = CBGetCount(hwnd);
TRACE("\n");
for(;i<iCount;i++)
{
LPSTR ext = (LPSTR) CBGetItemDataPtr(hwnd,i);
if(!_stricmp(lpstrExt,ext))
return i;
}
return -1;
}
/***********************************************************************
* FILEDLG95_FILETYPE_Clean
*
* Clean the memory used by the filetype combo box
*/
static void FILEDLG95_FILETYPE_Clean(HWND hwnd)
{
FileOpenDlgInfos *fodInfos = (FileOpenDlgInfos *) GetPropA(hwnd,FileOpenDlgInfosStr);
int iPos;
int iCount = CBGetCount(fodInfos->DlgInfos.hwndFileTypeCB);
TRACE("\n");
/* Delete each string of the combo and their associated data */
for(iPos = iCount-1;iPos>=0;iPos--)
{
MemFree((LPVOID)(CBGetItemDataPtr(fodInfos->DlgInfos.hwndFileTypeCB,iPos)));
CBDeleteString(fodInfos->DlgInfos.hwndFileTypeCB,iPos);
}
/* Current filter */
if(fodInfos->ShellInfos.lpstrCurrentFilter)
MemFree((LPVOID)fodInfos->ShellInfos.lpstrCurrentFilter);
}
/***********************************************************************
* FILEDLG95_LOOKIN_Init
*
* Initialisation of the look in combo box
*/
static HRESULT FILEDLG95_LOOKIN_Init(HWND hwndCombo)
{
IShellFolder *psfRoot, *psfDrives;
IEnumIDList *lpeRoot, *lpeDrives;
LPITEMIDLIST pidlDrives, pidlTmp, pidlTmp1, pidlAbsTmp;
LookInInfos *liInfos = MemAlloc(sizeof(LookInInfos));
TRACE("\n");
liInfos->iMaxIndentation = 0;
SetPropA(hwndCombo, LookInInfosStr, (HANDLE) liInfos);
/* Initialise data of Desktop folder */
SHGetSpecialFolderLocation(0,CSIDL_DESKTOP,&pidlTmp);
FILEDLG95_LOOKIN_AddItem(hwndCombo, pidlTmp,LISTEND);
SHFree(pidlTmp);
SHGetSpecialFolderLocation(0,CSIDL_DRIVES,&pidlDrives);
SHGetDesktopFolder(&psfRoot);
if (psfRoot)
{
/* enumerate the contents of the desktop */
if(SUCCEEDED(IShellFolder_EnumObjects(psfRoot, hwndCombo, SHCONTF_FOLDERS, &lpeRoot)))
{
while (S_OK == IEnumIDList_Next(lpeRoot, 1, &pidlTmp, NULL))
{
FILEDLG95_LOOKIN_AddItem(hwndCombo, pidlTmp,LISTEND);
/* special handling for CSIDL_DRIVES */
if (ILIsEqual(pidlTmp, pidlDrives))
{
if(SUCCEEDED(IShellFolder_BindToObject(psfRoot, pidlTmp, NULL, &IID_IShellFolder, (LPVOID*)&psfDrives)))
{
/* enumerate the drives */
if(SUCCEEDED(IShellFolder_EnumObjects(psfDrives, hwndCombo,SHCONTF_FOLDERS, &lpeDrives)))
{
while (S_OK == IEnumIDList_Next(lpeDrives, 1, &pidlTmp1, NULL))
{
pidlAbsTmp = ILCombine(pidlTmp, pidlTmp1);
FILEDLG95_LOOKIN_AddItem(hwndCombo, pidlAbsTmp,LISTEND);
SHFree(pidlAbsTmp);
SHFree(pidlTmp1);
}
IEnumIDList_Release(lpeDrives);
}
IShellFolder_Release(psfDrives);
}
}
SHFree(pidlTmp);
}
IEnumIDList_Release(lpeRoot);
}
}
IShellFolder_Release(psfRoot);
SHFree(pidlDrives);
return NOERROR;
}
/***********************************************************************
* FILEDLG95_LOOKIN_DrawItem
*
* WM_DRAWITEM message handler
*/
static LRESULT FILEDLG95_LOOKIN_DrawItem(LPDRAWITEMSTRUCT pDIStruct)
{
COLORREF crWin = GetSysColor(COLOR_WINDOW);
COLORREF crHighLight = GetSysColor(COLOR_HIGHLIGHT);
COLORREF crText = GetSysColor(COLOR_WINDOWTEXT);
RECT rectText;
RECT rectIcon;
SHFILEINFOA sfi;
HIMAGELIST ilItemImage;
int iIndentation;
LPSFOLDER tmpFolder;
LookInInfos *liInfos = (LookInInfos *)GetPropA(pDIStruct->hwndItem,LookInInfosStr);
TRACE("\n");
if(pDIStruct->itemID == -1)
return 0;
if(!(tmpFolder = (LPSFOLDER) CBGetItemDataPtr(pDIStruct->hwndItem,
pDIStruct->itemID)))
return 0;
if(pDIStruct->itemID == liInfos->uSelectedItem)
{
ilItemImage = (HIMAGELIST) SHGetFileInfoA ((LPCSTR) tmpFolder->pidlItem,
0,
&sfi,
sizeof (SHFILEINFOA),
SHGFI_PIDL | SHGFI_SMALLICON |
SHGFI_OPENICON | SHGFI_SYSICONINDEX |
SHGFI_DISPLAYNAME );
}
else
{
ilItemImage = (HIMAGELIST) SHGetFileInfoA ((LPCSTR) tmpFolder->pidlItem,
0,
&sfi,
sizeof (SHFILEINFOA),
SHGFI_PIDL | SHGFI_SMALLICON |
SHGFI_SYSICONINDEX |
SHGFI_DISPLAYNAME);
}
/* Is this item selected ?*/
if(pDIStruct->itemState & ODS_SELECTED)
{
SetTextColor(pDIStruct->hDC,(0x00FFFFFF & ~(crText)));
SetBkColor(pDIStruct->hDC,crHighLight);
FillRect(pDIStruct->hDC,&pDIStruct->rcItem,(HBRUSH)crHighLight);
}
else
{
SetTextColor(pDIStruct->hDC,crText);
SetBkColor(pDIStruct->hDC,crWin);
FillRect(pDIStruct->hDC,&pDIStruct->rcItem,(HBRUSH)crWin);
}
/* Do not indent item if drawing in the edit of the combo*/
if(pDIStruct->itemState & ODS_COMBOBOXEDIT)
{
iIndentation = 0;
ilItemImage = (HIMAGELIST) SHGetFileInfoA ((LPCSTR) tmpFolder->pidlItem,
0,
&sfi,
sizeof (SHFILEINFOA),
SHGFI_PIDL | SHGFI_SMALLICON | SHGFI_OPENICON
| SHGFI_SYSICONINDEX | SHGFI_DISPLAYNAME );
}
else
{
iIndentation = tmpFolder->m_iIndent;
}
/* Draw text and icon */
/* Initialise the icon display area */
rectIcon.left = pDIStruct->rcItem.left + ICONWIDTH/2 * iIndentation;
rectIcon.top = pDIStruct->rcItem.top;
rectIcon.right = rectIcon.left + ICONWIDTH;
rectIcon.bottom = pDIStruct->rcItem.bottom;
/* Initialise the text display area */
rectText.left = rectIcon.right;
rectText.top = pDIStruct->rcItem.top + YTEXTOFFSET;
rectText.right = pDIStruct->rcItem.right + XTEXTOFFSET;
rectText.bottom = pDIStruct->rcItem.bottom;
/* Draw the icon from the image list */
COMDLG32_ImageList_Draw(ilItemImage,
sfi.iIcon,
pDIStruct->hDC,
rectIcon.left,
rectIcon.top,
ILD_TRANSPARENT );
/* Draw the associated text */
if(sfi.szDisplayName)
TextOutA(pDIStruct->hDC,rectText.left,rectText.top,sfi.szDisplayName,strlen(sfi.szDisplayName));
return NOERROR;
}
/***********************************************************************
* FILEDLG95_LOOKIN_OnCommand
*
* LookIn combo box WM_COMMAND message handler
* If the function succeeds, the return value is nonzero.
*/
static BOOL FILEDLG95_LOOKIN_OnCommand(HWND hwnd, WORD wNotifyCode)
{
FileOpenDlgInfos *fodInfos = (FileOpenDlgInfos *) GetPropA(hwnd,FileOpenDlgInfosStr);
TRACE("\n");
switch(wNotifyCode)
{
case CBN_CLOSEUP:
{
LPSFOLDER tmpFolder;
int iItem;
iItem = CBGetCurSel(fodInfos->DlgInfos.hwndLookInCB);
tmpFolder = (LPSFOLDER) CBGetItemDataPtr(fodInfos->DlgInfos.hwndLookInCB,
iItem);
if(SUCCEEDED(IShellBrowser_BrowseObject(fodInfos->Shell.FOIShellBrowser,
tmpFolder->pidlItem,
SBSP_ABSOLUTE)))
{
return TRUE;
}
break;
}
}
return FALSE;
}
/***********************************************************************
* FILEDLG95_LOOKIN_AddItem
*
* Adds an absolute pidl item to the lookin combo box
* returns the index of the inserted item
*/
static int FILEDLG95_LOOKIN_AddItem(HWND hwnd,LPITEMIDLIST pidl, int iInsertId)
{
LPITEMIDLIST pidlNext;
SHFILEINFOA sfi;
SFOLDER *tmpFolder = MemAlloc(sizeof(SFOLDER));
LookInInfos *liInfos;
TRACE("\n");
if(!(liInfos = (LookInInfos *)GetPropA(hwnd,LookInInfosStr)))
return -1;
tmpFolder->m_iIndent = 0;
if(!pidl)
return -1;
/* Calculate the indentation of the item in the lookin*/
pidlNext = pidl;
while( (pidlNext=ILGetNext(pidlNext)) )
{
tmpFolder->m_iIndent++;
}
tmpFolder->pidlItem = ILClone(pidl);
if(tmpFolder->m_iIndent > liInfos->iMaxIndentation)
liInfos->iMaxIndentation = tmpFolder->m_iIndent;
SHGetFileInfoA((LPSTR)pidl,
0,
&sfi,
sizeof(sfi),
SHGFI_DISPLAYNAME | SHGFI_SYSICONINDEX
| SHGFI_PIDL | SHGFI_SMALLICON | SHGFI_ATTRIBUTES);
if((sfi.dwAttributes & SFGAO_FILESYSANCESTOR) || (sfi.dwAttributes & SFGAO_FILESYSTEM))
{
int iItemID;
/* Add the item at the end of the list */
if(iInsertId < 0)
{
iItemID = CBAddString(hwnd,sfi.szDisplayName);
}
/* Insert the item at the iInsertId position*/
else
{
iItemID = CBInsertString(hwnd,sfi.szDisplayName,iInsertId);
}
CBSetItemDataPtr(hwnd,iItemID,tmpFolder);
return iItemID;
}
return -1;
}
/***********************************************************************
* FILEDLG95_LOOKIN_InsertItemAfterParent
*
* Insert an item below its parent
*/
static int FILEDLG95_LOOKIN_InsertItemAfterParent(HWND hwnd,LPITEMIDLIST pidl)
{
LPITEMIDLIST pidlParent = GetParentPidl(pidl);
int iParentPos;
TRACE("\n");
iParentPos = FILEDLG95_LOOKIN_SearchItem(hwnd,(WPARAM)pidlParent,SEARCH_PIDL);
if(iParentPos < 0)
{
iParentPos = FILEDLG95_LOOKIN_InsertItemAfterParent(hwnd,pidlParent);
}
/* Free pidlParent memory */
SHFree((LPVOID)pidlParent);
return FILEDLG95_LOOKIN_AddItem(hwnd,pidl,iParentPos + 1);
}
/***********************************************************************
* FILEDLG95_LOOKIN_SelectItem
*
* Adds an absolute pidl item to the lookin combo box
* returns the index of the inserted item
*/
int FILEDLG95_LOOKIN_SelectItem(HWND hwnd,LPITEMIDLIST pidl)
{
int iItemPos;
LookInInfos *liInfos;
TRACE("\n");
iItemPos = FILEDLG95_LOOKIN_SearchItem(hwnd,(WPARAM)pidl,SEARCH_PIDL);
liInfos = (LookInInfos *)GetPropA(hwnd,LookInInfosStr);
if(iItemPos < 0)
{
while(FILEDLG95_LOOKIN_RemoveMostExpandedItem(hwnd) > -1);
iItemPos = FILEDLG95_LOOKIN_InsertItemAfterParent(hwnd,pidl);
}
else
{
SFOLDER *tmpFolder = (LPSFOLDER) CBGetItemDataPtr(hwnd,iItemPos);
while(liInfos->iMaxIndentation > tmpFolder->m_iIndent)
{
int iRemovedItem;
if(-1 == (iRemovedItem = FILEDLG95_LOOKIN_RemoveMostExpandedItem(hwnd)))
break;
if(iRemovedItem < iItemPos)
iItemPos--;
}
}
CBSetCurSel(hwnd,iItemPos);
liInfos->uSelectedItem = iItemPos;
return 0;
}
/***********************************************************************
* FILEDLG95_LOOKIN_RemoveMostExpandedItem
*
* Remove the item with an expansion level over iExpansionLevel
*/
static int FILEDLG95_LOOKIN_RemoveMostExpandedItem(HWND hwnd)
{
int iItemPos;
LookInInfos *liInfos = (LookInInfos *)GetPropA(hwnd,LookInInfosStr);
TRACE("\n");
if(liInfos->iMaxIndentation <= 2)
return -1;
if((iItemPos = FILEDLG95_LOOKIN_SearchItem(hwnd,(WPARAM)liInfos->iMaxIndentation,SEARCH_EXP)) >=0)
{
SFOLDER *tmpFolder;
tmpFolder = (LPSFOLDER) CBGetItemDataPtr(hwnd,iItemPos);
CBDeleteString(hwnd,iItemPos);
liInfos->iMaxIndentation--;
return iItemPos;
}
return -1;
}
/***********************************************************************
* FILEDLG95_LOOKIN_SearchItem
*
* Search for pidl in the lookin combo box
* returns the index of the found item
*/
static int FILEDLG95_LOOKIN_SearchItem(HWND hwnd,WPARAM searchArg,int iSearchMethod)
{
int i = 0;
int iCount = CBGetCount(hwnd);
TRACE("\n");
for(;i<iCount;i++)
{
LPSFOLDER tmpFolder = (LPSFOLDER) CBGetItemDataPtr(hwnd,i);
if(iSearchMethod == SEARCH_PIDL && ILIsEqual((LPITEMIDLIST)searchArg,tmpFolder->pidlItem))
return i;
if(iSearchMethod == SEARCH_EXP && tmpFolder->m_iIndent == (int)searchArg)
return i;
}
return -1;
}
/***********************************************************************
* FILEDLG95_LOOKIN_Clean
*
* Clean the memory used by the lookin combo box
*/
static void FILEDLG95_LOOKIN_Clean(HWND hwnd)
{
FileOpenDlgInfos *fodInfos = (FileOpenDlgInfos *) GetPropA(hwnd,FileOpenDlgInfosStr);
int iPos;
int iCount = CBGetCount(fodInfos->DlgInfos.hwndLookInCB);
TRACE("\n");
/* Delete each string of the combo and their associated data */
for(iPos = iCount-1;iPos>=0;iPos--)
{
MemFree((LPVOID)(CBGetItemDataPtr(fodInfos->DlgInfos.hwndLookInCB,iPos)));
CBDeleteString(fodInfos->DlgInfos.hwndLookInCB,iPos);
}
/* LookInInfos structure */
RemovePropA(fodInfos->DlgInfos.hwndLookInCB,LookInInfosStr);
}
/*
* TOOLS
*/
/***********************************************************************
* GetName
*
* Get the pidl's display name (relative to folder) and
* put it in lpstrFileName.
*
* Return NOERROR on success,
* E_FAIL otherwise
*/
HRESULT GetName(LPSHELLFOLDER lpsf, LPITEMIDLIST pidl,DWORD dwFlags,LPSTR lpstrFileName)
{
STRRET str;
HRESULT hRes;
TRACE("%p %p\n", lpsf, pidl);
if(!lpsf)
{
HRESULT hRes;
SHGetDesktopFolder(&lpsf);
hRes = GetName(lpsf,pidl,dwFlags,lpstrFileName);
IShellFolder_Release(lpsf);
return hRes;
}
/* Get the display name of the pidl relative to the folder */
if (SUCCEEDED(hRes = IShellFolder_GetDisplayNameOf(lpsf,
pidl,
dwFlags,
&str)))
{
StrRetToStrN(lpstrFileName, MAX_PATH, &str, pidl);
return NOERROR;
}
return E_FAIL;
}
/***********************************************************************
* GetShellFolderFromPidl
*
* pidlRel is the item pidl relative
* Return the IShellFolder of the absolute pidl
*/
IShellFolder *GetShellFolderFromPidl(LPITEMIDLIST pidlAbs)
{
IShellFolder *psf = NULL,*psfParent;
TRACE("%p\n", pidlAbs);
if(SUCCEEDED(SHGetDesktopFolder(&psfParent)))
{
psf = psfParent;
if(pidlAbs && pidlAbs->mkid.cb)
{
if(FAILED(IShellFolder_BindToObject(psfParent, pidlAbs, NULL, &IID_IShellFolder, (LPVOID*)&psf)))
{
psf = NULL;
}
}
IShellFolder_Release(psfParent);
}
return psf;
}
/***********************************************************************
* GetParentPidl
*
* Return the LPITEMIDLIST to the parent of the pidl in the list
*/
LPITEMIDLIST GetParentPidl(LPITEMIDLIST pidl)
{
LPITEMIDLIST pidlParent;
TRACE("%p\n", pidl);
pidlParent = ILClone(pidl);
ILRemoveLastID(pidlParent);
return pidlParent;
}
/***********************************************************************
* GetPidlFromName
*
* returns the pidl of the file name relative to folder
* NULL if an error occured
*/
LPITEMIDLIST GetPidlFromName(IShellFolder *psf,LPCSTR lpcstrFileName)
{
LPITEMIDLIST pidl;
ULONG ulEaten;
wchar_t lpwstrDirName[MAX_PATH];
if(!lpcstrFileName)
return NULL;
MultiByteToWideChar(CP_ACP,
MB_PRECOMPOSED,
lpcstrFileName,
-1,
(LPWSTR)lpwstrDirName,
MAX_PATH);
if(SUCCEEDED(IShellFolder_ParseDisplayName(psf,
0,
NULL,
(LPWSTR)lpwstrDirName,
&ulEaten,
&pidl,
NULL)))
{
return pidl;
}
return NULL;
}
/***********************************************************************
* GetFileExtension
*
*/
BOOL GetFileExtension(IShellFolder *psf,LPITEMIDLIST pidl,LPSTR lpstrFileExtension)
{
char FileName[MAX_PATH];
int result;
char *pdest;
int ch = '.';
if(SUCCEEDED(GetName(psf,pidl,SHGDN_NORMAL,FileName)))
{
if(!(pdest = strrchr( FileName, ch )))
return FALSE;
result = pdest - FileName + 1;
strcpy(lpstrFileExtension,&FileName[result]);
return TRUE;
}
return FALSE;
}
/*
* Memory allocation methods */
void *MemAlloc(UINT size)
{
return HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,size);
}
void MemFree(void *mem)
{
if(mem)
{
HeapFree(GetProcessHeap(),0,mem);
}
}
/*
* Implementation of IShellBrowser for the File Open common dialog
*
*
*/
#include <stdio.h>
#include "unknwn.h"
#include "filedlgbrowser.h"
#include "winuser.h"
#include "commctrl.h"
#include "wine/obj_dataobject.h"
#include "debugtools.h"
#include "cdlg.h"
#include "wine/undocshell.h"
DEFAULT_DEBUG_CHANNEL(commdlg)
#define SETDefFormatEtc(fe,cf,med) \
{ \
(fe).cfFormat = cf;\
(fe).dwAspect = DVASPECT_CONTENT; \
(fe).ptd =NULL;\
(fe).tymed = med;\
(fe).lindex = -1;\
};
/**************************************************************************
* Structure
*/
static ICOM_VTABLE(IShellBrowser) IShellBrowserImpl_Vtbl =
{
/* IUnknown */
IShellBrowserImpl_QueryInterface,
IShellBrowserImpl_AddRef,
IShellBrowserImpl_Release,
/* IOleWindow */
IShellBrowserImpl_GetWindow,
IShellBrowserImpl_ContextSensitiveHelp,
/* IShellBrowser */
IShellBrowserImpl_InsertMenusSB,
IShellBrowserImpl_SetMenuSB,
IShellBrowserImpl_RemoveMenusSB,
IShellBrowserImpl_SetStatusTextSB,
IShellBrowserImpl_EnableModelessSB,
IShellBrowserImpl_TranslateAcceleratorSB,
IShellBrowserImpl_BrowseObject,
IShellBrowserImpl_GetViewStateStream,
IShellBrowserImpl_GetControlWindow,
IShellBrowserImpl_SendControlMsg,
IShellBrowserImpl_QueryActiveShellView,
IShellBrowserImpl_OnViewWindowActive,
IShellBrowserImpl_SetToolbarItems
};
static ICOM_VTABLE(ICommDlgBrowser) IShellBrowserImpl_ICommDlgBrowser_Vtbl =
{
/* IUnknown */
IShellBrowserImpl_ICommDlgBrowser_QueryInterface,
IShellBrowserImpl_ICommDlgBrowser_AddRef,
IShellBrowserImpl_ICommDlgBrowser_Release,
/* ICommDlgBrowser */
IShellBrowserImpl_ICommDlgBrowser_OnDefaultCommand,
IShellBrowserImpl_ICommDlgBrowser_OnStateChange,
IShellBrowserImpl_ICommDlgBrowser_IncludeObject
};
/**************************************************************************
* Local Prototypes
*/
HRESULT IShellBrowserImpl_ICommDlgBrowser_OnSelChange(ICommDlgBrowser *iface, IShellView *ppshv);
LPITEMIDLIST GetSelectedPidl(IShellView *ppshv);
/**************************************************************************
* External Prototypes
*/
extern const char *FileOpenDlgInfosStr;
extern HRESULT GetName(LPSHELLFOLDER lpsf, LPITEMIDLIST pidl,DWORD dwFlags,LPSTR lpstrFileName);
extern HRESULT GetFileName(HWND hwnd, LPITEMIDLIST pidl, LPSTR lpstrFileName);
extern IShellFolder* GetShellFolderFromPidl(LPITEMIDLIST pidlAbs);
extern LPITEMIDLIST GetParentPidl(LPITEMIDLIST pidl);
extern LPITEMIDLIST GetPidlFromName(IShellFolder *psf,LPCSTR lpcstrFileName);
extern BOOL FILEDLG95_SHELL_FillIncludedItemList(HWND hwnd,
LPITEMIDLIST pidlCurrentFolder,
LPSTR lpstrMask);
extern int FILEDLG95_LOOKIN_SelectItem(HWND hwnd,LPITEMIDLIST pidl);
extern BOOL FILEDLG95_OnOpen(HWND hwnd);
/**************************************************************************
* IShellBrowserImpl_Construct
*/
IShellBrowser * IShellBrowserImpl_Construct(HWND hwndOwner)
{
IShellBrowserImpl *sb;
FileOpenDlgInfos *fodInfos = (FileOpenDlgInfos *) GetPropA(hwndOwner,FileOpenDlgInfosStr);
sb=(IShellBrowserImpl*)SHAlloc(sizeof(IShellBrowserImpl));
/* Initialisation of the member variables */
sb->ref=1;
sb->hwndOwner = hwndOwner;
/* Initialisation of the vTables */
sb->lpVtbl = &IShellBrowserImpl_Vtbl;
sb->lpVtbl2 = &IShellBrowserImpl_ICommDlgBrowser_Vtbl;
SHGetSpecialFolderLocation(hwndOwner,
CSIDL_DESKTOP,
&fodInfos->ShellInfos.pidlAbsCurrent);
TRACE("%p\n", sb);
return (IShellBrowser *) sb;
}
/**************************************************************************
*
*
* The INTERFACE of the IShellBrowser object
*
*/
/*
* IUnknown
*/
/***************************************************************************
* IShellBrowserImpl_QueryInterface
*/
HRESULT WINAPI IShellBrowserImpl_QueryInterface(IShellBrowser *iface,
REFIID riid,
LPVOID *ppvObj)
{
ICOM_THIS(IShellBrowserImpl, iface);
TRACE("(%p)\n", This);
*ppvObj = NULL;
if(IsEqualIID(riid, &IID_IUnknown)) /*IUnknown*/
{ *ppvObj = This;
}
else if(IsEqualIID(riid, &IID_IOleWindow)) /*IOleWindow*/
{ *ppvObj = (IOleWindow*)This;
}
else if(IsEqualIID(riid, &IID_IShellBrowser)) /*IShellBrowser*/
{ *ppvObj = (IShellBrowser*)This;
}
else if(IsEqualIID(riid, &IID_ICommDlgBrowser)) /*ICommDlgBrowser*/
{ *ppvObj = (ICommDlgBrowser*) &(This->lpVtbl2);
}
if(*ppvObj)
{ IUnknown_AddRef( (IShellBrowser*) *ppvObj);
return S_OK;
}
return E_NOINTERFACE;
}
/**************************************************************************
* IShellBrowser::AddRef
*/
ULONG WINAPI IShellBrowserImpl_AddRef(IShellBrowser * iface)
{
ICOM_THIS(IShellBrowserImpl, iface);
TRACE("(%p)\n", This);
return ++(This->ref);
}
/**************************************************************************
* IShellBrowserImpl_Release
*/
ULONG WINAPI IShellBrowserImpl_Release(IShellBrowser * iface)
{
ICOM_THIS(IShellBrowserImpl, iface);
TRACE("(%p)\n", This);
if (!--(This->ref))
{
SHFree(This);
return 0;
}
return This->ref;
}
/*
* IOleWindow
*/
/**************************************************************************
* IShellBrowserImpl_GetWindow (IOleWindow)
*
* Inherited from IOleWindow::GetWindow
*
* See Windows documentation for more details
*
* Note : We will never be window less in the File Open dialog
*
*/
HRESULT WINAPI IShellBrowserImpl_GetWindow(IShellBrowser * iface,
HWND * phwnd)
{
ICOM_THIS(IShellBrowserImpl, iface);
TRACE("(%p)\n", This);
if(!This->hwndOwner)
return E_FAIL;
*phwnd = This->hwndOwner;
return (*phwnd) ? S_OK : E_UNEXPECTED;
}
/**************************************************************************
* IShellBrowserImpl_ContextSensitiveHelp
*/
HRESULT WINAPI IShellBrowserImpl_ContextSensitiveHelp(IShellBrowser * iface,
BOOL fEnterMode)
{
ICOM_THIS(IShellBrowserImpl, iface);
TRACE("(%p)\n", This);
/* Feature not implemented */
return E_NOTIMPL;
}
/*
* IShellBrowser
*/
/**************************************************************************
* IShellBrowserImpl_BrowseObject
*
* See Windows documentation on IShellBrowser::BrowseObject for more details
*
* This function will override user specified flags and will always
* use SBSP_DEFBROWSER and SBSP_DEFMODE.
*/
HRESULT WINAPI IShellBrowserImpl_BrowseObject(IShellBrowser *iface,
LPCITEMIDLIST pidl,
UINT wFlags)
{
HRESULT hRes;
IShellFolder *psfTmp;
IShellView *psvTmp;
FileOpenDlgInfos *fodInfos;
LPITEMIDLIST pidlTmp;
ICOM_THIS(IShellBrowserImpl, iface);
TRACE("(%p)\n", This);
fodInfos = (FileOpenDlgInfos *) GetPropA(This->hwndOwner,FileOpenDlgInfosStr);
/* Format the pidl according to its parameter's category */
if(wFlags & SBSP_RELATIVE)
{
/* SBSP_RELATIVE A relative pidl (relative from the current folder) */
hRes = IShellFolder_BindToObject(fodInfos->Shell.FOIShellFolder,
pidl,
NULL,
&IID_IShellFolder,
(LPVOID *)&psfTmp);
if(FAILED(hRes))
{
return hRes;
}
/* create an absolute pidl */
pidlTmp = ILCombine(fodInfos->ShellInfos.pidlAbsCurrent,
(LPITEMIDLIST)pidl);
}
else if(wFlags & SBSP_PARENT)
{
/* Browse the parent folder (ignores the pidl) */
pidlTmp = GetParentPidl(fodInfos->ShellInfos.pidlAbsCurrent);
psfTmp = GetShellFolderFromPidl(pidlTmp);
}
else
{
/* An absolute pidl (relative from the desktop) */
pidlTmp = ILClone((LPITEMIDLIST)pidl);
psfTmp = GetShellFolderFromPidl(pidlTmp);
}
/* Retrieve the IShellFolder interface of the pidl specified folder */
if(!psfTmp)
return E_FAIL;
/* Release the current fodInfos->Shell.FOIShellFolder and update its value */
IShellFolder_Release(fodInfos->Shell.FOIShellFolder);
fodInfos->Shell.FOIShellFolder = psfTmp;
/* Create the associated view */
if(SUCCEEDED(hRes = IShellFolder_CreateViewObject(psfTmp,
fodInfos->ShellInfos.hwndOwner,
&IID_IShellView,
(LPVOID *)&psvTmp)))
{
HWND hwndView;
/* Get the foldersettings from the old view */
if(fodInfos->Shell.FOIShellView)
{
IShellView_GetCurrentInfo(fodInfos->Shell.FOIShellView,
&fodInfos->ShellInfos.folderSettings);
}
/* Create the window */
if(SUCCEEDED(hRes = IShellView_CreateViewWindow(psvTmp,
NULL,
&fodInfos->ShellInfos.folderSettings,
fodInfos->Shell.FOIShellBrowser,
&fodInfos->ShellInfos.rectView,
&hwndView)))
{
/* Fit the created view in the appropriate RECT */
MoveWindow(hwndView,
fodInfos->ShellInfos.rectView.left,
fodInfos->ShellInfos.rectView.top,
fodInfos->ShellInfos.rectView.right-fodInfos->ShellInfos.rectView.left,
fodInfos->ShellInfos.rectView.bottom-fodInfos->ShellInfos.rectView.top,
FALSE);
/* Select the new folder in the Look In combo box of the Open file dialog */
FILEDLG95_LOOKIN_SelectItem(fodInfos->DlgInfos.hwndLookInCB,pidlTmp);
/* Release old pidlAbsCurrent memory and update its value */
SHFree((LPVOID)fodInfos->ShellInfos.pidlAbsCurrent);
fodInfos->ShellInfos.pidlAbsCurrent = pidlTmp;
/* Release the current fodInfos->Shell.FOIShellView and update its value */
if(fodInfos->Shell.FOIShellView)
{
IShellView_DestroyViewWindow(fodInfos->Shell.FOIShellView);
IShellView_Release(fodInfos->Shell.FOIShellView);
}
//ShowWindow(fodInfos->ShellInfos.hwndView,SW_HIDE);
fodInfos->Shell.FOIShellView = psvTmp;
fodInfos->ShellInfos.hwndView = hwndView;
return NOERROR;
}
}
FILEDLG95_LOOKIN_SelectItem(fodInfos->DlgInfos.hwndLookInCB,fodInfos->ShellInfos.pidlAbsCurrent);
return hRes;
}
/**************************************************************************
* IShellBrowserImpl_EnableModelessSB
*/
HRESULT WINAPI IShellBrowserImpl_EnableModelessSB(IShellBrowser *iface,
BOOL fEnable)
{
ICOM_THIS(IShellBrowserImpl, iface);
TRACE("(%p)\n", This);
/* Feature not implemented */
return E_NOTIMPL;
}
/**************************************************************************
* IShellBrowserImpl_GetControlWindow
*/
HRESULT WINAPI IShellBrowserImpl_GetControlWindow(IShellBrowser *iface,
UINT id,
HWND *lphwnd)
{
ICOM_THIS(IShellBrowserImpl, iface);
TRACE("(%p)\n", This);
/* Feature not implemented */
return E_NOTIMPL;
}
/**************************************************************************
* IShellBrowserImpl_GetViewStateStream
*/
HRESULT WINAPI IShellBrowserImpl_GetViewStateStream(IShellBrowser *iface,
DWORD grfMode,
LPSTREAM *ppStrm)
{
ICOM_THIS(IShellBrowserImpl, iface);
TRACE("(%p)\n", This);
/* Feature not implemented */
return E_NOTIMPL;
}
/**************************************************************************
* IShellBrowserImpl_InsertMenusSB
*/
HRESULT WINAPI IShellBrowserImpl_InsertMenusSB(IShellBrowser *iface,
HMENU hmenuShared,
LPOLEMENUGROUPWIDTHS lpMenuWidths)
{
ICOM_THIS(IShellBrowserImpl, iface);
TRACE("(%p)\n", This);
/* Feature not implemented */
return E_NOTIMPL;
}
/**************************************************************************
* IShellBrowserImpl_OnViewWindowActive
*/
HRESULT WINAPI IShellBrowserImpl_OnViewWindowActive(IShellBrowser *iface,
IShellView *ppshv)
{
ICOM_THIS(IShellBrowserImpl, iface);
TRACE("(%p)\n", This);
/* Feature not implemented */
return E_NOTIMPL;
}
/**************************************************************************
* IShellBrowserImpl_QueryActiveShellView
*/
HRESULT WINAPI IShellBrowserImpl_QueryActiveShellView(IShellBrowser *iface,
IShellView **ppshv)
{
ICOM_THIS(IShellBrowserImpl, iface);
FileOpenDlgInfos *fodInfos;
TRACE("(%p)\n", This);
fodInfos = (FileOpenDlgInfos *) GetPropA(This->hwndOwner,FileOpenDlgInfosStr);
if(!(*ppshv = fodInfos->Shell.FOIShellView))
{
return E_FAIL;
}
IShellView_AddRef(fodInfos->Shell.FOIShellView);
return NOERROR;
}
/**************************************************************************
* IShellBrowserImpl_RemoveMenusSB
*/
HRESULT WINAPI IShellBrowserImpl_RemoveMenusSB(IShellBrowser *iface,
HMENU hmenuShared)
{
ICOM_THIS(IShellBrowserImpl, iface);
TRACE("(%p)\n", This);
/* Feature not implemented */
return E_NOTIMPL;
}
/**************************************************************************
* IShellBrowserImpl_SendControlMsg
*/
HRESULT WINAPI IShellBrowserImpl_SendControlMsg(IShellBrowser *iface,
UINT id,
UINT uMsg,
WPARAM wParam,
LPARAM lParam,
LRESULT *pret)
{
ICOM_THIS(IShellBrowserImpl, iface);
TRACE("(%p)\n", This);
/* Feature not implemented */
return E_NOTIMPL;
}
/**************************************************************************
* IShellBrowserImpl_SetMenuSB
*/
HRESULT WINAPI IShellBrowserImpl_SetMenuSB(IShellBrowser *iface,
HMENU hmenuShared,
HOLEMENU holemenuReserved,
HWND hwndActiveObject)
{
ICOM_THIS(IShellBrowserImpl, iface);
TRACE("(%p)\n", This);
/* Feature not implemented */
return E_NOTIMPL;
}
/**************************************************************************
* IShellBrowserImpl_SetStatusTextSB
*/
HRESULT WINAPI IShellBrowserImpl_SetStatusTextSB(IShellBrowser *iface,
LPCOLESTR lpszStatusText)
{
ICOM_THIS(IShellBrowserImpl, iface);
TRACE("(%p)\n", This);
/* Feature not implemented */
return E_NOTIMPL;
}
/**************************************************************************
* IShellBrowserImpl_SetToolbarItems
*/
HRESULT WINAPI IShellBrowserImpl_SetToolbarItems(IShellBrowser *iface,
LPTBBUTTON lpButtons,
UINT nButtons,
UINT uFlags)
{
ICOM_THIS(IShellBrowserImpl, iface);
TRACE("(%p)\n", This);
/* Feature not implemented */
return E_NOTIMPL;
}
/**************************************************************************
* IShellBrowserImpl_TranslateAcceleratorSB
*/
HRESULT WINAPI IShellBrowserImpl_TranslateAcceleratorSB(IShellBrowser *iface,
LPMSG lpmsg,
WORD wID)
{
ICOM_THIS(IShellBrowserImpl, iface);
TRACE("(%p)\n", This);
/* Feature not implemented */
return E_NOTIMPL;
}
/*
* ICommDlgBrowser
*/
/***************************************************************************
* IShellBrowserImpl_ICommDlgBrowser_QueryInterface
*/
HRESULT WINAPI IShellBrowserImpl_ICommDlgBrowser_QueryInterface(ICommDlgBrowser *iface,
REFIID riid,
LPVOID *ppvObj)
{
_ICOM_THIS_FromICommDlgBrowser(IShellBrowser,iface);
TRACE("(%p)\n", This);
return IShellBrowserImpl_QueryInterface(This,riid,ppvObj);
}
/**************************************************************************
* IShellBrowserImpl_ICommDlgBrowser_AddRef
*/
ULONG WINAPI IShellBrowserImpl_ICommDlgBrowser_AddRef(ICommDlgBrowser * iface)
{
_ICOM_THIS_FromICommDlgBrowser(IShellBrowser,iface);
TRACE("(%p)\n", This);
return IShellBrowserImpl_AddRef(This);
}
/**************************************************************************
* IShellBrowserImpl_ICommDlgBrowser_Release
*/
ULONG WINAPI IShellBrowserImpl_ICommDlgBrowser_Release(ICommDlgBrowser * iface)
{
_ICOM_THIS_FromICommDlgBrowser(IShellBrowser,iface);
TRACE("(%p)\n", This);
return IShellBrowserImpl_Release(This);
}
/**************************************************************************
* IShellBrowserImpl_ICommDlgBrowser_OnDefaultCommand
*
* Called when a user double-clicks in the view or presses the ENTER key
*/
HRESULT WINAPI IShellBrowserImpl_ICommDlgBrowser_OnDefaultCommand(ICommDlgBrowser *iface,
IShellView *ppshv)
{
LPITEMIDLIST pidl;
FileOpenDlgInfos *fodInfos;
_ICOM_THIS_FromICommDlgBrowser(IShellBrowserImpl,iface);
TRACE("(%p)\n", This);
fodInfos = (FileOpenDlgInfos *) GetPropA(This->hwndOwner,FileOpenDlgInfosStr);
/* If the selected object is not a folder, send a IDOK command to parent window */
if((pidl = GetSelectedPidl(ppshv)))
{
HRESULT hRes;
/* Selected item is a directory so browse to it */
ULONG ulAttr = SFGAO_FOLDER | SFGAO_HASSUBFOLDER;
IShellFolder_GetAttributesOf(fodInfos->Shell.FOIShellFolder, 1, &pidl, &ulAttr);
if (ulAttr)
hRes = IShellBrowser_BrowseObject((IShellBrowser *)This,pidl,SBSP_RELATIVE);
/* Tell the dialog that the user selected a file */
else
hRes = FILEDLG95_OnOpen(This->hwndOwner);
/* Free memory used by pidl */
SHFree((LPVOID)pidl);
return hRes;
}
return E_FAIL;
}
/**************************************************************************
* IShellBrowserImpl_ICommDlgBrowser_OnStateChange
*/
HRESULT WINAPI IShellBrowserImpl_ICommDlgBrowser_OnStateChange(ICommDlgBrowser *iface,
IShellView *ppshv,
ULONG uChange)
{
_ICOM_THIS_FromICommDlgBrowser(IShellBrowserImpl,iface);
TRACE("(%p)\n", This);
switch (uChange)
{
case CDBOSC_SETFOCUS:
break;
case CDBOSC_KILLFOCUS:
break;
case CDBOSC_SELCHANGE:
return IShellBrowserImpl_ICommDlgBrowser_OnSelChange(iface,ppshv);
case CDBOSC_RENAME:
break;
}
return NOERROR;
}
/**************************************************************************
* IShellBrowserImpl_ICommDlgBrowser_IncludeObject
*/
HRESULT WINAPI IShellBrowserImpl_ICommDlgBrowser_IncludeObject(ICommDlgBrowser *iface,
IShellView * ppshv,
LPCITEMIDLIST pidl)
{
FileOpenDlgInfos *fodInfos;
ULONG ulAttr;
STRRET str;
char szPath[MAX_PATH];
_ICOM_THIS_FromICommDlgBrowser(IShellBrowserImpl,iface);
TRACE("(%p)\n", This);
fodInfos = (FileOpenDlgInfos *) GetPropA(This->hwndOwner,FileOpenDlgInfosStr);
ulAttr = SFGAO_HIDDEN | SFGAO_FOLDER | SFGAO_FILESYSTEM | SFGAO_FILESYSANCESTOR | SFGAO_LINK;
IShellFolder_GetAttributesOf(fodInfos->Shell.FOIShellFolder, 1, &pidl, &ulAttr);
if( (ulAttr & SFGAO_HIDDEN) /* hidden */
| !(ulAttr & (SFGAO_FILESYSTEM | SFGAO_FILESYSANCESTOR))) /* special folder */
return S_FALSE;
/* always include directorys and links */
if(ulAttr & (SFGAO_FOLDER | SFGAO_LINK))
return S_OK;
/* Check if there is a mask to apply if not */
if(!fodInfos->ShellInfos.lpstrCurrentFilter ||
!lstrlenW(fodInfos->ShellInfos.lpstrCurrentFilter))
return S_OK;
IShellFolder_GetDisplayNameOf(fodInfos->Shell.FOIShellFolder, pidl, SHGDN_FORPARSING, &str);
StrRetToStrN(szPath, MAX_PATH, &str, pidl);
return PathMatchSpecW((LPWSTR)szPath, fodInfos->ShellInfos.lpstrCurrentFilter)? S_OK : S_FALSE;
}
/**************************************************************************
* IShellBrowserImpl_ICommDlgBrowser_OnSelChange
*/
HRESULT IShellBrowserImpl_ICommDlgBrowser_OnSelChange(ICommDlgBrowser *iface, IShellView *ppshv)
{
LPITEMIDLIST pidl;
_ICOM_THIS_FromICommDlgBrowser(IShellBrowserImpl,iface);
TRACE("(%p)\n", This);
if((pidl = GetSelectedPidl(ppshv)))
{
HRESULT hRes = E_FAIL;
char lpstrFileName[MAX_PATH];
FileOpenDlgInfos *fodInfos = (FileOpenDlgInfos *) GetPropA(This->hwndOwner,FileOpenDlgInfosStr);
ULONG ulAttr = SFGAO_FOLDER | SFGAO_HASSUBFOLDER;
IShellFolder_GetAttributesOf(fodInfos->Shell.FOIShellFolder, 1, &pidl, &ulAttr);
if (!ulAttr)
{
if(SUCCEEDED(hRes = GetName(fodInfos->Shell.FOIShellFolder,pidl,SHGDN_NORMAL,lpstrFileName)))
SetWindowTextW(fodInfos->DlgInfos.hwndFileName,(LPWSTR)lpstrFileName);
}
SHFree((LPVOID)pidl);
return hRes;
}
return E_FAIL;
}
/***********************************************************************
* GetSelectedPidl
*
* Return the pidl of the first selected item in the view
*/
LPITEMIDLIST GetSelectedPidl(IShellView *ppshv)
{
IDataObject *doSelected;
LPITEMIDLIST pidlSelected = NULL;
TRACE("sv=%p\n", ppshv);
/* Get an IDataObject from the view */
if(SUCCEEDED(IShellView_GetItemObject(ppshv,
SVGIO_SELECTION,
&IID_IDataObject,
(LPVOID *)&doSelected)))
{
STGMEDIUM medium;
FORMATETC formatetc;
/* Set the FORMATETC structure*/
SETDefFormatEtc(formatetc,
RegisterClipboardFormatA(CFSTR_SHELLIDLIST),
TYMED_HGLOBAL);
/* Get the pidl from IDataObject */
if(SUCCEEDED(IDataObject_GetData(doSelected,&formatetc,&medium)))
{
LPIDA cida = GlobalLock(medium.u.hGlobal);
TRACE("cida=%p\n", cida);
pidlSelected = ILClone((LPITEMIDLIST)(&((LPBYTE)cida)[cida->aoffset[1]]));
if(medium.pUnkForRelease)
IUnknown_Release(medium.pUnkForRelease);
else
{
GlobalUnlock(medium.u.hGlobal);
GlobalFree(medium.u.hGlobal);
}
}
IDataObject_Release(doSelected);
return pidlSelected;
}
return NULL;
}
/*
* Implementation of IShellBrowser for the File Open common dialog
*
*
*/
#ifndef SHBROWSER_H
#define SHBROWSER_H TRUE
#include "shlobj.h"
#include "winbase.h"
#include "objbase.h"
#include "commdlg.h"
/***********************************************************************
* Defines and global variables
*/
#define _ICOM_THIS_FromICommDlgBrowser(Class,name) Class* This = (Class*) (((char*)name)-sizeof(void *))
/***********************************************************************
* Data structure
*/
typedef struct
{
ICOM_VTABLE(IShellBrowser)* lpVtbl; /* IShellBrowser VTable */
ICOM_VTABLE(ICommDlgBrowser)* lpVtbl2; /* ICommDlgBrowser VTable */
DWORD ref; /* Reference counter */
HWND hwndOwner; /* Owner dialog of the interface */
} IShellBrowserImpl;
typedef struct
{
OPENFILENAMEA ofnInfos;
struct {
IShellBrowser *FOIShellBrowser;
IShellFolder *FOIShellFolder;
IShellView *FOIShellView;
} Shell;
struct {
HWND hwndOwner;
HWND hwndView;
RECT rectView;
FOLDERSETTINGS folderSettings;
LPITEMIDLIST pidlAbsCurrent;
LPWSTR lpstrCurrentFilter;
} ShellInfos;
struct {
HWND hwndFileTypeCB;
HWND hwndLookInCB;
HWND hwndFileName;
} DlgInfos;
} FileOpenDlgInfos;
/***********************************************************************
* Prototypes for the methods of the IShellBrowserImpl class
*/
/* Constructor */
IShellBrowser * IShellBrowserImpl_Construct(HWND hwndOwner);
/* IUnknown */
HRESULT WINAPI IShellBrowserImpl_QueryInterface(IShellBrowser *iface,
REFIID riid,
LPVOID *ppvObj);
ULONG WINAPI IShellBrowserImpl_AddRef(IShellBrowser * iface);
ULONG WINAPI IShellBrowserImpl_Release(IShellBrowser * iface);
/* IOleWindow */
HRESULT WINAPI IShellBrowserImpl_GetWindow(IShellBrowser * iface,
HWND * phwnd);
HRESULT WINAPI IShellBrowserImpl_ContextSensitiveHelp(IShellBrowser * iface,
BOOL fEnterMode);
/* IShellBrowser */
HRESULT WINAPI IShellBrowserImpl_BrowseObject(IShellBrowser *iface,
LPCITEMIDLIST pidl,
UINT wFlags);
HRESULT WINAPI IShellBrowserImpl_EnableModelessSB(IShellBrowser *iface,
BOOL fEnable);
HRESULT WINAPI IShellBrowserImpl_GetControlWindow(IShellBrowser *iface,
UINT id,
HWND *lphwnd);
HRESULT WINAPI IShellBrowserImpl_GetViewStateStream(IShellBrowser *iface,
DWORD grfMode,
LPSTREAM *ppStrm);
HRESULT WINAPI IShellBrowserImpl_InsertMenusSB(IShellBrowser *iface,
HMENU hmenuShared,
LPOLEMENUGROUPWIDTHS lpMenuWidths);
HRESULT WINAPI IShellBrowserImpl_OnViewWindowActive(IShellBrowser *iface,
IShellView *ppshv);
HRESULT WINAPI IShellBrowserImpl_QueryActiveShellView(IShellBrowser *iface,
IShellView **ppshv);
HRESULT WINAPI IShellBrowserImpl_RemoveMenusSB(IShellBrowser *iface,
HMENU hmenuShared);
HRESULT WINAPI IShellBrowserImpl_SendControlMsg(IShellBrowser *iface,
UINT id,
UINT uMsg,
WPARAM wParam,
LPARAM lParam,
LRESULT *pret);
HRESULT WINAPI IShellBrowserImpl_SetMenuSB(IShellBrowser *iface,
HMENU hmenuShared,
HOLEMENU holemenuReserved,
HWND hwndActiveObject);
HRESULT WINAPI IShellBrowserImpl_SetStatusTextSB(IShellBrowser *iface,
LPCOLESTR lpszStatusText);
HRESULT WINAPI IShellBrowserImpl_SetToolbarItems(IShellBrowser *iface,
LPTBBUTTON lpButtons,
UINT nButtons,
UINT uFlags);
HRESULT WINAPI IShellBrowserImpl_TranslateAcceleratorSB(IShellBrowser *iface,
LPMSG lpmsg,
WORD wID);
/* ICommDlgBrowser */
HRESULT WINAPI IShellBrowserImpl_ICommDlgBrowser_QueryInterface(ICommDlgBrowser *iface,
REFIID riid,
LPVOID *ppvObj);
ULONG WINAPI IShellBrowserImpl_ICommDlgBrowser_AddRef(ICommDlgBrowser * iface);
ULONG WINAPI IShellBrowserImpl_ICommDlgBrowser_Release(ICommDlgBrowser * iface);
HRESULT WINAPI IShellBrowserImpl_ICommDlgBrowser_OnDefaultCommand(ICommDlgBrowser *iface,
IShellView *ppshv);
HRESULT WINAPI IShellBrowserImpl_ICommDlgBrowser_OnStateChange(ICommDlgBrowser *iface,
IShellView *ppshv,
ULONG uChange);
HRESULT WINAPI IShellBrowserImpl_ICommDlgBrowser_IncludeObject(ICommDlgBrowser *iface,
IShellView * ppshv,
LPCITEMIDLIST pidl);
#endif /*SHBROWSER_H*/
......@@ -44,6 +44,9 @@ extern "C" {
#define OFN_SHARENOWARN 1
#define OFN_SHAREWARN 0
#define SAVE_DIALOG 1
#define OPEN_DIALOG 2
typedef UINT16 (CALLBACK *LPOFNHOOKPROC16)(HWND16,UINT16,WPARAM16,LPARAM);
typedef UINT (CALLBACK *LPOFNHOOKPROC)(HWND,UINT,WPARAM,LPARAM);
......@@ -591,7 +594,6 @@ BOOL WINAPI ChooseColorA(LPCHOOSECOLORA lpChCol);
BOOL WINAPI ChooseColorW(LPCHOOSECOLORW lpChCol);
#define ChooseColor WINELIB_NAME_AW(ChooseColor)
DWORD WINAPI CommDlgExtendedError(void);
DWORD WINAPI CommDlgExtendedError16(void);
HWND16 WINAPI FindText16( SEGPTR find);
HWND WINAPI FindTextA(LPFINDREPLACEA lpFind);
HWND WINAPI FindTextW(LPFINDREPLACEW lpFind);
......@@ -603,6 +605,8 @@ INT16 WINAPI GetFileTitleW(LPCWSTR lpFile, LPWSTR lpTitle, UINT cbBuf);
BOOL16 WINAPI GetOpenFileName16(SEGPTR ofn);
BOOL WINAPI GetOpenFileNameA(LPOPENFILENAMEA ofn);
BOOL WINAPI GetOpenFileNameW(LPOPENFILENAMEW ofn);
BOOL WINAPI GetFileDialog95A(LPOPENFILENAMEA ofn,UINT iDlgType);
BOOL WINAPI GetFileDialog95W(LPOPENFILENAMEW ofn,UINT iDlgType);
#define GetOpenFileName WINELIB_NAME_AW(GetOpenFileName)
BOOL16 WINAPI GetSaveFileName16(SEGPTR ofn);
BOOL WINAPI GetSaveFileNameA(LPOPENFILENAMEA ofn);
......@@ -636,11 +640,9 @@ LRESULT WINAPI FormatCharDlgProc16(HWND16,UINT16,WPARAM16,LPARAM);
LRESULT WINAPI FormatCharDlgProcA(HWND,UINT,WPARAM,LPARAM);
LRESULT WINAPI FormatCharDlgProcW(HWND,UINT,WPARAM,LPARAM);
#define FormatCharDlgProc WINELIB_NAME_AW(FormatCharDlgProc)
INT16 WINAPI FontFamilyEnumProc16( SEGPTR logfont, SEGPTR metrics, UINT16 nFontType, LPARAM lParam);
INT16 WINAPI FontStyleEnumProc16( SEGPTR logfont, SEGPTR metrics, UINT16 nFontType, LPARAM lParam);
BOOL WINAPI COMMDLG_DllEntryPoint(DWORD Reason, HINSTANCE16 hInst, WORD ds, WORD HeapSize, DWORD res1, WORD res2);
BOOL WINAPI COMDLG32_DllEntryPoint(HINSTANCE hInstance, DWORD Reason, LPVOID Reserved);
void COMDLG32_SetCommDlgExtendedError(DWORD err);
#include "poppack.h"
......
......@@ -183,4 +183,34 @@
#define FORMATDLGORD31 1543
#define FORMATDLGORD30 1544
#define IDD_OPENDIALOG 101
#define IDD_SAVEDIALOG 201
#define IDS_ABOUTBOX 101
#define IDS_DOCUMENTFOLDERS 102
#define IDS_PERSONAL 103
#define IDS_FAVORITES 104
#define IDS_PATH 105
#define IDS_DESKTOP 106
#define IDB_TOOLBAR 107
#define IDS_FONTS 108
#define IDS_MYCOMPUTER 110
#define IDS_SYSTEMFOLDERS 112
#define IDS_LOCALHARDRIVES 113
#define IDS_FILENOTFOUND 114
#define IDS_VERIFYFILE 115
#define IDS_CREATEFILE 116
#define IDC_OPENREADONLY 410
#define IDC_FILETYPESTATIC 441
#define IDC_FILENAMESTATIC 442
#define IDC_LOOKINSTATIC 443
#define IDC_SHELLSTATIC 461
#define IDC_FILETYPE 470
#define IDC_LOOKIN 471
#define IDC_FILENAME 480
#define IDC_UPFOLDER 1009
#define IDC_NEWFOLDER 1010
#define IDC_LIST 1011
#define IDC_DETAILS 1014
#endif /* #ifdef __WINE_DLGS_H */
......@@ -47,16 +47,16 @@ extern "C" {
/* FIXME: stricoll is not implemented but strcasecmp is probably close enough in most cases */
#define _stricoll strcasecmp
#define stricoll _stricoll
#define strlwr _strlwr
char *_strlwr(char *string);
#define strlwr CRTDLL__strlwr
char *CRTDLL__strlwr(char *string);
#define strnset _strnset
/* FIXME: _strnset is not implemented */
#define strrev _strrev
char *_strrev(char *string);
#define strrev CRTDLL__strrev
char *CRTDLL__strrev(char *string);
#define strset _strset
/* FIXME: _strset is not implemented */
#define strupr _strupr
char *_strupr(char *string);
#define strupr CRTDLL__strupr
char *CRTDLL__strupr(char *string);
#define ultoa _ultoa
/* FIXME: _ultoa is not implemented */
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment