(삽질기 부록#1 : context-menu 추가 및 삽질기 부록#2 : context-menu 추가 업그레이드 참조)
그런데, Notepad2 3.1.21 정식버전에서는 이 수정을 미묘하게 바꿔야 했으며, okto님의 수정요청도 받아들여 수정한 것도 있어 전체를 통합한 수정방법을 포스팅한다.
(File 메뉴에서 context-menu 관련 체크박스 2개가 동시에 체크되지 않도록 수정)
삽질기 1~3을 모두 적용했다고 가정하고 시작함.
수정 대상파일은 resource.h, Notepad2.rc, Notepad2.c의 3개이며, 모두 src 폴더에 저장되어 있다.
1. resource.h
다음 두 줄을 추가한다.
#define IDM_REGISTRY_UNKNOWN 40690
#define IDM_REGISTRY_ALL 40691
2. Notepad2.rc
IDR_MAINWND MENU DISCARDABLE에서 아래 내용을 찾는다.
구분자 하나와 context-menu에 관련된 두 줄을 추가하는 내용임.
MENUITEM "Propert&ies...", IDM_FILE_PROPERTIES이 부분을 아래와 같이 수정한다.
MENUITEM "Create &Desktop Link", IDM_FILE_CREATELINK
MENUITEM SEPARATOR
POPUP "&Favorites"
BEGIN
MENUITEM "&Open Favorites...\tAlt+I", IDM_FILE_OPENFAV
MENUITEM "&Add Current File...\tAlt+K", IDM_FILE_ADDTOFAV
MENUITEM "&Manage...\tF9", IDM_FILE_MANAGEFAV
END
MENUITEM "Propert&ies...", IDM_FILE_PROPERTIES
MENUITEM SEPARATOR
MENUITEM "Create &Desktop Link", IDM_FILE_CREATELINK
MENUITEM "Add context-menu to all file type", IDM_REGISTRY_ALL, CHECKED
MENUITEM "Add context-menu to unknown file type", IDM_REGISTRY_UNKNOWN, CHECKED
MENUITEM SEPARATOR
POPUP "&Favorites"
BEGIN
MENUITEM "&Open Favorites...\tAlt+I", IDM_FILE_OPENFAV
MENUITEM "&Add Current File...\tAlt+K", IDM_FILE_ADDTOFAV
MENUITEM "&Manage...\tF9", IDM_FILE_MANAGEFAV
END
구분자 하나와 context-menu에 관련된 두 줄을 추가하는 내용임.
3. Notepad2.h
새로운 함수 하나를 추가한다.
void CheckRegistry();
4. Notepad2.c
파일 앞부분의 변수 선언부에 다음 내용을 추가한다.
다음, LRESULT CALLBACK MainWndProc(HWND hwnd,UINT umsg,WPARAM wParam,LPARAM lParam)에서 아래 내용을 찾는다.
다음, void MsgInitMenu(HWND hwnd,WPARAM wParam,LPARAM lParam)에서 아래 내용을 찾는다.
다음은 LRESULT MsgCommand(HWND hwnd,WPARAM wParam,LPARAM lParam)의 수정이다.
이 함수는 전체가 하나의 switch-case 문으로 되어있는데, 이 case 중에 IDM_REGISTRY_ALL, IDM_REGISTRY_UNKNOWN 둘을 추가한다.
마지막으로 함수를 하나 추가한다.
BOOL bRegistryUnknownType;
BOOL bRegistryAllType;
다음, LRESULT CALLBACK MainWndProc(HWND hwnd,UINT umsg,WPARAM wParam,LPARAM lParam)에서 아래 내용을 찾는다.
case WM_COMMAND:여기에 아래와 같이 한 줄을 추가한다.
return MsgCommand(hwnd,wParam,lParam);
case WM_COMMAND:
CheckRegistry();
return MsgCommand(hwnd,wParam,lParam);
다음, void MsgInitMenu(HWND hwnd,WPARAM wParam,LPARAM lParam)에서 아래 내용을 찾는다.
EnableCmd(hmenu,IDM_EDIT_SELTONEXT,i);이 부분을 아래와 같이 수정한다. 2줄을 추가하는 것이다.
EnableCmd(hmenu,IDM_EDIT_SELTOPREV,i && lstrlenA(efrData.szFind));
EnableCmd(hmenu,IDM_EDIT_REPLACE,i /*&& !bReadOnly*/);
CheckCmd(hmenu,IDM_VIEW_USE2NDDEFAULT,Style_GetUse2ndDefault(hwndEdit));
EnableCmd(hmenu,IDM_EDIT_SELTONEXT,i);
EnableCmd(hmenu,IDM_EDIT_SELTOPREV,i && lstrlenA(efrData.szFind));
EnableCmd(hmenu,IDM_EDIT_REPLACE,i /*&& !bReadOnly*/);
CheckCmd(hmenu,IDM_REGISTRY_UNKNOWN,bRegistryUnknownType);
CheckCmd(hmenu,IDM_REGISTRY_ALL,bRegistryAllType);
CheckCmd(hmenu,IDM_VIEW_USE2NDDEFAULT,Style_GetUse2ndDefault(hwndEdit));
다음은 LRESULT MsgCommand(HWND hwnd,WPARAM wParam,LPARAM lParam)의 수정이다.
이 함수는 전체가 하나의 switch-case 문으로 되어있는데, 이 case 중에 IDM_REGISTRY_ALL, IDM_REGISTRY_UNKNOWN 둘을 추가한다.
case IDM_REGISTRY_ALL:
// Register registry - type unknown
if (bRegistryAllType)
{
//WinNT requires the key to have no subkeys
RegDeleteKey(HKEY_CLASSES_ROOT, L"*\\shell\\Open with notepad2\\command");
RegDeleteKey(HKEY_CLASSES_ROOT, L"*\\shell\\Open with notepad2");
}
else
{
HKEY key1;
LONG res = RegCreateKey(HKEY_CLASSES_ROOT,L"*\\shell\\Open with notepad2",&key1);
if (res == ERROR_SUCCESS)
{
WCHAR cmd[] = L"Open with ¬epad2";
RegSetValue(key1, NULL, REG_SZ, cmd, wcslen(cmd));
}
RegCloseKey(key1);
res = RegCreateKey(HKEY_CLASSES_ROOT,L"*\\shell\\Open with notepad2\\command",&key1);
if (res == ERROR_SUCCESS)
{
WCHAR cmd[MAX_PATH + 4];
WCHAR path[MAX_PATH];
int len;
GetModuleFileName(GetModuleHandle(NULL), path, MAX_PATH);
len = wsprintf(cmd, L"%s %%1", path);
RegSetValue(key1, NULL, REG_SZ, cmd, len);
}
RegCloseKey(key1);
if (bRegistryUnknownType)
{
//WinNT requires the key to have no subkeys
RegDeleteKey(HKEY_CLASSES_ROOT, L"Unknown\\shell\\Open with notepad2\\command");
RegDeleteKey(HKEY_CLASSES_ROOT, L"Unknown\\shell\\Open with notepad2");
bRegistryUnknownType = FALSE;
}
}
bRegistryAllType = !bRegistryAllType;
break;
case IDM_REGISTRY_UNKNOWN:
// Register registry - type all
if (bRegistryUnknownType)
{
//WinNT requires the key to have no subkeys
RegDeleteKey(HKEY_CLASSES_ROOT, L"Unknown\\shell\\Open with notepad2\\command");
RegDeleteKey(HKEY_CLASSES_ROOT, L"Unknown\\shell\\Open with notepad2");
}
else
{
HKEY key1;
LONG res = RegCreateKey(HKEY_CLASSES_ROOT,L"Unknown\\shell\\Open with notepad2",&key1);
if (res == ERROR_SUCCESS)
{
WCHAR cmd[] = L"Open with ¬epad2";
RegSetValue(key1, NULL, REG_SZ, cmd, wcslen(cmd));
}
RegCloseKey(key1);
res = RegCreateKey(HKEY_CLASSES_ROOT,L"Unknown\\shell\\Open with notepad2\\command",&key1);
if (res == ERROR_SUCCESS)
{
WCHAR cmd[MAX_PATH + 4];
WCHAR path[MAX_PATH];
int len;
GetModuleFileName(GetModuleHandle(NULL), path, MAX_PATH);
len = wsprintf(cmd, L"%s %%1", path);
RegSetValue(key1, NULL, REG_SZ, cmd, len);
}
RegCloseKey(key1);
if (bRegistryAllType)
{
//WinNT requires the key to have no subkeys
RegDeleteKey(HKEY_CLASSES_ROOT, L"*\\shell\\Open with notepad2\\command");
RegDeleteKey(HKEY_CLASSES_ROOT, L"*\\shell\\Open with notepad2");
bRegistryAllType = FALSE;
}
}
bRegistryUnknownType = !bRegistryUnknownType;
break;
마지막으로 함수를 하나 추가한다.
void CheckRegistry()
{
HKEY key;
LONG res;
res = RegOpenKey(HKEY_CLASSES_ROOT,L"*\\shell\\Open with notepad2",&key);
if(res == ERROR_SUCCESS)
bRegistryAllType = TRUE;
else bRegistryAllType = FALSE;
RegCloseKey(key);
res = RegOpenKey(HKEY_CLASSES_ROOT,L"unknown\\shell\\Open with notepad2",&key);
if(res == ERROR_SUCCESS)
bRegistryUnknownType = TRUE;
else bRegistryUnknownType = FALSE;
RegCloseKey(key);
}
이렇게 수정하면 아래처럼 File 메뉴에서 context-menu 관련 기능을 사용할 수 있다.
두 개의 context-menu중 하나만 선택되도록 수정했음. ^^;
아잉~[emo=086]
답글삭제@okto - 2009/06/24 22:09
답글삭제핫핫! [emo=051]