1 /* 2 * Internet control panel applet: general propsheet 3 * 4 * Copyright 2010 Detlef Riekenberg 5 * 6 * This library is free software; you can redistribute it and/or 7 * modify it under the terms of the GNU Lesser General Public 8 * License as published by the Free Software Foundation; either 9 * version 2.1 of the License, or (at your option) any later version. 10 * 11 * This library is distributed in the hope that it will be useful, 12 * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 14 * Lesser General Public License for more details. 15 * 16 * You should have received a copy of the GNU Lesser General Public 17 * License along with this library; if not, write to the Free Software 18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA 19 * 20 */ 21 22 #include <stdarg.h> 23 #include <windef.h> 24 #include <winbase.h> 25 #include <winuser.h> 26 #include <wininet.h> 27 #include <winreg.h> 28 #include <shlwapi.h> 29 #include <prsht.h> 30 #include <shlobj.h> 31 32 #include "inetcpl.h" 33 #include "wine/debug.h" 34 35 WINE_DEFAULT_DEBUG_CHANNEL(inetcpl); 36 37 static const WCHAR about_blank[] = {'a','b','o','u','t',':','b','l','a','n','k',0}; 38 static const WCHAR start_page[] = {'S','t','a','r','t',' ','P','a','g','e',0}; 39 static const WCHAR default_page[] = {'D','e','f','a','u','l','t','_','P','a','g','e','_','U','R','L',0}; 40 static const WCHAR reg_ie_main[] = {'S','o','f','t','w','a','r','e','\\', 41 'M','i','c','r','o','s','o','f','t','\\', 42 'I','n','t','e','r','n','e','t',' ','E','x','p','l','o','r','e','r','\\', 43 'M','a','i','n',0}; 44 45 /* list of unimplemented buttons */ 46 static DWORD disabled_general_buttons[] = {IDC_HOME_CURRENT, 47 IDC_HISTORY_SETTINGS, 48 0}; 49 static DWORD disabled_delhist_buttons[] = {IDC_DELETE_FORM_DATA, 50 IDC_DELETE_PASSWORDS, 51 0}; 52 53 /********************************************************************* 54 * delhist_on_command [internal] 55 * 56 * handle WM_COMMAND in Delete browsing history dialog 57 * 58 */ 59 static INT_PTR delhist_on_command(HWND hdlg, WPARAM wparam) 60 { 61 switch (wparam) 62 { 63 case MAKEWPARAM(IDOK, BN_CLICKED): 64 if (IsDlgButtonChecked(hdlg, IDC_DELETE_TEMP_FILES)) 65 FreeUrlCacheSpaceW(NULL, 100, 0); 66 67 if (IsDlgButtonChecked(hdlg, IDC_DELETE_COOKIES)) 68 { 69 WCHAR pathW[MAX_PATH]; 70 71 if(SHGetSpecialFolderPathW(NULL, pathW, CSIDL_COOKIES, TRUE)) 72 FreeUrlCacheSpaceW(pathW, 100, 0); 73 } 74 75 if (IsDlgButtonChecked(hdlg, IDC_DELETE_HISTORY)) 76 { 77 WCHAR pathW[MAX_PATH]; 78 79 if(SHGetSpecialFolderPathW(NULL, pathW, CSIDL_HISTORY, TRUE)) 80 FreeUrlCacheSpaceW(pathW, 100, 0); 81 } 82 83 EndDialog(hdlg, IDOK); 84 return TRUE; 85 86 case MAKEWPARAM(IDCANCEL, BN_CLICKED): 87 EndDialog(hdlg, IDCANCEL); 88 return TRUE; 89 90 case MAKEWPARAM(IDC_DELETE_TEMP_FILES, BN_CLICKED): 91 case MAKEWPARAM(IDC_DELETE_COOKIES, BN_CLICKED): 92 case MAKEWPARAM(IDC_DELETE_HISTORY, BN_CLICKED): 93 case MAKEWPARAM(IDC_DELETE_FORM_DATA, BN_CLICKED): 94 case MAKEWPARAM(IDC_DELETE_PASSWORDS, BN_CLICKED): 95 { 96 BOOL any = IsDlgButtonChecked(hdlg, IDC_DELETE_TEMP_FILES) || 97 IsDlgButtonChecked(hdlg, IDC_DELETE_COOKIES) || 98 IsDlgButtonChecked(hdlg, IDC_DELETE_HISTORY) || 99 IsDlgButtonChecked(hdlg, IDC_DELETE_FORM_DATA) || 100 IsDlgButtonChecked(hdlg, IDC_DELETE_PASSWORDS); 101 EnableWindow(GetDlgItem(hdlg, IDOK), any); 102 break; 103 } 104 105 default: 106 break; 107 } 108 return FALSE; 109 } 110 111 112 /********************************************************************* 113 * delhist_dlgproc [internal] 114 * 115 * Delete browsing history dialog procedure 116 * 117 */ 118 static INT_PTR CALLBACK delhist_dlgproc(HWND hdlg, UINT msg, WPARAM wparam, LPARAM lparam) 119 { 120 switch (msg) 121 { 122 case WM_COMMAND: 123 return delhist_on_command(hdlg, wparam); 124 125 case WM_INITDIALOG: 126 { 127 DWORD *ptr = disabled_delhist_buttons; 128 while (*ptr) 129 { 130 EnableWindow(GetDlgItem(hdlg, *ptr), FALSE); 131 ptr++; 132 } 133 CheckDlgButton(hdlg, IDC_DELETE_TEMP_FILES, BST_CHECKED); 134 break; 135 } 136 137 default: 138 break; 139 } 140 return FALSE; 141 } 142 143 /********************************************************************* 144 * parse_url_from_outside [internal] 145 * 146 * Filter an URL, add a usable scheme, when needed 147 * 148 */ 149 static DWORD parse_url_from_outside(LPCWSTR url, LPWSTR out, DWORD maxlen) 150 { 151 HMODULE hdll; 152 DWORD (WINAPI *pParseURLFromOutsideSourceW)(LPCWSTR, LPWSTR, LPDWORD, LPDWORD); 153 DWORD res; 154 155 hdll = LoadLibraryA("shdocvw.dll"); 156 pParseURLFromOutsideSourceW = (void *) GetProcAddress(hdll, (LPSTR) 170); 157 158 if (pParseURLFromOutsideSourceW) 159 { 160 res = pParseURLFromOutsideSourceW(url, out, &maxlen, NULL); 161 FreeLibrary(hdll); 162 return res; 163 } 164 165 ERR("failed to get ordinal 170: %d\n", GetLastError()); 166 FreeLibrary(hdll); 167 return 0; 168 } 169 170 /********************************************************************* 171 * general_on_command [internal] 172 * 173 * handle WM_COMMAND 174 * 175 */ 176 static INT_PTR general_on_command(HWND hwnd, WPARAM wparam) 177 { 178 WCHAR buffer[INTERNET_MAX_URL_LENGTH]; 179 DWORD len; 180 DWORD type; 181 LONG res; 182 183 switch (wparam) 184 { 185 case MAKEWPARAM(IDC_HOME_EDIT, EN_CHANGE): 186 /* enable apply button */ 187 SendMessageW(GetParent(hwnd), PSM_CHANGED, (WPARAM)hwnd, 0); 188 break; 189 190 case MAKEWPARAM(IDC_HOME_BLANK, BN_CLICKED): 191 SetDlgItemTextW(hwnd, IDC_HOME_EDIT, about_blank); 192 break; 193 194 case MAKEWPARAM(IDC_HOME_DEFAULT, BN_CLICKED): 195 len = sizeof(buffer); 196 type = REG_SZ; 197 res = SHRegGetUSValueW(reg_ie_main, default_page, &type, buffer, &len, FALSE, (LPBYTE) about_blank, sizeof(about_blank)); 198 if (!res && (type == REG_SZ)) SetDlgItemTextW(hwnd, IDC_HOME_EDIT, buffer); 199 break; 200 201 case MAKEWPARAM(IDC_HISTORY_DELETE, BN_CLICKED): 202 DialogBoxW(hcpl, MAKEINTRESOURCEW(IDD_DELETE_HISTORY), hwnd, 203 delhist_dlgproc); 204 break; 205 206 default: 207 TRACE("not implemented for command: %d/%d\n", HIWORD(wparam), LOWORD(wparam)); 208 return FALSE; 209 } 210 return TRUE; 211 } 212 213 /********************************************************************* 214 * general_on_initdialog [internal] 215 * 216 * handle WM_INITDIALOG 217 * 218 */ 219 static VOID general_on_initdialog(HWND hwnd) 220 { 221 WCHAR buffer[INTERNET_MAX_URL_LENGTH]; 222 DWORD len; 223 DWORD type; 224 LONG res; 225 DWORD *ptr = disabled_general_buttons; 226 227 /* disable unimplemented buttons */ 228 while (*ptr) 229 { 230 EnableWindow(GetDlgItem(hwnd, *ptr), FALSE); 231 ptr++; 232 } 233 234 /* read current homepage from the registry. Try HCU first, then HKLM */ 235 *buffer = 0; 236 len = sizeof(buffer); 237 type = REG_SZ; 238 res = SHRegGetUSValueW(reg_ie_main, start_page, &type, buffer, &len, FALSE, (LPBYTE) about_blank, sizeof(about_blank)); 239 240 if (!res && (type == REG_SZ)) 241 { 242 SetDlgItemTextW(hwnd, IDC_HOME_EDIT, buffer); 243 } 244 } 245 246 /********************************************************************* 247 * general_on_notify [internal] 248 * 249 * handle WM_NOTIFY 250 * 251 */ 252 static INT_PTR general_on_notify(HWND hwnd, WPARAM wparam, LPARAM lparam) 253 { 254 PSHNOTIFY *psn; 255 WCHAR buffer[INTERNET_MAX_URL_LENGTH]; 256 WCHAR parsed[INTERNET_MAX_URL_LENGTH]; 257 LONG res; 258 259 psn = (PSHNOTIFY *) lparam; 260 TRACE("WM_NOTIFY (%p, 0x%lx, 0x%lx) from %p with code: %d\n", hwnd, wparam, lparam, 261 psn->hdr.hwndFrom, psn->hdr.code); 262 263 if (psn->hdr.code == PSN_APPLY) 264 { 265 *buffer = 0; 266 GetDlgItemTextW(hwnd, IDC_HOME_EDIT, buffer, sizeof(buffer)/sizeof(WCHAR)); 267 TRACE("EDITTEXT has %s\n", debugstr_w(buffer)); 268 269 res = parse_url_from_outside(buffer, parsed, sizeof(parsed)/sizeof(WCHAR)); 270 TRACE("got %d with %s\n", res, debugstr_w(parsed)); 271 272 if (res) 273 { 274 HKEY hkey; 275 276 /* update the dialog, when needed */ 277 if (lstrcmpW(buffer, parsed)) 278 SetDlgItemTextW(hwnd, IDC_HOME_EDIT, parsed); 279 280 /* update the registry */ 281 res = RegOpenKeyW(HKEY_CURRENT_USER, reg_ie_main, &hkey); 282 if (!res) 283 { 284 res = RegSetValueExW(hkey, start_page, 0, REG_SZ, (const BYTE *)parsed, 285 (lstrlenW(parsed) + 1) * sizeof(WCHAR)); 286 RegCloseKey(hkey); 287 return !res; 288 } 289 } 290 } 291 return FALSE; 292 } 293 294 /********************************************************************* 295 * general_dlgproc [internal] 296 * 297 */ 298 INT_PTR CALLBACK general_dlgproc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam) 299 { 300 301 switch (msg) 302 { 303 case WM_INITDIALOG: 304 general_on_initdialog(hwnd); 305 return TRUE; 306 307 case WM_COMMAND: 308 return general_on_command(hwnd, wparam); 309 310 case WM_NOTIFY: 311 return general_on_notify(hwnd, wparam, lparam); 312 313 default: 314 /* do not flood the log */ 315 if ((msg == WM_SETCURSOR) || (msg == WM_NCHITTEST) || (msg == WM_MOUSEMOVE)) 316 return FALSE; 317 318 TRACE("(%p, 0x%08x/%d, 0x%lx, 0x%lx)\n", hwnd, msg, msg, wparam, lparam); 319 320 } 321 return FALSE; 322 } 323