We have a fairly complex GUI, so when certain windows are resized their Redraw() is set to false till the operation is completed. The problem with this is that if the OS "Show window content while dragging" setting is checked, when decreasing the window's size the windows behind it are not repainted. This means I have to force the repaint myself so the remains of the resized window are deleted. I have no problem getting the dimensions of the region that was uncovered. What I'm looking for is best way to cause all windows within that region to repaint their part.
Not being much of a GUI programmer, I can traverse the uncovered region and list the windows in it. Then, I can ask each one of them to repaint its part. But I'm quite certain there has to be a better way to do this...
It is worth mentioning the app is written in PowerBuilder. This means I can call whatever Win32 function I'd like, but have limited control over the GUI behavior and the message handling. If there's a better way to prevent the window's content resize from being visible, or there's a way to make a non-redrawn window clean after itself, I'd love to hear it (just have the limitations above in mind).
I'm curious what version of PowerBuilder you are working in? I do resizing all the time and never run into issues like you are describing.
Maybe you can lay out some more detail on why you need to set your redraws to false within the PowerBuilder environment.
Hope I can help.
Related
I develop audio plugins, which are run inside their hosts and work realtime. Each plugin has its own window with controls, which often contains some kind of analysis pane, a pretty big rectangle that gets repeatedly painted (e.g. 20-50x per second). This is all working well.
The trouble comes when the user adjusts a parameter - the plugin uses WM_MOUSEMOVE to track mouse movements and on each change calls ::InvalidateRect to make the relevant portion of the window be redrawn. If you move quickly enough, the window really gets quickly repainted, however there seems no time for the host and other windows to be redrawn and these usually perform some kind of analysis feedback too, so it is really not ideal.
No my questions:
1) Assuming the host and other window are using ::InvalidateRect too, why mine is prioritized?
2) How to make ::InvalidateRect not prioritized, meaning the window needs to be invalidated, but it may be later, the rest of the system must get time for their redrawing too.
Thanks in advance!
It is possible to use the SetWindowPos API on Windows to keep a windows always on top of other windows, and there are many questions on StackOverflow dealing with this.
It is possible to keep only part of a Window always visible? I.e. specify a clipping region inside an existing window, and keep only that part visible?
A use case would be the following (on Windows):
User clicks on icon to run app.
User highlights a portion of the screen to focus on (similar to the Snipping Tool on Windows 7)
The highlighted part of the screen remains always visible, even when other windows/programs are moved over the selected region.
I know the issues that would spring up with having other applications that are also set to being topmost. Just curious if this is even possible?
Even if you change part of your window to be transparent to what's below (with a clipping region) it's still going to take all the mouse clicks, etc. that occur over the transparent part.
Your best bet is to create a new smaller window and make it top-most while hiding the main one.
My application is a Windows Forms one.
I tried using the windows wallpaper, but this depends on the "Fill", "Stretch", "Fit" or "Tile" settings.
I just need the image as it is on the desktop, but including the part "under" the taskbar, because this part is visible in case of transparent taskbar.
Why I need this?
Because I have a tray application which slides from under the taskbar when opening. And I need to set a mask there, so it can't be seen sliding, until it reaches the top of the taskbar. Again, this is only a problem when the taskbar is transparent.
I am not sure if I understood your question correctly. But to me, it seems that you need the image that has created wallpaper. If it seems easier, take a look at registry entries at following location:
HKEY_CURRENT_USER\Control Panel\Desktop
This will give you the path, size, tile/no tile etc. information for the wallpaper.
There is a Win32 function called PaintDesktop you could try but unless I'm misunderstanding things you should be able to just adjust the height of your window so it is never really behind the taskbar...
Why I need this? Because I have a tray application which slides from under the taskbar when opening. And I need to set a mask there, so it can't be seen sliding, until it reaches the top of the taskbar. Again, this is only a problem when the taskbar is transparent.
The problem here is that you're starting the slide up from the bottom of the entire screen, rather than starting from the bottom of the screen's working area (i.e., the top of the taskbar). That's why you're seeing the pop-up window slide up behind a transparent taskbar.
Luckily, the solution is much simpler than obtaining the desktop background and/or doing any type of masking. It's also much faster, and it's always good that your eye candy isn't unnecessarily taxing the user's computer.
All you need to do is determine the coordinates of the screen's working area, which is defined by Windows as the area that can be used by applications, not including the taskbar and other side bars. You can obtain this information easily in WinForms by querying the Screen.PrimaryScreen.WorkingArea property. This will return a Rectangle that corresponds to the primary screen's working area. Since you know that the taskbar is always displayed on the primary screen, this is exactly what you want.
Once you have the coordinates of the primary screen's working area, start your pop-up window's slide from the bottom of that.*
This is a good lesson of why you should always include an explanation of why you want to accomplish something. There's often an even better way that you haven't thought of.
*Of course, I'm ignoring the fact that a user might not have their taskbar positioned at the bottom of the screen. You can put it on either side or even on top. It sounds to me like you haven't considered this in your question, either. If this is an app that you're writing only for yourself or for a controlled environment where you can be sure that no one has their taskbar in non-default positions, that might be OK. But if you're writing software to distribute to a wider audience, you will need to take this into account. The rcWork coordinates will be correct, regardless of where the taskbar is positioned, of course, but you will need to know whether to start the pop-up window's slide from the bottom, the left side, the right side, or the top.
Is it possible to create an invisible X window? For initialization of an OpenGL ES 2.0 context, one has to create a X window manually, but I can't find a way to make it invisible. Since I'm only doing GPGPU I don't need an output window. In fact, it is rather annoying in my case.
I'm aware of a solution from an earlier question, where it has been pointed out to use InputOnly in XCreateWindow(). This, however, leads to the X error GLXBadDrawable. Probably because EGL requires the window to respond to graphics request. Is there another way? Maybe create it minimized? But I can't find anything on that either. Also setting the window's size really small doesn't help, since it always occupies the whole screen on my device (Nokia N9).
When you create an X window, it is created unmapped, so what about creating an InputOutput window and leaving it unmapped? Another option would be (if the window must stay mapped), to move it out of the screen.
I previously asked a question about changing the cursor system-wide on OSX. I used NSCursor to change the cursor, but the effects are only as long as the application is active. When another application becomes active, the custom cursor is lost.
Here is a related, more general question. How can you write an application to have system-wife effects? For example drawing an image on-screen even when your application is not active, and something else is?
I understand I probably need to go at a lower level than the Cocoa APIs. I just cannot figure out where to start looking? Any specific Carbon APIs that I need to be looking at? Or even lower?
Any pointers would be appreciated! If you specifically know how to change the cursor system-wide or how to draw an image and move it around (no matter what application is active), that would solve my current problem as well! Can I write an application that can achieve this when its installed on the system?
Thanks!
You can achieve the effect you want, but not the way you're thinking about doing it.
You say,
I am writing a presentation aid application that shows the equivalent of the "laser pointer" on screen, programmatically. My first idea was to use the mouse cursor itself as the pointer, and change its appearance as a red circle.
Then fake that. Create an application, perhaps of type LSUIElement, perhaps not, depending on the behavior you want. Create a borderless window (type NSBorderlessWindowMask) and fill it with a clear color. Set its window level high enough so that it floats over everything (using -[NSWindow setLevel:], though I can't think of what the best level would be off-hand), and draw into it.
It's true that you cannot set the cursor when you are not the foremost app. It's true that you cannot just scribble on the screen. But you can get the same effects if you're clever.
This behaviour is not provided by any APIs on Mac OS X. You would have to modify the resource files in the OS, and that's a very dangerous operation that could brick the target computer. You have to know what you're doing.
Are you trying to implement a theming app or something like that? What's your goal? If you tell us what you are trying to do, we may be able to suggest alternate approaches.