Using embedded text files in a rt app - c#

this might be a stupid question, but I just can't seem to figure out how to access my text files that I embedded in my app. I know several ways to do it for desktop apps (through searching for ways to do it for rt apps) but have never found a way to do it for rt apps. This has been bugging me for MONTHS!

Anything in your app package can be referred to using an ms-appx:/// URI (the three /// are important), and opened with StorageFile.GetFromApplicationUriAsync (a static method, see http://msdn.microsoft.com/en-us/library/windows/apps/windows.storage.storagefile.getfilefromapplicationuriasync.aspx).
You can also get your package's StorageFolder object through Windows.ApplicationModel.Package.InstalledLocation, see http://msdn.microsoft.com/en-us/library/windows/apps/windows.applicationmodel.package.installedlocation.aspx. Then you use StorageFolder.GetFileAsync (http://msdn.microsoft.com/en-us/library/windows/apps/windows.storage.storagefolder.getfileasync.aspx) with a relative pathname.

Related

How to retrieve an icon/image from the window of a running UWP application?

I am able to get icons from non-UWP apps with the following code:
from win32con GCL_HICON, WM_GETICON,
from win32gui import GetClassLong, SendMessageTimeout
_, icon_handle = SendMessageTimeout(hwnd, WM_GETICON, 1, 0, 0, 50)
if icon_handle == 0:
icon_handle = GetClassLong(hwnd, GCL_HICON)
if icon_handle == 0:
return Settings.BLANK_ICON
Documentation says that the next step should be using LoadIcon/LoadImage to extract it from the executable, but I've tried to avoid that.
SO post says UWP app icon path could be retrieved by SHLoadIndirectString (ctypes.windll.shlwapi.SHLoadIndirectString from Python), but that topic deals with the files associations found in the registry - an open window isn't the starting point.
How can I retrieve that "indirect string" having just a window handle? Or maybe someone knows about some other solution to this problem, I'm interested in any type of icon/image I can get.
EDIT: accepted answer together with this answer reveals a way to solve this with Python and ctypes.
There is not just one icon for a UWP app, there may be many, to be able to adapt to a specific device, form factors, etc.
As #Simon Mourier said, Most of "modern app" (or Windows Store apps, or apps in the AppX application model) information can be queried from official APIs.(I'm just a porter)
You can start with the GetPackageFullName function (it gets the package full name for the specified process). Once you get a package full name, you can use the Package Query API to get more information.
These API are native one, so they don't have equivalent in the .NET Framework to my knowledge. However, they are accessible from WinRT application somehow (and you can indeed access some of the WinRT APIs from standard .NET Framework apps, but this is kindof hack).
The images contained in these apps are special, because they are defined as resources (assets) keys that can be tweaked using qualifiers to form a final path. This is documented for example here: How to name resources using qualifiers (HTML) and here: Quickstart: Using file or image resources (HTML).
The problem is what you can find depends heavily on the application itself, so it's not super easy to determine what image you can use and I have not found any API for this, so I have coded a sample that gets the highest scale image for a given resource name as an exemple (FindHighestScaleQualifiedImagePath). You can load a WPF BitmapSource (or any other imaging platform resource) from this path.
Samples is included in the link provided. For details, please refer to:
Get Icon from UWP App

Get path to any file on the computer in UWP app

I am developing a UWP app for the first time. I always used Windows Forms and WPF, but the potential design of these apps is gorgeous, but the problem is they are kind of sandbox, especially for my current project. Basically, I am making a games launcher, where you add your games and the program creates a list of games. (Think of it like a Steam for everything with a modern Windows 10 Material design).
Now, I managed to do almost everything, but two things. First, and most important, is getting the path to the game. I create a file picker, I can pick the .exe files, I can get their names, but the file.Path property doesn't work, it returns a null path. I thought this might be because of UWP's sandboxed design, but I got far into this, that I really don't want to abandon it.
The second problem would be the launching of these files. I managed to do it on Steam games using Steam's specific URI. ("steam://rungameid/xxxxxx" where xxxxxx is the game id) But it doesn't work if I just put a path as a URI.
What do you think? Are there any solutions? Let me show you some of the related code:
public async void SelectEXE()
{
var picker = new Windows.Storage.Pickers.FileOpenPicker
{
ViewMode = Windows.Storage.Pickers.PickerViewMode.Thumbnail,
SuggestedStartLocation = Windows.Storage.Pickers.PickerLocationId.PicturesLibrary
};
picker.FileTypeFilter.Add(".exe");
Windows.Storage.StorageFile file = await picker.PickSingleFileAsync();
if (file != null)
{
stuffWrite[0] = file.Name;
stuffWrite[1] = file.Path;
count++;
WriteCount();
WriteItem(count, string.Join(",", stuffWrite));
UpdateList();
}
}
async void LaunchGame(string uriToLaunch)
{
Uri uri = new Uri(uriToLaunch);
games_list.Items.Add(uriToLaunch);
uri = new Uri("steam://rungameid/730"); //replace with actual path
await Windows.System.Launcher.LaunchUriAsync(uri);
}
Sandbox restrictions make it so that getting the path from that property will not reliably work, as Ahmed pointed out.
As for launching, you can't launch exe files directly from a UWP app. It's simply not possible as it is explicitly restricted from doing so by design. Some workaround solutions to your problem:
Use Steam to launch non-Steam games. You can add non-Steam shortcuts and this creates a SteamID based on the file's path so you can launch it from the UWP app using a URI. I found the algorithm to launch any exe using the Steam URI scheme from this board post and follow the link to the person's Python project source code.
Create a helper Win32 app that does the launching for you. In my app suite I communicate between the UWP and Win32 using WebSocket. There are also new solutions to integrate Win32 apps into UWP like Desktop Bridge and full trust Win32.
Use a 3rd party scripting tool like AutoHotkey. Have your UWP app generate the string of a script to launch the game, and save the text file with extension that launches that script language by default. You can then use the Launcher class to launch the file, which the scripting app will open with by default and then it will launch the game. I doubt your app would be accepted on the Windows Store if you did this.
Consider not using UWP at all. There are some libraries to make WPF look more modern as I'm sure you know.

What's the default file path in WinRT/WP 8.1?

Hello fellow programmers.
I recently made a mistake while using the SQLite-NET package for Windows Phone 8.1. When opening a new SQLiteConnection, I would give as parameter to its constructor the string "data.db", without being actually aware of what was going on under the hood. Later on, I noticed that the file wouldn't be deleted, even if I uninstalled the application (since I would have in my app the same entries that I had before uninstalling it); I assume that I should be using the local folder for application data instead.
However, here is the real question: what the hell is the folder where the data.db file was created? I tried to figure it out with the following piece of code:
var file = await StorageFile.GetFileFromApplicationUriAsync(new Uri("ms-appx:///data.db"));
System.Diagnostics.Debug.WriteLine(file.Path);
and what I got as output of the WriteLine method was the path
C:\Data\SharedData\PhoneTools\AppxLayouts\f7529f24-ba24-4fdb-8353-cff9214180a0VS.Debug_ARM.Valbrand\data.db,
which only got me even more confused. I couldn't find any satisfactory info on this, and I would REALLY like to further my understanding of what happened here.
Thanks in advance!
The path you are looking at is the install directory of your app. You have a Silverlight 8.1 app, so the path is slightly different than a Silverlight 8.0 app, but the articles here and here will help you get a rough understanding.
The recommended usage of this directory is to take the resources that you want backed up out of it on first run and move them to the app data container, so they can be backed up by the system.
C:\Data\SharedData\PhoneTools\AppxLayouts\f7529f24-ba24-4fdb-8353-cff9214180a0VS.Debug_ARM.Valbrand\data.db
This is the path on your phone/emulator.
And This is not the location where you can find in your PC.

Windows Form Application : Publish issue

I'm very new to Visual Studio 2010. I decided to create a simple WFA with C#.
Everything work fine with Images and Audio playback. My intention is to create a standalone application and send it to my friend as a gift. Problem I facing now is that when I tried to publish the application, the Images / Audio is still using the same location in my PC. So it won't play nor display any images.
Any comment on this or guide for me? I did try search for solution but doesn't seems to have any luck.
This is the code that I used to play Audio :
SoundPlayer ply = new SoundPlayer(#"C:\Users\Liam619\Documents\Visual Studio 2010\Projects\BirthdayApp\BirthdayApp\Resources\BirthdaySong.wav");
If I remove or change the path, the Application will hit error for locating the Audio file.
There may be several solutions to your problem.
a) embed the sound into a resource. As a beginner, resources may be a bit tricky to get it right the first time. But I want to encourage you reading something about it. You'll need resources when you want to translate your first program.
b) create an installer which copies the sound file to the installation directory. Try InnoSetup. If you're a programmer, sooner or later, you'll need to create a Setup anyway. Always worth knowing how to do that.
In that case, you still need the path to the sound file, but if you install your EXE into the same path as the sound file, see getting the application's executable directory.
everything in the database whether images or audio refers to your own server database.you have to send the database too with the app and the correct version .NET framework needs to be installed on the target PC.

WinRT: App to enumerate files outside libraries and known folders

I am working on a Metro app that shows the content of a given folder in a ListView control.
MS decided that developers don't need the System.IO.Directory class and removed it entirely from the framework.
I am looking for a replacement to enumerate files in C# in a metro style app. I have checked all the enumeration samples provided by MS and they all seem to only enumerate the Windows Libraries using the KnownFolders class, something like:
StorageFolder picturesFolder = KnownFolders.PicturesLibrary;
and calling the GetFilesAsync() or GetFoldersAsync() methods depending on your needs. These are all gold if I wanted to enumerate only inside the pictures or music library. However I am looking to enumerate files on directories that are not included in a library.
Anyone knows how this is possible in WinRT???
You are, by design, extremely limited in this area for Metro apps. The idea is that a Metro app is only given access to those things that it is trusted to access, so you can either:
access local storage, specific to your application
access a handful of well-known storage locations, or
access a specifically granted location.
Take a look at http://msdn.microsoft.com/en-us/library/windows/apps/hh464959.aspx to get an idea as to what you'll be able to access.
From http://tirania.org/blog/archive/2011/Sep-15.html :
When you use C# and VB, you are using the full .NET framework. But
they have chosen to expose a smaller subset of the API to developers
to push the new vision for Windows 8.
And this new vision includes safety/sandboxed systems and asynchronous
programming. This is why you do not get direct file system access or
socket access and why synchronous APIs that you were used to consuming
are not exposed.
Now, you notice that I said "exposed" and not "gone".
What they did was that they only exposed to the compiler a set of APIs
when you target the Metro profile. So your application will not
accidentally call File.Create for example. At runtime though, the CLR
will load the full class library, the very one that contains
File.Create, so internally, the CLR could call something like
File.Create, it is just you that will have no access to it.
This split is similar to what has been done in the past with
Silverlight, where not every API was exposed, and where mscorlib was
given rights that your application did not have to ensure the system
safety.
You might be thinking that you can use some trick (referencing the GAC
library instead of the compiler reference or using reflection to get
to private APIs, or P/Invoking into Win32). But all of those uses will
be caught by AppStore review application and you wont be able to
publish your app through Microsoft's store.
You can still do whatever ugly hack you please on your system. It just
wont be possible to publish that through the AppStore.
So there's probably no official way, and if there's an unofficial way, it probably won't be accepted to the app store.
Just in general this makes sense: I don't want to download a seemingly legit application just to have it scan my hard drive and find my "budget.xls" spreadsheet which includes my banking/credit information.
EDIT: it is possible to grant temporary access to secure files/folders through WinRT's file picker, but it has to be invoked and chosen explicitly by the user.
You can use the StorageFolder.GetFolderFromPathAsync Method to get a StorageFolder instance from a path.
StorageFolder folder = await StorageFolder.GetFolderFromPathAsync(#"C:\...");
Note that you may not have permission to do this for all paths on your machine though.
Similar situation. Wanted to access chrome bookmarks file to parse. Had to use FileOpenPicker initially, but the file that it returns can be "cached" in the futureaccesslist(?) for subsequent retrieval.

Categories