Home | Info | Community | Development | myReactOS | Contact Us
ReactOS Development > Doxygenbrandband.cpp
Go to the documentation of this file.
00001 /* 00002 * ReactOS Explorer 00003 * 00004 * Copyright 2009 Andrew Hill <ash77 at domain reactos.org> 00005 * 00006 * This library is free software; you can redistribute it and/or 00007 * modify it under the terms of the GNU Lesser General Public 00008 * License as published by the Free Software Foundation; either 00009 * version 2.1 of the License, or (at your option) any later version. 00010 * 00011 * This library is distributed in the hope that it will be useful, 00012 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00013 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00014 * Lesser General Public License for more details. 00015 * 00016 * You should have received a copy of the GNU Lesser General Public 00017 * License along with this library; if not, write to the Free Software 00018 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 00019 */ 00020 00021 /* 00022 Implements the logo band of a cabinet window. Most remarkable feature is the 00023 animation. 00024 */ 00025 #include "precomp.h" 00026 00027 /* 00028 TODO: 00029 Add Exec command handlers 00030 Properly implement GetBandInfo 00031 Fix SetSite to revoke brand band service when site is cleared 00032 */ 00033 00034 inline void FillSolidRect(HDC dc, const RECT *bounds) 00035 { 00036 ::ExtTextOut(dc, 0, 0, ETO_OPAQUE, bounds, NULL, 0, NULL); 00037 } 00038 00039 inline void FillSolidRect(HDC dc, const RECT *bounds, COLORREF clr) 00040 { 00041 ::SetBkColor(dc, clr); 00042 ::ExtTextOut(dc, 0, 0, ETO_OPAQUE, bounds, NULL, 0, NULL); 00043 } 00044 00045 long GetScreenDepth() 00046 { 00047 HDC tempDC; 00048 long depth; 00049 00050 tempDC = GetDC(NULL); 00051 depth = GetDeviceCaps(tempDC, BITSPIXEL) * GetDeviceCaps(tempDC, PLANES); 00052 ReleaseDC(NULL, tempDC); 00053 return depth; 00054 } 00055 00056 static const int gSmallImageSize = 22; 00057 static const int gMediumImageSize = 26; 00058 static const int gLargeImageSize = 38; 00059 00060 static const int gTrueColorResourceBase = 240; 00061 static const int g256ColorResourceBase = 245; 00062 00063 CBrandBand::CBrandBand() 00064 { 00065 fProfferCookie = 0; 00066 fCurrentFrame = 0; 00067 fMaxFrameCount = 0; 00068 fImageBitmap = NULL; 00069 fBitmapSize = 0; 00070 fAdviseCookie = 0; 00071 } 00072 00073 CBrandBand::~CBrandBand() 00074 { 00075 DeleteObject(fImageBitmap); 00076 } 00077 00078 void CBrandBand::StartAnimation() 00079 { 00080 fCurrentFrame = 0; 00081 SetTimer(5678, 30, NULL); 00082 } 00083 00084 void CBrandBand::StopAnimation() 00085 { 00086 KillTimer(5678); 00087 fCurrentFrame = 0; 00088 Invalidate(FALSE); 00089 } 00090 00091 void CBrandBand::SelectImage() 00092 { 00093 int screenDepth; 00094 RECT clientRect; 00095 int clientWidth; 00096 int clientHeight; 00097 int clientSize; 00098 HINSTANCE shell32Instance; 00099 BITMAP bitmapInfo; 00100 int resourceID; 00101 00102 screenDepth = GetScreenDepth(); 00103 GetClientRect(&clientRect); 00104 clientWidth = clientRect.right - clientRect.left; 00105 clientHeight = clientRect.bottom - clientRect.top; 00106 clientSize = min(clientWidth, clientHeight); 00107 if (screenDepth > 8) 00108 resourceID = gTrueColorResourceBase; 00109 else 00110 resourceID = g256ColorResourceBase; 00111 if (clientSize >= gLargeImageSize) 00112 resourceID += 2; 00113 else if (clientSize >= gMediumImageSize) 00114 resourceID += 1; 00115 shell32Instance = GetModuleHandle(L"shell32.dll"); 00116 fImageBitmap = LoadBitmap(shell32Instance, MAKEINTRESOURCE(resourceID)); 00117 GetObjectW(fImageBitmap, sizeof(bitmapInfo), &bitmapInfo); 00118 fBitmapSize = bitmapInfo.bmWidth; 00119 fMaxFrameCount = bitmapInfo.bmHeight / fBitmapSize; 00120 } 00121 00122 HRESULT STDMETHODCALLTYPE CBrandBand::GetBandInfo(DWORD dwBandID, DWORD dwViewMode, DESKBANDINFO* pdbi) 00123 { 00124 if (pdbi->dwMask & DBIM_MINSIZE) 00125 { 00126 pdbi->ptMinSize.x = 38; 00127 pdbi->ptMinSize.y = 22; 00128 } 00129 if (pdbi->dwMask & DBIM_MAXSIZE) 00130 { 00131 pdbi->ptMaxSize.x = 38; 00132 pdbi->ptMaxSize.y = 38; 00133 } 00134 if (pdbi->dwMask & DBIM_INTEGRAL) 00135 { 00136 pdbi->ptIntegral.x = 38; 00137 pdbi->ptIntegral.y = 38; 00138 } 00139 if (pdbi->dwMask & DBIM_ACTUAL) 00140 { 00141 pdbi->ptActual.x = 38; 00142 pdbi->ptActual.y = 38; 00143 } 00144 if (pdbi->dwMask & DBIM_TITLE) 00145 wcscpy(pdbi->wszTitle, L""); 00146 if (pdbi->dwMask & DBIM_MODEFLAGS) 00147 pdbi->dwModeFlags = DBIMF_UNDELETEABLE; 00148 if (pdbi->dwMask & DBIM_BKCOLOR) 00149 pdbi->crBkgnd = 0; 00150 return S_OK; 00151 } 00152 00153 HRESULT STDMETHODCALLTYPE CBrandBand::SetSite(IUnknown* pUnkSite) 00154 { 00155 CComPtr<IBrowserService> browserService; 00156 CComPtr<IOleWindow> oleWindow; 00157 CComPtr<IServiceProvider> serviceProvider; 00158 CComPtr<IProfferService> profferService; 00159 HWND parentWindow; 00160 HWND hwnd; 00161 HRESULT hResult; 00162 00163 fSite.Release(); 00164 if (pUnkSite == NULL) 00165 { 00166 hResult = AtlUnadvise(fSite, DIID_DWebBrowserEvents, fAdviseCookie); 00167 // TODO: revoke brand band service 00168 return S_OK; 00169 } 00170 hResult = pUnkSite->QueryInterface(IID_IDockingWindowSite, (void **)&fSite); 00171 if (FAILED(hResult)) 00172 return hResult; 00173 parentWindow = NULL; 00174 hResult = pUnkSite->QueryInterface(IID_IOleWindow, (void **)&oleWindow); 00175 if (SUCCEEDED(hResult)) 00176 hResult = oleWindow->GetWindow(&parentWindow); 00177 if (!::IsWindow(parentWindow)) 00178 return E_FAIL; 00179 00180 hwnd = SHCreateWorkerWindowW(0, parentWindow, 0, WS_VISIBLE | WS_CHILD | WS_CLIPSIBLINGS | WS_CLIPCHILDREN, NULL, 0); 00181 if (hwnd == NULL) 00182 return E_FAIL; 00183 SubclassWindow(hwnd); 00184 hResult = pUnkSite->QueryInterface(IID_IServiceProvider, (void **)&serviceProvider); 00185 if (SUCCEEDED(hResult)) 00186 { 00187 hResult = serviceProvider->QueryService(SID_SBrandBand, IID_IProfferService, (void **)&profferService); 00188 if (SUCCEEDED(hResult)) 00189 hResult = profferService->ProfferService(SID_SBrandBand, (IServiceProvider *)this, &fProfferCookie); 00190 hResult = serviceProvider->QueryService(SID_SShellBrowser, IID_IBrowserService, (void **)&browserService); 00191 if (SUCCEEDED(hResult)) 00192 hResult = AtlAdvise(browserService, (IDispatch *)this, DIID_DWebBrowserEvents, &fAdviseCookie); 00193 } 00194 // ignore any hResult errors up to here - they are nonfatal 00195 hResult = S_OK; 00196 SelectImage(); 00197 return hResult; 00198 } 00199 00200 HRESULT STDMETHODCALLTYPE CBrandBand::GetSite(REFIID riid, void **ppvSite) 00201 { 00202 if (ppvSite == NULL) 00203 return E_POINTER; 00204 if (fSite.p == NULL) 00205 { 00206 *ppvSite = NULL; 00207 return E_FAIL; 00208 } 00209 return fSite.p->QueryInterface(riid, ppvSite); 00210 } 00211 00212 HRESULT STDMETHODCALLTYPE CBrandBand::GetWindow(HWND *lphwnd) 00213 { 00214 if (lphwnd == NULL) 00215 return E_POINTER; 00216 *lphwnd = m_hWnd; 00217 return S_OK; 00218 } 00219 00220 HRESULT STDMETHODCALLTYPE CBrandBand::ContextSensitiveHelp(BOOL fEnterMode) 00221 { 00222 return E_NOTIMPL; 00223 } 00224 00225 HRESULT STDMETHODCALLTYPE CBrandBand::CloseDW(DWORD dwReserved) 00226 { 00227 ShowDW(FALSE); 00228 00229 if (IsWindow()) 00230 DestroyWindow(); 00231 00232 m_hWnd = NULL; 00233 00234 return S_OK; 00235 } 00236 00237 HRESULT STDMETHODCALLTYPE CBrandBand::ResizeBorderDW(const RECT* prcBorder, IUnknown* punkToolbarSite, BOOL fReserved) 00238 { 00239 return E_NOTIMPL; 00240 } 00241 00242 HRESULT STDMETHODCALLTYPE CBrandBand::ShowDW(BOOL fShow) 00243 { 00244 if (m_hWnd) 00245 { 00246 if (fShow) 00247 ShowWindow(SW_SHOW); 00248 else 00249 ShowWindow(SW_HIDE); 00250 } 00251 return S_OK; 00252 } 00253 00254 HRESULT STDMETHODCALLTYPE CBrandBand::HasFocusIO() 00255 { 00256 if (GetFocus() == m_hWnd) 00257 return S_OK; 00258 return S_FALSE; 00259 } 00260 00261 HRESULT STDMETHODCALLTYPE CBrandBand::TranslateAcceleratorIO(LPMSG lpMsg) 00262 { 00263 return E_NOTIMPL; 00264 } 00265 00266 HRESULT STDMETHODCALLTYPE CBrandBand::UIActivateIO(BOOL fActivate, LPMSG lpMsg) 00267 { 00268 return E_NOTIMPL; 00269 } 00270 00271 HRESULT STDMETHODCALLTYPE CBrandBand::GetClassID(CLSID *pClassID) 00272 { 00273 if (pClassID == NULL) 00274 return E_POINTER; 00275 *pClassID = CLSID_BrandBand; 00276 return S_OK; 00277 } 00278 00279 HRESULT STDMETHODCALLTYPE CBrandBand::IsDirty() 00280 { 00281 return S_FALSE; 00282 } 00283 00284 HRESULT STDMETHODCALLTYPE CBrandBand::Load(IStream *pStm) 00285 { 00286 return E_NOTIMPL; 00287 } 00288 00289 HRESULT STDMETHODCALLTYPE CBrandBand::Save(IStream *pStm, BOOL fClearDirty) 00290 { 00291 return E_NOTIMPL; 00292 } 00293 00294 HRESULT STDMETHODCALLTYPE CBrandBand::GetSizeMax(ULARGE_INTEGER *pcbSize) 00295 { 00296 return E_NOTIMPL; 00297 } 00298 00299 HRESULT STDMETHODCALLTYPE CBrandBand::OnWinEvent(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, LRESULT *theResult) 00300 { 00301 return E_NOTIMPL; 00302 } 00303 00304 HRESULT STDMETHODCALLTYPE CBrandBand::IsWindowOwner(HWND hWnd) 00305 { 00306 if (hWnd == m_hWnd) 00307 return S_OK; 00308 return S_FALSE; 00309 } 00310 00311 HRESULT STDMETHODCALLTYPE CBrandBand::QueryStatus(const GUID *pguidCmdGroup, ULONG cCmds, OLECMD prgCmds[ ], OLECMDTEXT *pCmdText) 00312 { 00313 return E_NOTIMPL; 00314 } 00315 00316 HRESULT STDMETHODCALLTYPE CBrandBand::Exec(const GUID *pguidCmdGroup, DWORD nCmdID, DWORD nCmdexecopt, VARIANT *pvaIn, VARIANT *pvaOut) 00317 { 00318 if (IsEqualIID(*pguidCmdGroup, CGID_PrivCITCommands)) 00319 { 00320 } 00321 else if (IsEqualIID(*pguidCmdGroup, CGID_BrandCmdGroup)) 00322 { 00323 switch (nCmdID) 00324 { 00325 case BBID_STARTANIMATION: 00326 StartAnimation(); 00327 return S_OK; 00328 case BBID_STOPANIMATION: 00329 StopAnimation(); 00330 return S_OK; 00331 } 00332 } 00333 return E_FAIL; 00334 } 00335 00336 HRESULT STDMETHODCALLTYPE CBrandBand::QueryService(REFGUID guidService, REFIID riid, void **ppvObject) 00337 { 00338 CComPtr<IServiceProvider> serviceProvider; 00339 HRESULT hResult; 00340 00341 if (IsEqualIID(guidService, SID_SBrandBand)) 00342 return this->QueryInterface(riid, ppvObject); 00343 hResult = fSite->QueryInterface(IID_IServiceProvider, (void **)&serviceProvider); 00344 if (FAILED (hResult)) 00345 return hResult; 00346 return serviceProvider->QueryService(guidService, riid, ppvObject); 00347 } 00348 00349 HRESULT STDMETHODCALLTYPE CBrandBand::GetTypeInfoCount(UINT *pctinfo) 00350 { 00351 return E_NOTIMPL; 00352 } 00353 00354 HRESULT STDMETHODCALLTYPE CBrandBand::GetTypeInfo(UINT iTInfo, LCID lcid, ITypeInfo **ppTInfo) 00355 { 00356 return E_NOTIMPL; 00357 } 00358 00359 HRESULT STDMETHODCALLTYPE CBrandBand::GetIDsOfNames(REFIID riid, LPOLESTR *rgszNames, UINT cNames, LCID lcid, DISPID *rgDispId) 00360 { 00361 return E_NOTIMPL; 00362 } 00363 00364 HRESULT STDMETHODCALLTYPE CBrandBand::Invoke(DISPID dispIdMember, REFIID riid, LCID lcid, WORD wFlags, DISPPARAMS *pDispParams, VARIANT *pVarResult, EXCEPINFO *pExcepInfo, UINT *puArgErr) 00365 { 00366 if (pDispParams == NULL) 00367 return E_INVALIDARG; 00368 switch (dispIdMember) 00369 { 00370 case DISPID_DOWNLOADCOMPLETE: 00371 StopAnimation(); 00372 break; 00373 case DISPID_DOWNLOADBEGIN: 00374 StartAnimation(); 00375 break; 00376 } 00377 return E_INVALIDARG; 00378 } 00379 00380 LRESULT CBrandBand::OnSize(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL &bHandled) 00381 { 00382 Invalidate(FALSE); 00383 return 0; 00384 } 00385 00386 LRESULT CBrandBand::OnEraseBkgnd (UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL &bHandled) 00387 { 00388 return 1; 00389 } 00390 00391 LRESULT CBrandBand::OnPaint(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL &bHandled) 00392 { 00393 PAINTSTRUCT paintInfo; 00394 HDC dc; 00395 POINT destinationPoint; 00396 HDC sourceDC; 00397 HBITMAP oldBitmap; 00398 RECT clientRect; 00399 RECT tempRect; 00400 00401 dc = BeginPaint(&paintInfo); 00402 GetClientRect(&clientRect); 00403 00404 destinationPoint.x = (clientRect.right - clientRect.left - fBitmapSize) / 2; 00405 destinationPoint.y = (clientRect.bottom - clientRect.top - fBitmapSize) / 2; 00406 00407 ::SetBkColor(dc, RGB(255, 255, 255)); 00408 00409 tempRect.left = 0; 00410 tempRect.top = 0; 00411 tempRect.right = clientRect.right; 00412 tempRect.bottom = destinationPoint.y; 00413 FillSolidRect(dc, &tempRect, RGB(255, 255, 255)); 00414 00415 tempRect.left = 0; 00416 tempRect.top = destinationPoint.y + fBitmapSize; 00417 tempRect.right = clientRect.right; 00418 tempRect.bottom = clientRect.bottom; 00419 FillSolidRect(dc, &paintInfo.rcPaint, RGB(255, 255, 255)); 00420 00421 tempRect.left = 0; 00422 tempRect.top = destinationPoint.y; 00423 tempRect.right = destinationPoint.x; 00424 tempRect.bottom = destinationPoint.y + fBitmapSize; 00425 FillSolidRect(dc, &paintInfo.rcPaint, RGB(255, 255, 255)); 00426 00427 tempRect.left = destinationPoint.x + fBitmapSize; 00428 tempRect.top = destinationPoint.y; 00429 tempRect.right = clientRect.right; 00430 tempRect.bottom = destinationPoint.y + fBitmapSize; 00431 FillSolidRect(dc, &paintInfo.rcPaint, RGB(255, 255, 255)); 00432 00433 sourceDC = CreateCompatibleDC(dc); 00434 oldBitmap = (HBITMAP)SelectObject(sourceDC, fImageBitmap); 00435 00436 BitBlt(dc, destinationPoint.x, destinationPoint.y, fBitmapSize, fBitmapSize, sourceDC, 0, fCurrentFrame * fBitmapSize, SRCCOPY); 00437 00438 SelectObject(sourceDC, oldBitmap); 00439 DeleteDC(sourceDC); 00440 00441 EndPaint(&paintInfo); 00442 return 0; 00443 } 00444 00445 LRESULT CBrandBand::OnTimer(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL &bHandled) 00446 { 00447 fCurrentFrame++; 00448 if (fCurrentFrame >= fMaxFrameCount) 00449 fCurrentFrame = 0; 00450 Invalidate(FALSE); 00451 return 0; 00452 } 00453 00454 HRESULT CreateBrandBand(REFIID riid, void **ppv) 00455 { 00456 CComObject<CBrandBand> *theMenuBar; 00457 HRESULT hResult; 00458 00459 if (ppv == NULL) 00460 return E_POINTER; 00461 *ppv = NULL; 00462 ATLTRY (theMenuBar = new CComObject<CBrandBand>); 00463 if (theMenuBar == NULL) 00464 return E_OUTOFMEMORY; 00465 hResult = theMenuBar->QueryInterface (riid, (void **)ppv); 00466 if (FAILED (hResult)) 00467 { 00468 delete theMenuBar; 00469 return hResult; 00470 } 00471 return S_OK; 00472 } Generated on Sun May 27 2012 04:22:54 for ReactOS by
1.7.6.1
|