Click here to Skip to main content
15,884,836 members
Please Sign up or sign in to vote.
0.00/5 (No votes)
I'm making a subliminal images program for me and to put it for free online, I want the pics to show fast on the screen (say one every 5 seconds, for the duration of 300 ms), I know how to do all except that the way I know to draw on the screen doesn't have another way of removing what the program drew on the screen and showing what was behind it except by redrawing the whole screen, also I want that if the user clicked by mistake a mouse click on the image which appears and fades fast, the program doesn't take the mouse click and passes it down to the thing in screen just below it.

If I make a borderless form it would take the mouse clicks and maybe the keyboard focus (maybe I can make it not able to be focused on as I remember maybe there's a way)

What I have tried:

C#
[DllImport("User32.dll")]
public static extern IntPtr GetDC(IntPtr hwnd);
[DllImport("User32.dll")]
public static extern void ReleaseDC(IntPtr hwnd, IntPtr dc);
//Get a Graphics object for the entire screen and draw a rectangle with it:
[DllImport("user32.dll")]
public static extern bool InvalidateRect(IntPtr hwnd, IntPtr lpRect, bool bErase);


IntPtr desktopPtr;
Graphics g;

            desktopPtr = GetDC(IntPtr.Zero);
            g = Graphics.FromHdc(desktopPtr);
            g.DrawImage(...)
            Thread.Sleep(300);
            InvalidateRect(IntPtr.Zero, IntPtr.Zero, true);

I solved it, but this draws the pic on the screen very slowly from top to bottom and I want an instant drawing of it...


I need to pass the mouse click down to the next windows just below it if the user mouse clicks on the form by mistake, the form gets closed immediately and the mouse click should be ordered in that exact place, this is for knowing the scaling factor of the display to order the mouse click in the correct position:
private float getScalingFactor()
{
Graphics g = Graphics.FromHwnd(IntPtr.Zero);
IntPtr desktop = g.GetHdc();
int LogicalScreenHeight = GetDeviceCaps(desktop, (int)DeviceCap.VERTRES);
int PhysicalScreenHeight = GetDeviceCaps(desktop, (int)DeviceCap.DESKTOPVERTRES);

float ScreenScalingFactor = (float)PhysicalScreenHeight / (float)LogicalScreenHeight;

return ScreenScalingFactor; // 1.25 = 125%
}

[DllImport("gdi32.dll")]
static extern int GetDeviceCaps(IntPtr hdc, int nIndex);

public enum DeviceCap
{
VERTRES = 10,
DESKTOPVERTRES = 117,

// http://pinvoke.net/default.aspx/gdi32/GetDeviceCaps.html
}

whether it's a right or left or middle click should be taken in consideration too.
Posted
Updated 12-Oct-21 13:14pm
v13
Comments
PIEBALDconsult 11-Oct-21 18:59pm    
Is that what your customers want?
john1990_1 11-Oct-21 19:04pm    
No, I need the pic to be drawn on the screen efficiently and not be drawn slowly from top to bottom, I made a borderless form which is another solution but it takes keyboard focus and consumes mouse clicks, is there a way to make a borderless form that can't get focus and doesn't "eat" mouse clicks and lets them go to the window just below it?

1 solution

Draw your images into Bitmaps so they are "ready to go" (you may have this already) and save them in a collection like a List.

Then create a UserControl based on a Picturebox, and add a Timer to the Picturebox in the Show event handler. handle the Tick event.
Add a "showing" flag to your control.
Add your own property called Images, which accepts the List of Images. When it is set, call a method to display an image.
In the show method call a method called DisplayImage.

In DisplayImage:
Set the Showing flag to true.
Set the Timer.Interval property to 300
Select an Image from the List, and set the controls Image property to the image. Set up for the next one.
Start the Timer.

In the Tick handler:
Check the Showing flag
If it's true, clear it, set the Interval to 5000, and clear the Image property.
Otherwise, set it, and call DisplayImage.

Then just add the control to your form, and set the Images property to your collection.
 
Share this answer
 
Comments
john1990_1 12-Oct-21 11:16am    
Thx, all this I already did, I put the images in "Image" not "Bitmap" one file each time and show the form only on LoadComplete of the pictrurebox, so it's the same, the only problem is that if the user presses with a mouse and the form appears so he presses on the form by mistake the click gets eaten, I think in that case I would close the form and order a mouse click on that exact location, how can this be done with taking into account display zoom scale ratio?
john1990_1 12-Oct-21 11:22am    
I added to the question.
Dave Kreskowiak 12-Oct-21 12:58pm    
I think he's trying to do this as an "overlay" on top of the Desktop and other applications?
john1990_1 12-Oct-21 12:59pm    
Dave would you please explain?
Dave Kreskowiak 12-Oct-21 13:00pm    
Me? No, YOU have to explain what you're trying to do.

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900