Now I want to launch a Windows 8 Metro App by a C# form application, but it's hard for me to find the right way...
I had tried these ways(I had installed the Metro App and registered a protocol):
1.
var success = await Windows.System.Launcher.LaunchUriAsync(new Uri("TestContent"));
In the "TestContent" above, I tried the protocol name registered on my computer and the Metro App's name, but the same error "Access Denied" occurred.
2.
Process p = new Process();
p.StartInfo.FileName = "ProtocolName://";
p.Start();
This time the Metro App only showed the splash screen but didn't launch the whole program.
Any ideas?
Thank you in advance.
2015/10/01 ADD:
After Reading this question:
[link]stackoverflow.com/questions/18787609/…
I think it is impossible to run a metro app from a windows form.
The right format to launch is :
Uri uri = new Uri("protocolname://anything");
await Windows.System.Launcher.LaunchUriAsync(uri);
And, Make sure that you're doing that from the foreground app, i.e. Not Background Task or a Toast notification or Tile .. etc.
After Reading this question:
C# Mixing WinRT and Windows Forms
I think it may be impossible to run a metro app from a windows form.
But when I try the code below :
Process p = new Process();
p.StartInfo.FileName = #"BINGMAPS://";
p.Start();
The BINGMAPS runs normally.
Did I miss any necessary setting in the Metro App?
First you need your app to handle protocol activation and then in App.xaml.cs in OnActivated event handle it to launch the first page or whatever page you want to call in Metro app. In C# form application using javascript set the current page content as the metro app. It will work.
Related
I'm playing with Microsoft's UWP AppServiceBridgeSample (here).
It is working well, but I would like to get rid of the console window of the BackgroundProcess application. The reason for this is that my BackgroundProcess starts another Win32 desktop application and works only as a mediator, so I don't want to disturb users with a console window. (Yes, it can be minimized, but I would rather not show it at all).
I have tried to hide it using the API mentioned here, but with no luck, the console window is still visible. Neither did switching the project's output type from Console Application to Windows Application.work.
Another thing I have tried was to create other BackgroundProcess project as a Windows application. It runs fine until I call AppServiceConnection.OpenAsync(), which causes the BackgroundProcess application to exitstrong text, thus the connection to UWA is not available.
static async void ThreadProc()
{
try
{
AppServiceConnection connection = new AppServiceConnection();
connection.AppServiceName = "CommunicationService";
connection.PackageFamilyName = Windows.ApplicationModel.Package.Current.Id.FamilyName;
connection.RequestReceived += Connection_RequestReceived;
AppServiceConnectionStatus status = await connection.OpenAsync();
//status check etc. ...
}
catch(Exception ex)
{
MessageBox.Show(ex.ToString());
}
}
It seems that opening the AppService connection is only possible from a console app.
So here are my two questions:
Is it, by any chance, even possible to hide the background process' console window?
Can I use the background process as a Windows application, without AppServiceConnection failing during OpenAsync calls?
Re 1: Go into the project settings and change the output type from Console to Windows app. Also make sure the Main() function doesn't exit until you are done with the background process. Here is a better sample that shows this with a Windows Application:
https://stefanwick.com/2017/05/26/uwp-calling-office-interop-apis/
Re 2: AppServiceConnection works the same way from a windowed application as well. Make sure you add the right reference to the Windows.winmd to be able to build. If you have trouble with that, please post a specific question with details of the problem you are seeing
I need to interact with another application, that resides in the tray.
I'm currenty using TestStack White this way:
ProcessStartInfo processStartInfo = new ProcessStartInfo("MyProg.exe");
Application application = Application.AttachOrLaunch(processStartInfo);
_window = application.GetWindows()[0];
Everything works if the application was not running before this call, since launching it, this is visible.
Instead, if the application was already running, and in the tray, White could not find any window, and I can see this in the console as the following log:
Could not find any windows for this application
...and, after some retries, it fails with an exception.
Now, the best solution I found is to kill the application and relaunch it:
application.Kill();
application = Application.Launch("MyProg.exe");
and this works.
But I guess there is a better solution to this.
Open the application you want to automate and print all the running process names, find which stands for the application.
The add the following code...
Application myApp;
myApp = Application.Attach("ProcessName");
Hope it helps...
Did you try attaching to the explorer.exe process?? Since the system tray icon for the app will reside under the explorer.exe.
Something like this:
Did you try attaching to the explorer.exe process?? Since the system tray icon for the app will reside under the explorer.exe.
Something like this:
Process _explorerProcess = Process.GetProcessesByName("explorer")[0];
application = Application.Attach(_explorerProcess.Id);
Window desktopWindow = application.GetWindows()[0];
You should then be able to interact with the system tray icon.
I need to launch or run an windows exe file from a OEM in Win store App.
can below be used? I try but have error but why since diagnostic is in the framework
using System.Diagnostics;
Process myProcess = new Process();
try
{
myProcess.StartInfo.UseShellExecute = false;
// here I point to the OEM windows exe file
myProcess.StartInfo.FileName = "C:\\HelloWorld.exe";
myProcess.StartInfo.CreateNoWindow = true;
myProcess.Start();
}
catch (Exception e)
{
Console.WriteLine(e.Message);
}
-- Update
# Michal :
Thank you. This method works using URI.
One problem :
the WinRT app goes into background after launching. How to make the winRT app not going background?
Is there any other way? I need to integrate the Exe from the OEM into Win Store App.
Note:
I want to know is this can be done or I am doing something which is not allowed?
If I didnot make my case clearer, please tell me what I miss.
I tried it but it did not work. So my solution should be using similar approach like Diagnostic but what it can be?
Recycling bits from https://social.msdn.microsoft.com/Forums/windowsapps/en-US/0a822355-909f-44b4-9c79-cb986087fe27/after-launching-or-activate-an-app-the-main-app-goes-into-background?forum=winappswithcsharp
This is expected behavior and there's no good way around it. Launching a file or protocol switches to the default handler with no expectation of return.
Launching an app via protocol like this a hack in the first place. Since you are a side-loaded app look into writing a Brokered Windows Runtime Component to allow proper use of desktop API and communication with a desktop back-end.
See the Brokered Windows Runtime Component docs at http://msdn.microsoft.com/en-us/library/windows/apps/dn630195.aspx
When you launch a console application by double-clicking it in explorer, the console is visible. However, if you run a console application through an already non-visible application, the console is invisible (maybe because it is trying to read the standard output or something).
So, how can I show my console window to the user even if the console application was started by a background app?
I already tried the ShowWindow and SetForeground Windows API without any luck. I also tried the following.
//paths for starting the server.
var processInformation = new ProcessStartInfo(myOwnPath);
processInformation.WorkingDirectory = myOwnWorkingDirectory;
processInformation.UseShellExecute = false;
processInformation.WindowStyle = ProcessWindowStyle.Normal;
processInformation.CreateNoWindow = false;
processInformation.RedirectStandardInput = false;
processInformation.RedirectStandardError = false;
processInformation.RedirectStandardOutput = false;
Process.Start(processInformation);
Any ideas?
Note: It is perfectly fine if the application needs to launch itself and shut down the old instance to get the console window visible.
Try setting UseShellExecute to true. Setting it to false lets you to redirect input, output, and error streams.
Is it possible to embed a DOS console in a Windows Form or User Control in C# 2.0?
We have a legacy DOS product that my Windows app has to interact with, and it's been requested that an instance of the legacy product should run within the Windows application.
At the moment, I'm using the user32.dll to locate the window that the DOS product is running in, minimising then maximising the window, and typing characters into the window. This isn't a very good solution to the problem, as it means my application has to store the window name in application settings, and requires that the user returns to the correct page of the DOS app before using the interaction function.
EDIT: Some more information
The legacy app needs to be visible to the user, but not in a separate window.
I've tried TimothyP's answer and it works very well, but is it possible to achieve the same functionality, but with the DOS window visually embedded in a windows form or user control instead of popping up in it's own window? Preferably in a ShowDialog() way so that the user cannot interact with the app wile they are in 'Legacy Mode', so to speak.
It's possible to redirect the standard input/output of console/dos applications using the Process class. It might look something like this:
var processStartInfo = new ProcessStartInfo("someoldapp.exe", "-p someparameters");
processStartInfo.UseShellExecute = false;
processStartInfo.ErrorDialog = false;
processStartInfo.RedirectStandardError = true;
processStartInfo.RedirectStandardInput = true;
processStartInfo.RedirectStandardOutput = true;
processStartInfo.CreateNoWindow = true;
Process process = new Process();
process.StartInfo = processStartInfo;
bool processStarted = process.Start();
StreamWriter inputWriter = process.StandardInput;
StreamReader outputReader = process.StandardOutput;
StreamReader errorReader = process.StandardError;
process.WaitForExit();
You can now use the streams to interact with the application.
By setting processStartInfo.CreateNoWindow to true the original application will be hidden.
I hope this helps.
Concerning your question on how to display the DOS app inside the Windows app.
There are a few solutions.
The first one is to simply not display the DOS app (with CreateNoWindow)
and "simulate" the UI of the DOS app in your Windows application by reading and writing to the streams.
The other solution would be to use the Win32API, get the Windows Handle (Whnd) of the Console/DOS application window and set its parent to your form. I'm currently not at home
and since it has been ages since I've done this, I can't remember by heart how it is done. If I'm not mistaken you'll need to use the following Win32 API calls:
FindWindow
GetWindow
SetParent
If I have some time left later today, I'll see if I can find better samples.
You can use the CreateProcess function and the hStdInput, Output, and Error members of the STARTUPINFO argument, this will allow you to intercept standard input and output of the application.