Closed Bug 252067 Opened 20 years ago Closed 20 years ago

Add support for translucent windows for Win32 (Windows 2000 and later)

Categories

(Core :: XUL, enhancement)

x86
Windows 2000
enhancement
Not set
normal

Tracking

()

RESOLVED FIXED
mozilla1.8alpha3

People

(Reporter: jonitis, Assigned: jonitis)

References

Details

Attachments

(6 files, 8 obsolete files)

(deleted), image/png
Details
(deleted), application/vnd.mozilla.xul+xml
Details
(deleted), image/png
Details
(deleted), patch
emaijala+moz
: review+
Details | Diff | Splinter Review
(deleted), patch
emaijala+moz
: review+
Details | Diff | Splinter Review
(deleted), application/octet-stream
Details
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.0; en-US; rv:1.7) Gecko/20040614 Firefox/0.9 Build Identifier: Mozilla/5.0 (Windows; U; Windows NT 5.0; en-US; rv:1.7) Gecko/20040614 Firefox/0.9 Patch available to implement translucent windows. Reproducible: Always Steps to Reproduce: See bug 113232 for more details Run Mozilla with -chrome from: http://bugzilla.mozilla.org/attachment.cgi?id=111901&action=view Actual Results: The window background is not transparent. Octopus is drawn on white background. Expected Results: The window background should be transparent This is a followup for bug 113232 that adds support for translucent windows for Windows 2000 and Windows XP. Older Windows versions will not support this because this patch uses UpdateLayeredWindow API function.
Attached patch diff -d -u -8 (obsolete) (deleted) — Splinter Review
Attached patch diff -d -u -8 -w (for review purposes only) (obsolete) (deleted) — Splinter Review
The changed files: 1. gfx/src/nsBlender.cpp 2. widget/public/nsIWidget.h (spelling and whitespace only) 3. widget/src/windows/nsWindow.h 4. widget/src/windows/nsWindow.cpp While learning widget code I noticed many spelling errors in comments which I fixed. I also replaced tab symbols with spaces. Both nsWindow.h and nsWindow.cpp were changed to make the indentation actually be 2 spaces as declared in header. These changes were not required, but I guess some cleanup is required from time to time. The real changes are at the end of nsWindow.cpp in #ifdef MOZ_XUL section. Because the new utility function GetTopLevelHWND was created I changed all places in nsWindow.cpp what were looking for topmost HWND to use it. I also replaced the GetNativeData(NS_NATIVE_WINDOW) with mWnd when it was called for 'this' or nsWindow type instead of nsIWidget. I also changed the conditions in WM_WINDOWPOSCHANGED part to check only for window growth to avoid useless system calls in case when window was minimized. This code was compiled with MS VS2003.NET compiler and is not tested with VS6. It is tested on Win98 where translucency is not supported. It works as expected on Windows XP On Windows 2000 the translucency works, but clicks on the buttons don't. Seems that something is wrong with coordinates because the button click is triggered when you click on the octopus image. This incompatibility between Win2K and WinXP is strange. Still have to investigate. At the moment I do not have access to Win2k machine to debug this - help wanted. Except Win2k mouse coordinate strangeness everything seems to work fine. Code is ready for review.
Could it be that Win2K is incorrectly compensating for non-existent window decorations? Dainis, does translucency (fractional alpha values) work if you throw a translucent PNG in there? I'd love to see a screenshot of that :-) In the future it's probably better to keep cleanup separate from actual functionality changes. Doing OnPaint at every Invalidate might not be a good idea, but let's not worry about that for now. We should be batching invalidates at a higher level via the view manager BeginUpdateViewBatch mechanism, anyway. In nsWindow::Update, I think you don't need to do anything in the translucent window case. The window is always up to date.
+ PRPackedBool mIsTranslucent; + + HBITMAP mMemoryBitmap; + HDC mMemoryDC; + PRUint8* mAlphaMask; These should be #ifdef XUL, right?
Memeber variables take only 13 bytes. Is it worth to put everything in MOZ_XUL if in most cases it will be defined? Then it will require too much #ifdef's... Probably I can always have mIsTransparent (which will always be PR_FALSE) and use conditional compilation only for mMemoryBitmap, mMemoryDC and mAlphaMask.
Attached image PNG with alpha transparency (deleted) —
> Probably I can always have mIsTransparent (which will always be PR_FALSE) and > use conditional compilation only for mMemoryBitmap, mMemoryDC and mAlphaMask. Sounds good. It's only 13 bytes, but it's 13 bytes per nsWindow widget. Thanks for the screenshot. Looks fantastic!
Assignee: nobody → Dainis_Jonitis
Status: UNCONFIRMED → NEW
Ever confirmed: true
Attached patch diff -d -u -8 (obsolete) (deleted) — Splinter Review
Attachment #153647 - Attachment is obsolete: true
Attached patch diff -d -u -8 -w (for review purposes only) (obsolete) (deleted) — Splinter Review
Attachment #153648 - Attachment is obsolete: true
Addressed Robert`s review notes: 1. Now all new member variables (including mIsTranslucent) are in #ifdef MOZ_XUL. Without define there should be zero overhead. The code size should shrink because of removal of duplicates of GetTopLevelHWND and unneeded GetNativeData. 2. nsWindow::Update for translucent windows does nothing. Currently I just commented out call to UpdateTranslucentWindow, because I do not know how to enforce the nsWindow::Update to be called and test what happens.
Attachment #153671 - Flags: superreview?(roc)
Attachment #153671 - Flags: review?(ere)
About mouse clicks not working right on Win2000. The WM_MOUSEMOVE, WM_LBUTTONDOWN and WM_LBUTTONUP are not generated if mouse cursor is in the non-client area. The vertical coordinate that starts generating messages is 23 pixels. When window is minimized and then restored everything starts to work as expected. Why this is different on Win2000 compared to WinXP is still unclear to me. Win2000 bug?
I suspect Win2K bug. The uses of translucent windows in Win2K did not respond to events. Are the horizontal coordinates also off by a little bit?
So when you mousedown over the octopus, the correct coordinates are generated in Win2K? You could try overriding WM_NCHITTEST to always return HTCLIENT if you think the cursor is in the window.
Aha, now I see why after minimizing/restoring it started to work. The WS_CAPTION style for topmost window has gone. If I change SetWindowTranslucencyInner to remove WS_CAPTION: HWND hWnd = GetTopLevelHWND(mWnd); LONG_PTR style = ::GetWindowLongPtr(hWnd, GWL_STYLE) & ~WS_CAPTION; LONG_PTR exStyle = ::GetWindowLongPtr(hWnd, GWL_EXSTYLE) & ~WS_EX_LAYERED; if (aTranslucent) exStyle |= WS_EX_LAYERED; ::SetWindowLongPtr(hWnd, GWL_STYLE, style); ::SetWindowLongPtr(hWnd, GWL_EXSTYLE, exStyle); it started to work on Win2k, too. Now I have to figure out why WS_CAPTION appeared on Win2k and test if it still works on WinXP.
Attached patch diff -d -u -8 (obsolete) (deleted) — Splinter Review
Attachment #153671 - Attachment is obsolete: true
Attached patch diff -d -u -8 -w (for review purposes only) (obsolete) (deleted) — Splinter Review
Attachment #153672 - Attachment is obsolete: true
Attachment #153671 - Flags: superreview?(roc)
Attachment #153671 - Flags: review?(ere)
Attachment #153790 - Flags: superreview?(roc)
Attachment #153790 - Flags: review?(ere)
The latest patch makes mouse clicks to work correctly on Windows 2000. Seems that Win2k has some limitation/bug that prevented HideWindowChrome to set window style if window previously was already set to WS_EX_LAYERED mode in SetWindowTranslucencyInner. To workaround that the WS_CAPTION bits are removed from style in the SetWindowTranslucencyInner, before WS_EX_LAYERED mode is set. Now this works on both Win2K and WinXP. Special thanks to Robert O'Callahan for initial implementation of translucency on GTK and being very helpful while working on this bug! Now we need MNG for really cool technology demos :)
+#ifdef MOZ_XUL + PRPackedBool mIsTranslucent; + HBITMAP mMemoryBitmap; + HDC mMemoryDC; + PRUint8* mAlphaMask; +#endif char mLeadByte; put mLeadByte above, among the packedbools. That might save some space. Where are mMemoryDC and mMemoryBitmap destroyed? + } else + { + ::DeleteDC(mMemoryDC); + ::DeleteObject(mMemoryBitmap); + delete [] mAlphaMask; I think you should set these to NULL here. + pPixel [0] = (*pAlpha * pPixel [0]) >> 8; + pPixel [1] = (*pAlpha * pPixel [1]) >> 8; + pPixel [2] = (*pAlpha * pPixel [2]) >> 8; Shouldn't this be division by 255? (I'm not sure.) If so, nsBlender.cpp has a fast way to do this. Other than that, I think it's ready.
Attached patch diff -d -u -8 (obsolete) (deleted) — Splinter Review
Attachment #153790 - Attachment is obsolete: true
Attachment #153791 - Attachment is obsolete: true
> put mLeadByte above, among the packedbools. That might save some space. Moved #ifdef MOZ_XUL above all PRPackedBool variables. Moved mIsTranslucent to the bottom of this define. Thus the define block starts with 4 byte HBITMAP which follows the other 4 byte HBRUSH. No memory alignment holes. > Where are mMemoryDC and mMemoryBitmap destroyed? DeleteDC and DeleteObject release the GDI objects. There are no GDI handle leaks. Now after relese I reset both mMemoryDC and mMemory bitmap to NULL and mAlphaMask to nsnull. > Shouldn't this be division by 255? (I'm not sure.) If so, nsBlender.cpp > has a fast way to do this. Now nsColor.h is included and FAST_DIVIDE_BY_255 macro used.
Attachment #153790 - Flags: superreview?(roc)
Attachment #153790 - Flags: review?(ere)
Attachment #153805 - Flags: superreview?(roc)
Attachment #153805 - Flags: review?(ere)
> DeleteDC and DeleteObject release the GDI objects. There are no GDI handle > leaks. I don't see where they are released when the nsWindow is destroyed normally.
> I don't see where they are released when the nsWindow is destroyed normally. Normally? Who would think about such rare condition :) Something like that in nsWindow::Destroy #ifdef MOZ_XUL if (mIsTranslucent) { ::DeleteDC(mMemoryDC); ::DeleteObject(mMemoryBitmap); delete [] mAlphaMask; mMemoryDC = NULL; mMemoryBitmap = NULL; mAlphaMask = nsnull; } #endif Now I will wait before updating patch every hour :)
Comment on attachment 153805 [details] [diff] [review] diff -d -u -8 This patch doesn't apply cleanly to nsWindow.cpp. I'd really really appreciate separate patches for the style and spelling fixes and the real functionality.
Attachment #153805 - Flags: superreview?(roc)
Attachment #153805 - Flags: review?(ere)
Attachment #153805 - Flags: review-
Functionality first, cleanup later? Or vice versa?
Attached patch step 1 of 2. New functionality only (obsolete) (deleted) — Splinter Review
Per Ere`s request I split the patch into the two parts. The first step adds only the new functionality, but skips all the whitespace cleanup, etc. I will attach the step 2 that does all the cleanup once this one will be in CVS and I will heave something to compare against. As written above the cleanup was not only the whitespace changes and spelling errors but also the optimizations in calling GetNativeData, GetTopLevelHWND, not calling API functions if window was getting smaller etc.
Attachment #154014 - Flags: superreview?(roc)
Attachment #154014 - Flags: review?(ere)
Attachment #153805 - Attachment is obsolete: true
Attachment #154014 - Flags: superreview?(roc) → superreview+
Comment on attachment 154014 [details] [diff] [review] step 1 of 2. New functionality only r=ere
Attachment #154014 - Flags: review?(ere) → review+
Patch checked in on behalf of Dainis. Please open a new bug for the cleanup work.
Status: NEW → RESOLVED
Closed: 20 years ago
Resolution: --- → FIXED
I had to back out the checkin as it doesn't compile in Visual C++ 6 or needs a newer Platform SDK than creature has.
Status: RESOLVED → REOPENED
Resolution: FIXED → ---
These errors were reported: c:/builds/tinderbox/MozillaTrunk/WINNT_5.0_Clobber/mozilla/widget/src/windows/nsWindow.cpp(7430) : error C2065: 'LONG_PTR' : undeclared identifier c:/builds/tinderbox/MozillaTrunk/WINNT_5.0_Clobber/mozilla/widget/src/windows/nsWindow.cpp(7430) : error C2146: syntax error : missing ';' before identifier 'style' c:/builds/tinderbox/MozillaTrunk/WINNT_5.0_Clobber/mozilla/widget/src/windows/nsWindow.cpp(7430) : error C2065: 'style' : undeclared identifier c:/builds/tinderbox/MozillaTrunk/WINNT_5.0_Clobber/mozilla/widget/src/windows/nsWindow.cpp(7431) : error C2146: syntax error : missing ';' before identifier 'exStyle' c:/builds/tinderbox/MozillaTrunk/WINNT_5.0_Clobber/mozilla/widget/src/windows/nsWindow.cpp(7431) : error C2065: 'exStyle' : undeclared identifier c:/builds/tinderbox/MozillaTrunk/WINNT_5.0_Clobber/mozilla/widget/src/windows/nsWindow.cpp(7431) : error C2039: 'GetWindowLongPtr' : is not a member of '`global namespace'' c:/builds/tinderbox/MozillaTrunk/WINNT_5.0_Clobber/mozilla/widget/src/windows/nsWindow.cpp(7431) : error C2065: 'GetWindowLongPtr' : undeclared identifier c:/builds/tinderbox/MozillaTrunk/WINNT_5.0_Clobber/mozilla/widget/src/windows/nsWindow.cpp(7441) : error C2039: 'SetWindowLongPtr' : is not a member of '`global namespace'' c:/builds/tinderbox/MozillaTrunk/WINNT_5.0_Clobber/mozilla/widget/src/windows/nsWindow.cpp(7441) : error C2065: 'SetWindowLongPtr' : undeclared identifier c:/builds/tinderbox/MozillaTrunk/WINNT_5.0_Clobber/mozilla/widget/src/windows/nsWindow.cpp(7574) : error C2065: 'AC_SRC_ALPHA' : undeclared identifier
Seems that old Platform SDK on build machines caused Tinderbox build errors: 1. nsWindow.cpp(7430) : error C2065: 'LONG_PTR' : undeclared identifier That could be fixed by using GetWindowLong and SetWindowLong instead of GetWindowLongPtr and SetWindowLongPtr. Older versions return LONG, but newer ones are 64-bit ready. 2. nsWindow.cpp(7574) : error C2065: 'AC_SRC_ALPHA' : undeclared identifier #ifndef AC_SRC_ALPHA #define AC_SRC_ALPHA 0x01 #endif
Regarding point 1, it would be nice to use #ifdefs or whatever to ensure that the code will stay working on Win64...
Attached patch This should fix build bustage (deleted) — Splinter Review
Attachment #154014 - Attachment is obsolete: true
1. I changed the GetWindowLongPtr to nsToolkit::mGetWindowLong (and same for setter). 2. Defined the missing constant. Someone can try to build with this?
Attachment #154395 - Flags: superreview?(roc)
Attachment #154395 - Flags: review?(ere)
Comment on attachment 154395 [details] [diff] [review] This should fix build bustage It looks ok to me, but you should ask someone with VC6 to try it. I don't have a VC6 build at hand right now.
Attachment #154395 - Flags: superreview?(roc) → superreview+
It compiled for me. Is there a testcase somewhere? "Chrome XUL for PNG with 256 levels of transparency" gives me a XUL error: XML Parsing Error: not well-formed Location: http://bugzilla.mozilla.org/attachment.cgi?id=153661&action=view Line Number 10, Column 74: <image src="http://bugzilla.mozilla.org/attachment.cgi?id=153660&action=view"/> -------------------------------------------------------------------------^ The "^" points to the = in "action=view".
That XUL wasn't properly XML-escaped. Try "dist\bin\mozilla -chrome http://bugzilla.mozilla.org/attachment.cgi?id=111901&action=view" But really, the main thing is that it builds. You used VC6, Chris?
Chris says he used VC6. Let's reland this ASAP
Comment on attachment 154395 [details] [diff] [review] This should fix build bustage I'll land it.
Attachment #154395 - Flags: review?(ere) → review+
Patch checked in.
Status: REOPENED → RESOLVED
Closed: 20 years ago20 years ago
Resolution: --- → FIXED
This breaks my Win32/MinGW/cygwin build with an error 'pUpdateLayeredWindow' undeclared. Earlier it has errors :- e:/mozilla/source/mozilla/widget/src/windows/nsWindow.cpp:7270: error: `WINUSERA PI' does not name a type e:/mozilla/source/mozilla/widget/src/windows/nsWindow.cpp:7273: error: extra `;' e:/mozilla/source/mozilla/widget/src/windows/nsWindow.cpp:7276: error: expected init-declarator before '*' token e:/mozilla/source/mozilla/widget/src/windows/nsWindow.cpp:7276: error: expected `,' or `;' before '*' token e:/mozilla/source/mozilla/widget/src/windows/nsWindow.cpp: In function `PRBool I sTranslucencySupported()': e:/mozilla/source/mozilla/widget/src/windows/nsWindow.cpp:7290: error: `pUpdateL ayeredWindow' undeclared (first use this function) e:/mozilla/source/mozilla/widget/src/windows/nsWindow.cpp:7290: error: (Each und eclared identifier is reported only once for each function it appears in.) e:/mozilla/source/mozilla/widget/src/windows/nsWindow.cpp:7290: error: `UpdateLa yeredWindowProc' undeclared (first use this function) e:/mozilla/source/mozilla/widget/src/windows/nsWindow.cpp:7290: error: expected primary-expression before ')' token e:/mozilla/source/mozilla/widget/src/windows/nsWindow.cpp:7290: error: expected `;' before '::' token e:/mozilla/source/mozilla/widget/src/windows/nsWindow.cpp: In member function `n sresult nsWindow::UpdateTranslucentWindow()': e:/mozilla/source/mozilla/widget/src/windows/nsWindow.cpp:7587: error: `pUpdateL ayeredWindow' undeclared (first use this function) make[5]: *** [nsWindow.o] Error 1
Status: RESOLVED → REOPENED
Resolution: FIXED → ---
I tried making navigator.xul's <window> be style="background-color:transparent", and there were 4 major issues: 1. No border/title bar. I'm guessing that's expected (it's the behavior in the testcase). 2. The content area is an empty gray box, and I don't see any page content. 3. Every time I open a menu (e.g. file menu), the rectangle it will occupy becomes transparent (I can see my desktop), then a moment later the menu appears. This is slow. 4. Loading the browser took a while - it seemed like my overflowed personal toolbar folder was moving bookmarks into the ">>" dropdown list one at a time.
After fix for bug 253108 "Translucent xul windows on gtk2 breaks gtk embedding" I checked how translucent windows work in mfcembed, viewer and winembed and mouse clicks on buttons did not worked. But do not panic - most likely I know what is wrong. Similarly as previous Win2K problem the WS_EX_LAYERED can not be used together with some other style flags. In the embeding clients the different window styles were used than in mozilla.exe and looks that some additional flags should be masked out in SetWindowTranslucencyInner(). BTW do we actually need system menu for windows with hidden chrome? Now HideWindowChrome leaves these flags on WS_SYSMENU | WS_MAXIMIZEBOX | S_MINIMIZEBOX. About MinGW build failure. The Platform SDK defines WINUSERAPI as #if !defined(_USER32_) #define WINUSERAPI DECLSPEC_IMPORT #else #define WINUSERAPI #endif I will try to fix both these problems in a couple of days. But I would like to first know your thoughts about system menu for translucent windows.
No system menu for translucent windows. Translucency should never be applied to windows that aren't top level; it should never be turned on for embedders' windows.
If someone wants to fix MinGW bustage immediately then please remove the WINUSERAPI from UpdateLayeredWindowProc declaration and check in the changes. Other declarations in nsWindow.cpp that use WINAPI (like HeapWalkProc, GetProcessHeapsProc) do not include WINUSERAPI in their declarations. WINUSERAPI expands to nothing anyway. typedef BOOL WINAPI UpdateLayeredWindowProc (...
Hmmm, I didn't expect it to work (I get paranoid about Win32 sometimes), but removing the WINUSERAPI as mentioned above fixed my Win32/MinGW/cygwin build. I'll leave it to Dainis to do the formal patch so he can fix all aspects in one patch. My local builds now have the patch, so I'm not concerned anymore.
Attachment #154656 - Flags: superreview?(roc)
Attachment #154656 - Flags: review?(ere)
Attachment #154656 - Flags: superreview?(roc) → superreview+
Comment on attachment 154656 [details] [diff] [review] Fix MinGW, ignore translucency for embedded apps, remove system menu for translucent windows r=ere
Attachment #154656 - Flags: review?(ere) → review+
The supplementary patch is now checked in.
Status: REOPENED → RESOLVED
Closed: 20 years ago20 years ago
Resolution: --- → FIXED
See bug 254191 for code cleanup.
I'm not seeing the correct behavior on Win 2000 sp4 with build 2004081709 (1.8a3). I'm still seeing the testcase with the white background instead of the transparent one.
(In reply to comment #56) Are you running Mozilla with a -chrome param like this? mozilla -chrome "file:///c:/warpzilla/mozilla/dist/bin/alphapng.xul" What video card are you using? Video driver version, DirectX version?
When I run it from the link in Comment #0 it shows the octopus on a white background. If I run it from the command line with a local copy of the file, it will make a tab in the taskbar, but nothing shows on the screen. And I have to kill Mozilla from the Task Manager. Right-clicking on the tab has no effect. Changing the xul file to a different background color will allow the window to appear, but obviously not transparent. GeForce2 MX Driver: 6.14.10.5216 DirectX 8.0
Attached file Standalone Win32 test application (deleted) —
(In reply to comment #58) Try standalone Win32 test application skintest.exe - should display the same octopus with alternating transparency. If this will work then the problem is somwhere Mozilla related, otherwise something is wrong with your config. > GeForce2 MX > Driver: 6.14.10.5216 > DirectX 8.0 Try installing DirectX 9.0c, nVidia ForceWare 61.77.
DirectX 9.0 and the new nVidia drivers fixed the problem. Thanks for the help.
DirectX 9.0c should not be a requirement (although strongly recommended), because the original Win2K had only 8.0. Looks that buggy nVidia drivers were causing the problem. That info could be added to knowledgebase or known problems list. I feel relief, knowing that is not a problem with my code :)
This excellent work has some nits needing shakeout. See dependancies. - N.
Status: RESOLVED → REOPENED
Depends on: 264707
Resolution: FIXED → ---
Why this bug was reopened? All symptoms in bug 264707 are present even without changes in this bug. This bug did not made any regressions - should be FIXED. For window transparency issues in anything older than Windows 2000 see bug 264708.
Status: REOPENED → RESOLVED
Closed: 20 years ago20 years ago
Resolution: --- → FIXED
Blocks: 297563
Please see bug 298889 which is attempting to address the behavior noted in comment 47.
Target Milestone: --- → mozilla1.8alpha3
Component: XP Toolkit/Widgets: XUL → XUL
QA Contact: xptoolkit.widgets
You need to log in before you can comment on or make changes to this bug.

Attachment

General

Creator:
Created:
Updated:
Size: