|
|
/* icon.c - Handles Icon + Caption objects.
*/
#include "packager.h"
#include <shellapi.h>
// #include <shlapip.h>
static LPIC IconCreate(VOID); void GetDisplayName(LPSTR szName, LPCSTR szPath);
/* IconClone() -
* * Clones an appearance pane icon. */ LPIC IconClone( LPIC lpic ) { LPIC lpicNew;
if (lpicNew = IconCreate()) { // Get the icon
StringCchCopy(lpicNew->szIconPath, ARRAYSIZE(lpicNew->szIconPath), lpic->szIconPath); lpicNew->iDlgIcon = lpic->iDlgIcon; GetCurrentIcon(lpicNew);
// Get the icon text
StringCchCopy(lpicNew->szIconText, ARRAYSIZE(lpicNew->szIconText), lpic->szIconText); }
return lpicNew; }
/* IconCreate() -
*/ static LPIC IconCreate( VOID ) { HANDLE hdata = NULL; LPIC lpic = NULL;
if (!(hdata = GlobalAlloc(GMEM_MOVEABLE, sizeof(IC))) || !(lpic = (LPIC)GlobalLock(hdata))) goto errRtn;
// Store the data in the window itself
lpic->hdata = hdata; lpic->hDlgIcon = NULL; lpic->iDlgIcon = 0; *lpic->szIconPath = 0; *lpic->szIconText = 0;
return lpic;
errRtn: ErrorMessage(E_FAILED_TO_CREATE_CHILD_WINDOW);
if (lpic) GlobalUnlock(hdata);
if (hdata) GlobalFree(hdata);
return NULL; }
/* IconCreateFromFile() -
* * Allows an appearance pane icon to be created automatically if * a file is dropped, imported, or pasted into the packager. */ LPIC IconCreateFromFile( LPSTR lpstrFile ) { LPIC lpic;
if (lpic = IconCreate()) { // Get the icon
StringCchCopy(lpic->szIconPath, ARRAYSIZE(lpic->szIconPath), lpstrFile); lpic->iDlgIcon = 0;
if (*(lpic->szIconPath)) GetCurrentIcon(lpic);
// Get the icon text
GetDisplayName(lpic->szIconText, lpstrFile); }
return lpic; }
/* IconCreateFromObject() -
* * Allows an appearance pane icon to be created automatically if an * OLE object is dropped into the appearance pane. */ LPIC IconCreateFromObject( LPOLEOBJECT lpObject ) { DWORD otObject; HANDLE hdata; LPIC lpic = NULL; LPSTR lpdata;
OleQueryType(lpObject, &otObject);
if ((otObject == OT_LINK && Error(OleGetData(lpObject, gcfLink, &hdata))) || (otObject == OT_EMBEDDED && Error(OleGetData(lpObject, gcfOwnerLink, &hdata)))) hdata = NULL;
if (hdata && (lpdata = GlobalLock(hdata))) { if (lpic = IconCreate()) { // Get the icon
RegGetExeName(lpic->szIconPath, lpdata, CBPATHMAX); lpic->iDlgIcon = 0; GetCurrentIcon(lpic);
// Get the icon text
switch (otObject) { case OT_LINK: while (*lpdata++) ;
StringCchCopy(lpic->szIconText, ARRAYSIZE(lpic->szIconText), lpdata); Normalize(lpic->szIconText); break;
case OT_EMBEDDED: RegGetClassId(lpic->szIconText, ARRAYSIZE(lpic->szIconText), lpdata); break; }
GlobalUnlock(hdata); } }
return lpic; }
/* IconDelete() - Used to clear the appearance pane of icon stuff.
*/ VOID IconDelete( LPIC lpic ) { HANDLE hdata;
if (!lpic) return;
if (lpic->hDlgIcon) DestroyIcon(lpic->hDlgIcon);
GlobalUnlock(hdata = lpic->hdata); GlobalFree(hdata); }
/* IconDraw() - Used to draw the icon and its caption.
*/ VOID IconDraw( LPIC lpic, HDC hdc, LPRECT lprc, BOOL fFocus, INT cxImage, INT cyImage ) { BOOL fMF; HFONT hfont = NULL; RECT rcText; DWORD dwLayout;
hfont = SelectObject(hdc, ghfontTitle); if (!(fMF = (cxImage && cyImage))) { // Figure out how large the text region will be
if (*(lpic->szIconText)) { SetRect(&rcText, 0, 0, gcxArrange - 1, gcyArrange - 1); DrawText(hdc, lpic->szIconText, -1, &rcText, DT_CALCRECT | DT_WORDBREAK | DT_NOPREFIX | DT_SINGLELINE); } else { SetRect(&rcText, 0, 0, 0, 0); }
// Figure out the image dimensions
cxImage = (gcxIcon > rcText.right) ? gcxIcon : rcText.right; cyImage = gcyIcon + rcText.bottom; }
// Draw the icon
if (lpic->hDlgIcon) { // Do not mirror the Icon.
dwLayout = GetLayout(hdc); if ((dwLayout != GDI_ERROR) && (dwLayout & LAYOUT_RTL)) { SetLayout(hdc, dwLayout | LAYOUT_BITMAPORIENTATIONPRESERVED); } DrawIcon(hdc, (lprc->left + lprc->right - gcxIcon) / 2, (lprc->top + lprc->bottom - cyImage) / 2, lpic->hDlgIcon); if ((dwLayout != GDI_ERROR) && (dwLayout & LAYOUT_RTL)) { SetLayout(hdc, dwLayout); } }
// Draw the icon text
if (*(lpic->szIconText)) { if (fMF) { SetBkMode(hdc, TRANSPARENT); SetTextAlign(hdc, TA_CENTER); TextOut(hdc, cxImage / 2, gcyIcon + 1, lpic->szIconText, lstrlen(lpic->szIconText)); } else { OffsetRect(&rcText, (lprc->left + lprc->right - cxImage) / 2, (lprc->top + lprc->bottom - cyImage) / 2 + gcyIcon); DrawText(hdc, lpic->szIconText, -1, &rcText, DT_CENTER | DT_WORDBREAK | DT_NOPREFIX | DT_SINGLELINE); } }
if (hfont) SelectObject(hdc, hfont);
if (fFocus && cxImage && cyImage) { RECT rcFocus;
SetRect(&rcFocus, (lprc->left + lprc->right - cxImage) / 2, (lprc->top + lprc->bottom - cyImage) / 2, (lprc->left + lprc->right + cxImage) / 2, (lprc->top + lprc->bottom + cyImage) / 2); DrawFocusRect(hdc, &rcFocus); } }
/* IconReadFromNative() - Used to retrieve the icon object from memory.
*/ LPIC IconReadFromNative( LPSTR *lplpstr ) { LPIC lpic; WORD w;
if (lpic = IconCreate()) { StringCchCopy(lpic->szIconText, ARRAYSIZE(lpic->szIconText), *lplpstr); *lplpstr += lstrlen(lpic->szIconText) + 1; StringCchCopy(lpic->szIconPath, ARRAYSIZE(lpic->szIconPath), *lplpstr); *lplpstr += lstrlen(lpic->szIconPath) + 1; MemRead(lplpstr, (LPSTR)&w, sizeof(WORD)); lpic->iDlgIcon = (INT)w; GetCurrentIcon(lpic); }
return lpic; }
/* IconWriteToNative() - Used to write the icon object to memory.
*/ DWORD IconWriteToNative( LPIC lpic, LPSTR *lplpstr ) { DWORD cBytes; WORD w;
if (lplpstr) { // Now, write out the icon text and the icon
cBytes = lstrlen(lpic->szIconText) + 1; MemWrite(lplpstr, (LPSTR)lpic->szIconText, cBytes);
cBytes = lstrlen(lpic->szIconPath) + 1; MemWrite(lplpstr, (LPSTR)lpic->szIconPath, cBytes); w = (WORD)lpic->iDlgIcon; MemWrite(lplpstr, (LPSTR)&w, sizeof(WORD)); }
return (lstrlen(lpic->szIconText) + 1 + lstrlen(lpic->szIconPath) + 1 + sizeof(WORD)); }
VOID GetCurrentIcon( LPIC lpic ) { WORD wIcon = (WORD)lpic->iDlgIcon;
if (lpic->hDlgIcon) DestroyIcon(lpic->hDlgIcon);
if (!(lpic->hDlgIcon = ExtractAssociatedIcon(ghInst, lpic->szIconPath, &wIcon))) lpic->hDlgIcon = LoadIcon(ghInst, MAKEINTRESOURCE(ID_APPLICATION));
}
//
// get the nice name to show to the user given a filename
//
// FEATURE: we realy should just call the shell!!!
//
void GetDisplayName(LPSTR szName, LPCSTR szPath) { WIN32_FIND_DATA fd; HANDLE h; BOOL IsLFN;
StringCchCopy(szName, MAX_PATH, szPath); // verified
h = FindFirstFile(szPath, &fd);
if (h != INVALID_HANDLE_VALUE) { FindClose(h); StringCchCopy(szName, MAX_PATH, fd.cFileName);
IsLFN = !(fd.cAlternateFileName[0] == 0 || lstrcmp(fd.cFileName, fd.cAlternateFileName) == 0);
if (!IsLFN) { AnsiLower(szName); AnsiUpperBuff(szName, 1); } } else { Normalize(szName); // strip path part
} }
|