I need a functionality to get all existing (open) instances of some conrete WPF window. I create those windows programatically in few places in code.
Is there a XAML/WPF solution for that? Something like GetInstancesByType(type)?
You can use the Application.Windows property:
foreach( var window in Application.Current.Windows.OfType<MyType>() )
{
// do stuff
}
As H.B. pointed out, you would need to include System.Linq to get the OfType<T> extension method, but it's not necessary.
Related
I am writing a program that will get user inputs and store data about GUI elements, which user has clicked in desktop applications.
I need data from GUI like: element name, element description, class, element parent, children, etc.
Code is written on C#. As i found out, i can use Xamarin.Mac to call macOs AppKit API from C# (https://learn.microsoft.com/en-us/dotnet/api/appkit.nsapplication?view=xamarin-mac-sdk-14).
Now the question is what do i call to get this data?
Or is there any alternative way to get this data?
First, from the XAML part, make sure the objects have a name defined and that they are public after you can call the variable name in the C# code, and from there put a dot (".") many methods, attributes, and options will appear, for example, you are asking about the children, you could use
var titleBarChildre = AppTitleBar.Children.ToList();
etc.
How can I localize an WPF Application using the MVVM Pattern? I really want to do it the "right" way.
My current approach is that I use .resx Resource files to localize my application.
I included them in my xaml code
xmlns:localization="clr-namespace:ClientLibTestTool.ViewLanguages"
and access them like this:
<Button x:Name="BtnGenerate"
Content="{x:Static localization:localization.ButtonGenerate}"/>
My Questions:
Is there a better way to do it?
How can i test the different languages (load application with different language settings)?
Is it possible to change the language at runtime?
Answers:
Question 1:
Question 2: (Thank you, stijn)
public MainWindow()
{
// Debug Settings
localization.Culture = CultureInfo.GetCultureInfo("en-US");
// localization.Culture = CultureInfo.GetCultureInfo("de-DE");
this.InitializeComponent();
}
Question 3: (Thank you, stijn)
Not really, it is necessary to redraw the complete window.
This is the appropriate way to do it, as far as I'm concerned.
To switch languages, change the culture used by the localization class:
localization.Culture = CultureInfo.GetCultureInfo( "de-DE" );
Since all strings are fetched at runtime (all calls in the generated Designer.cs files look like ResourceManager.GetString( "SomeString", resourceCulture ); and resourceCulture is what gets set by the call above, this affects what you get at runtime. However supose you use the values in menu items etc from within xaml, you have to rebuild the entire menu before this takes effect.
I have created an instance of a window inside a class, but I am unable to access the instance of the window from my other class directly.
Is there a way to reference the window instance I have already created using a C# method, perhaps searching through the open app windows until it finds the Dashboard window I am trying to access?
Application.Current.Windows gives you all windows, shouldn't be hard to find using its type.
(As Ed pointed out this does not sound like very good design, so you might want to think about how you can get things done without messy window references)
System.Reflection.Assembly assemby = System.Reflection.Assembly.GetExecutingAssembly();
System.Type[] types = assemby.GetTypes();
var varWindows = types.ToList()
.Where(current => current.BaseType == typeof(Window));
MessageBox.Show(varWindows.Count().ToString());
Application.Current.Windows gets us all instantiated windows, but the above code get us all windows.
How Can I Evaluate a String in C# Windows Application because I need to Dynamically select object in a form based on the Combination of 2 String that give me the name of the needed object
You can tryControlCollection.Find method to find control by name.
For example:
MyForm.Controls.Find("FooButton", true);
Method returns an array of Control element with the Name property set to "FooButton".
There is no C# eval equivalent. But by the link you can find some useful answers. Ofc, if you want to find or evaluate something than winform controls
UPDATE: I think sometimes it is better get control by key directly. For example:
Control control = this.Controls["FooTxtBox"];
if(control==null)
{
MessageBox.Show("Control not found");
}
control.Text = "something";
This is a feature (compiler as a service) that should be available in the next version of the .NET Framework, version 5.
Perhaps reflection could be your solution for this?
Just use the string as the lookup for the Form.Controls collection. Then when you've got the instance of the control, just call whatever method you need on it to select it.
Have a look at this:
http://www.logiclabz.com/c/evaluate-function-in-c-net-as-eval-function-in-javascript.aspx (Link is dead, please provide an updated source)
i'm kind of stuck here. i'm using a dragndrop-library which serializes the dragged UIElements via XamlWriter.Save().
now i'm trying to dragndrop some instances of a class extending Grid. in the constructor i push some elements into the visual tree.
the constructor gets called when the object is deserialized and the elements get added again (and again and again depending on how often i dragndrop). sadly Children.Count tells me there are no child elements if i retrieve the value from within the constructor. if i retrieve it from outside (by myGrid.Children.Count) it gives me the higher (unwanted) amount.
is there any other function i should use to initialize the visuals? or any other way to prevent those duplicates?
thanks and cheers
took a while, but i seem to have found a solution.
now i'm able to create a base class already containing the visual elements all the subclasses need. and they are parsable via XamlWriter/Reader without duplicates. whew.
1) extend UserControl (dont Add->UserControl but Add->Class and inherit manually)
2) put the standard InitializeControl(); into the constructor
3) implement InitializeControl() and put the layouting, child adding and whatever in there
4) xamlwrite/xamlread/inherit like crazy
hope it will be helpful to someone and that i havent overseen the unforeseen..
--
edit: of course.
there will be duplicates but we cant see them.
after the XamlReader is through there are the UIElements created by my InitializeComponent() AND the ones getting xaml-parsed after that. any references in the code regard the code-created controls which are NOT show :/
sigh.
one far from perfect way around this is to put a switch into an Initialized event handler, like so:
if(HasContent)
Initialize();
else
Reinitialize();
Multiinitialize();
where the Initialize() would add the UIElements to the visual tree, the Reinitialize() just finds the right references (by control = FindName("controlName")) and the Multiinitialze() recreates the event handlers and what else gets lost on the way throug the XamlReader.
well, now you can instantiate the custom inherited UserControl in xaml but there is no easy way to set attributes. that is because setting the attributes happens before the Initialized-event and there are NullPointerExceptions awaiting. you could work around that with bindings i guess.
but there HAS to be an easier way. please let me know!