Moving the location and changing size of a external program - c#

By the term of external program, it refer to programs not developed by me.
I have 2 program that needs to be launch together, 1 of it is program developed by me, another is for instance, Window Media Player (just for example only).
These programs will be placed in a static position with no user interaction, so I need to configure their height width and their x/y coordinates. No issue for my own program, but for external program, will I be able to use window message to change their size as well as location.
I have never worked with window message before but I read up somewhere about sendMessage(), but I not sure of the command to move and resize.
My program is done in C#, and I hope to be able to do something like that

You can use the MoveWindow API
[DllImport("user32.dll", SetLastError = true)]
internal static extern bool MoveWindow(IntPtr hWnd, int X, int Y, int nWidth, int nHeight, bool bRepaint);
MoveWindow(ApplicationHandle, 600, 600, 600, 600, True);

If you have the HWND (obtainable through FindWindow or FindWindowEx), you can use SetWindowPos / MoveWindow.

Related

Permanently hide or move taskbar off screen windows 10 LTSB ENT

We need to hide the taskbar and start menu. We have an app that runs full screen, it is a touch screen application. Our touch screen application is 99.9999% always on screen, covering the entire screen. It is however a complex multimedia app and on rare occasions we have found it crashed exposing the desktop. We have a custom made Win10 LTSB ENT build which is robust and appropriate, but we want to go a step further. We want to remove the taskbar (which is 'hidden') from the desktop entirely.
We can hide the taskbar using the code below, but it keeps returning 5 seconds later. Something keeps undoing our 'hide' and restoring the taskbar without us doing anything.
Am I doing something wrong? Is there a service or mechanism in Windows OS I need to adjust?
private static void setTaskBar(bool hide)
{
IntPtr window = Program.FindWindow("Shell_traywnd", "");
if (hide)
Program.SetWindowPos(window, IntPtr.Zero, 0, 0, 0, 0, 128U);
else
Program.SetWindowPos(window, IntPtr.Zero, 0, 0, 0, 0, 64U);
[DllImport("user32", SetLastError = true)]
private static extern IntPtr FindWindowEx(
IntPtr hWndl,
IntPtr hWnd2,
string lpsz1,
string lpsz2);
}
[DllImport("user32")]
private static extern bool SetWindowPos(
IntPtr hWndl,
IntPtr hWndInsertAfter,
int X,
int Y,
int cx,
int cy,
uint uFlags);
The taskbar is somewhat special, it receives messages from the window manager when other windows go in and out of fullscreen etc and adjusts itself accordingly.
Messing with the shell is the wrong solution. A better solution would be to launch another instance of your program that only has a fullscreen window and does nothing but waiting for the real instance to crash and then restart it if desired.

Show popup in background wpf

The task is this: I need to be able to show popup from my application but doing so should not interact with user typing something in skype, playing games, etc. The window of the application should me opened if it's minimized.
I have the instance of my Main Window. This instance contains code that will show the popup. Thing is I can't use something like this:
window.ShowActivated = false;
simply because this seams to work only if the window is first shown (which is not - the application is already running when I need to call the popup).
Now the other approach that works is using win api.
[DllImport("user32.dll")]
static extern IntPtr GetActiveWindow();
[DllImport("USER32.DLL")]
public static extern bool SetForegroundWindow(IntPtr hWnd);
var currentForegroundWindow = GetActiveWindow();
window.Show();
SetForegroundWindow(currentForegroundWindow);
What are my concerns - if user is playing game or has low performance PC I can interrupt his actions and he can actually see the window I'm trying to show (which is annoying). So I tried this:
[DllImport("user32.dll", SetLastError=true)]
static extern bool SetWindowPos(IntPtr hWnd, IntPtr hWndInsertAfter, int X, int Y, int cx, int cy, SetWindowPosFlags uFlags);
SetWindowPos(window.Handle, Bottom, 0, 0, 0, 0, NOREDRAW | NOACTIVATE | NOMOVE);
Now this seams to be ideal. I should be showing the window and I should show it on the bottom. But - it simply don't do the trick. Am I doing something wrong?

SendMessage() only working when window is open, not when minimized

I've been using SendMessage to send mouse clicks to a couple of windows. One being a game(everything works perfectly), but the other window, being a 3rd party tool for the game is having trouble with SendMessage. If the window is 'not minimized' everything works fine, don't matter if window is completely covered up by another. But if that same window is minimized then nothing happens, I checked with spy++ and the messages are indeed getting received but not being processed (correct term?). I've tried to solve this last couple days, doing both searches on here and Google alike, many of topics but nothing helped?
//MyImports
[DllImport("user32.dll", CharSet = CharSet.Auto)]
static extern IntPtr SendMessage(IntPtr hWnd, UInt32 Msg, IntPtr wParam, IntPtr lParam);
[DllImport("user32.dll", SetLastError = true)]
static extern IntPtr FindWindow(string lpClassName, string lpWindowName);
And this is how I have it wrapped
public static void LClick(string windowclass, int x, int y)
{
IntPtr WHandle = FindWindow(windowclass, null);
SendMessage(WHandle, (int)WMessages.WM_LBUTTONDOWN, (IntPtr)1, (IntPtr)MakeLParam(x, y));
SendMessage(WHandle, (int)WMessages.WM_LBUTTONUP, (IntPtr)0, (IntPtr)MakeLParam(x, y));
}
I have tried focus, activate. One thing that might be useful info is that the third party program is being loaded as module("Qt5QWindowIcon") of the game.
I tried PostMessage as well, and it does the same thing as SendMessage() same problem when minimized.
This game does allow for macroing and unattended macroing, Hints the third part tool designed to execute the macros (published by the creators) I'm just trying to simulate a mouse click on the program to start the macro.
I would just use SendInput, but the entire purpose of my program is to run in background.
I 've faced same problem .Please change assembly name and project name (Changed name not started with name on that you are throwing/posting windows message)then rebuild it and check it. Now you will able to debug.

How do I get the position of a form and the screen it is displayed on, and restore that the next time my form is displayed?

I have 2 monitors and I need to save form position and it should show on screen where it was closed.
Can someone suggest how to get screen on which it is, and on form load show it on screen where form was closed?
The settings I save in registry.
The simplest way is to call the GetWindowPlacement function. That returns a WINDOWPLACEMENT structure that contains information about the window's on-screen coordinates.
Using this function instead of the Form.Location property solves the problems you'll experience with multiple monitors, minimized windows, strangely positioned taskbars, etc.
The route of attack would be to call the GetWindowPlacement function when your application is shutting down, persist the location of the window to the registry (or wherever you are storing it—the registry is no longer the recommended place for saving application state), and then when your application is re-opened, calling the corresponding SetWindowPlacement function to restore the window to its previous position.
Since these are native functions exposed by the Win32 API, and you're working in C#, you'll need to call them via P/Invoke. Here are the required definitions (for organizational purposes, I recommend placing these in a static class named NativeMethods):
[StructLayout(LayoutKind.Sequential)]
struct POINT
{
public int X;
public int Y;
}
[StructLayout(LayoutKind.Sequential)]
struct RECT
{
public int left;
public int top;
public int right;
public int bottom;
}
[Serializable]
[StructLayout(LayoutKind.Sequential)]
struct WINDOWPLACEMENT
{
public int length;
public int flags;
public int showCmd;
public POINT ptMinPosition;
public POINT ptMaxPosition;
public RECT rcNormalPosition;
}
[DllImport("user32", SetLastError = true)]
[return: MarshalAs(UnmanagedType.Bool)]
static extern bool GetWindowPlacement(IntPtr hWnd, ref WINDOWPLACEMENT lpwndpl);
[DllImport("user32", SetLastError = true)]
[return: MarshalAs(UnmanagedType.Bool)]
static extern bool SetWindowPlacement(IntPtr hWnd, ref WINDOWPLACEMENT lpwndpl);
To get the current position of your window (which you would do when your app is closing), use this code:
WINDOWPLACEMENT wp = new WINDOWPLACEMENT();
wp.length = Marshal.SizeOf(wp);
GetWindowPlacement(MyForm.Handle, ref wp);
Recall that I mentioned the registry is no longer the recommended place for persisting application state. Since you're developing in .NET, you have much more powerful and versatile options available. And since the WINDOWPLACEMENT class declared above is marked [Serializable], it would be very easy to serialize this information to your application settings, and then reload it the next time you open.
I implemented a similar functionality a lot of times. All you have to do is save the Form.WindowState, Form.Size and Form.Loaction properties when the form is closed and restore them when the form is opened.

Is it possible to completely prevent multiple instance on .NET Compact Framework?

Since I've try many ways to stop the multiple instance problem on handheld device which running on .net compact framework 3.5.
Currently , I got the solution by create "Mutex" and check if there is the same process is running. I put this statement in "Program.cs" which will executed at first time when program start.
But i think it's not shoot my problems cause I got request from user that they need to disable the "program icon" while it's running.
I understand the user's point that sometime they maybe "Open" the program multiple times or more within short period. So , If it still able to "Open". That mean the program will need to initial itself and maybe going fail finally. Is it possible to absolutely prevent the multiple instance ? or is there another way without programming like edit the registry on Windows CE ?
Here is my source code:
bool firstInstance;
NamedMutex mutex = new NamedMutex(false, "MyApp.exe", out firstInstance);
if (!firstInstance)
{
//DialogResult dialogResult = MessageBox.Show("Process is already running...");
Application.Exit();
}
NamedMutex is class from OpenNetCF.
Your code is almost fine. only missing thing is to remove the application exit and put in there the code needed to bring current running instance on top. i did this in the past so you do not need to disable or hide the icon you simply detect the already running instance and bring it on foreground.
Edit:
here some code snippet:
[DllImport("coredll.dll")]
private static extern IntPtr FindWindow(IntPtr className, string windowName);
[DllImport("coredll.dll")]
internal static extern int SetForegroundWindow(IntPtr hWnd);
[DllImport("coredll.dll")]
private static extern bool SetWindowPos(IntPtr hwnd, int hwnd2, int x,int y, int cx, int cy, int uFlags);
if (IsInstanceRunning())
{
IntPtr h = FindWindow(IntPtr.Zero, "Form1");
SetForegroundWindow(h);
SetWindowPos(h, 0, 0, 0, Screen.PrimaryScreen.Bounds.Width,Screen.PrimaryScreen.Bounds.Height, 0x0040);
return;
}
check these links for more info...
http://www.nesser.org/blog/archives/56 (including comments)
What is the best way to make a single instance application in Compact Framework?

Categories