Need work-around for overriding RoutedUICommand.Text property - c#

I have a static Command class like this (but with many more commands):
class GuiCommands
{
static GuiCommands()
{
addInterface = new RoutedUICommand(DictTable.getInst().getText("gui.addInterface"), "addInterface", typeof(GuiCommands));
removeInterface = new RoutedUICommand(DictTable.getInst().getText("gui.removeInterface"), "removeInterface", typeof(GuiCommands));
}
public static RoutedUICommand addInterface { get; private set; }
public static RoutedUICommand removeInterface { get; private set; }
}
It should use my dictionary to get the texts in the right language, which doesn't work, because my dictionary isn't initialized when the static constructor is executed.
My first attempt was to create a new command-class which derives from RoutedUICommand, override the Text property and call the dict in the get method. But the Text property isn't virtual and neither is the GetText()-Method it calls.
The only thing i can think of is provide a static initialize method in this class that translates all the dict-keys. But this is not very clean IMHO because i have to name every command once again like this
addInterface.Text = DictTable.getInst().getText(addInterface.Text);
and if i forget to name one, there won't be an error, just no translation.
I don't even like that i have to name the command twice in this class and once again in the XAML commandbindings.
Do you have any ideas how this can be solved more elegantly?
I like RoutedUICommands much, but like this they're useless to me. Why couldn't Microsoft add the little word 'virtual' a little more often?? (or make it default like JAVA does?!)

I found an acceptable way by translating all commands automatically using reflection.
This way i at least don't have to add all the commands to another method.
I call the translate-method right after i initialized my dictionary.
public static void translate()
{
// get all public static props
var properties = typeof(GuiCommands).GetProperties(BindingFlags.Public | BindingFlags.Static);
// get their uicommands
var routedUICommands = properties.Select(prop => prop.GetValue(null, null)).OfType<RoutedUICommand>(); // instance = null for static (non-instance) props
foreach (RoutedUICommand ruic in routedUICommands)
ruic.Text = DictTable.getInst().getText(ruic.Text);
}

Related

I can't get value of base class field from child class object in c#

using System;
public class Program
{
public static void Main()
{
CloudCollectionHelper cloudHelper = new CloudCollectionHelper();
SlackHelper slackHelper = new SlackHelper();
cloudHelper.DatabaseID=12345;
Console.WriteLine(slackHelper.GetSlackPageTokens());
}
class CloudCollectionHelper
{
public long DatabaseID { get; set; }
}
class SlackHelper:CloudCollectionHelper
{
public long GetSlackPageTokens()
{
return DatabaseID;
}
}
}
current output: 0
Expected Output: 12345
I need output 12345 because DatabaseID from the cloudhelper so i need that databaseID in the slackhelper.
this is my c# online compiler: https://dotnetfiddle.net/QNQeEX
The child class does not get the assigned values from the base class. Becouse there can be mutliple instances from it. For example, if you have
...
CloudCollectionHelper cloudHelper1 = new CloudCollectionHelper();
CloudCollectionHelper cloudHelper2 = new CloudCollectionHelper();
cloudHelper1.DatabaseID = 1234;
cloudHelper2.DatabaseID = 6789;
Console.WriteLine(slackHelper.GetSlackPageTokens()); //It would not know, what value to use.
...
The best way would be assigning the value directly to the child class or using the static modifier.
Edit:
Best way if you need to take this value from the child class for whatever reason would be doing something like this:
...
CloudCollectionHelper cloudHelper = new CloudCollectionHelper();
cloudHelper.DatabaseID = 12345; //First assign the needed Value
SlackHelper slackHelper = new SlackHelper(cloudHelper); //then create a new instance from the child class
...
and add the constructor from the SlackHelper child class like this:
class SlackHelper:CloudCollectionHelper
{
public SlackHelper(CloudCollectionHelper cloudHelper)
{
this.DatabaseID = cloudHelper.DatabaseID;
}
... //Do everything else what this class needs here
}
If the Value from cloudHelper.DatabaseID can update during the runtime, you will need a event to update the child class. It still isn't the best way to do this, because the DatabaseID value is already public and can be accessed without the child class.
Edit 2:
Like I already told you in the comments, you could also avoid this problem with the static modifier. But this will effect every instance made from the CloudCollectionHelper class. As soons as you make it static, this will only hold 1 possible value for all instances.
(Please keep in your mind to use a comment if needed or best case, just avoid Magic numbers)
The property of your Object slackhelper has not been affected.
You don't need to create a CloudCollectionHelper Object.
SlackHelper slackHelper = new SlackHelper();
slackHelper.DatabaseID=12345;
Console.WriteLine(slackHelper.GetSlackPageTokens());
You should create this property inside the class to allow to read the Database ID
public long GetSlackPageTokens()
{
return base.DatabaseID;
}

How to dynamically decide which static class to use

We have a large class that contains a bunch of css selectors stored as static strings. Example:
public class Constants
}
public static string Selector1 = "#someID";
public static string Selector2 = ".some.classes a";
// and so on...
}
We now need to test a different version of our web app which requires a few different selectors. So we need to find a clean scalable way to override these selectors based on some configuration.
My solution to the problem is this: I'm trying to create a BaseConstants class which will have the current set of selectors. Then I create another class called UpdatedConstants which will subclass the BaseConstants class. This class will then contian all the selectors and just override the ones that need changing with the new keyword. Example:
public class UpdatedConstants : BaseConstants
{
// Overrides the base class's Selector1 string
public new static string Selector1 = "#someOtherID";
}
This works well for overriding the strings however I'm stumped as to how the project will decide which static class to use when it is compiled. All our existing code uses the Constants class like this:
var element = driver.GetElement(Constants.SomeSelector);
Is there a way to dynamically decide which class is the final Constants class? Perhaps by some meta-programming magic?
Let me know if anyone has questions or needs a better explanation of the problem. Thanks
Make your constants classes non-static and use a singleton. This also lets you use virtual properties, since you want to use a base Constants class.
public static class Constants
{
static Constants()
{
#if FOO
Current = new ConstantsFoo();
#elif BAR
Current = new ConstantsBar();
#endif
}
public static ConstantsBase Current { get; private set; }
}
//...snip
var element = driver.GetElement(Constants.Current.SomeSelector);
If you don't want to change all occurences Constants.SomeSelector, the only way to have different behavoirs is using pre-processor directives in the Constants class:
public class Constants
}
#if OLD
public static string Selector1 = "#someID";
#elif NEW
public static string Selector1 = "#someNewID";
#endif
public static string Selector2 = ".some.classes a";
// and so on...
}
Else you can use the approach from Ed Plunketts answer.
Okay, probably not what you're looking for, but... You might want to consider not doing it like this.
Put it this way - if you travel down the road, what will your code look like in 5 years? You'll have a base class that contains your original settings, a subclass for how they were modified the first time (when you asked this question), a subclass inheriting from that subclass on how they were modified the next time, and so on. I could easily imagine 10 subclasses in a giant chain - and if you wanted to trace the current value for any setting, you'd have to travel up that chain until you found where it was most recently set/overriden. It sounds like a maintenance nightmare, to be honest.
If I were in your shoes, this is what the new code would look like:
public static class Constants
{
public static string Selector1 { get { return ReadFromSettings("Selector1"); } }
public static string Selector2 { get { return ReadFromSettings("Selector2"); } }
//etc
// then, code for ReadFromSettings()
}
... and then migrate those settings into an actual settings file. Nobody needs to change any code on the calling end (they still reference Constants.Selector1) - except, instead of having this all hard-coded in a series of derived classes, you just have a file with your values.

Replace (and backup) Method dynamically in C#

I need to change a specific property dynamically and have been using this snipplet:
var _oldMethod = typeof(TypeName).GetProperty("OldProperty", BindingFlags.Public | BindingFlags.Static).GetMethod;
var _newMethod = typeof(OwnTypeName).GetProperty("NewProperty", BindingFlags.Public | BindingFlags.Static).GetMethod;
ReplaceMethod(_oldMethod, _newMethod);
...
private static unsafe void ReplaceMethod(MethodInfo _oldMethod, MethodInfo _newMethod)
{
var _oldMethodAddress = new IntPtr((int*)_oldMethod.MethodHandle.Value.ToPointer() + 2);
var _destination = (uint*)_oldMethodAddress.ToPointer();
*destination = (uint)_newMethod.MethodHandle.GetFunctionPointer().ToInt32();
}
Unfortunately this required some decompiling with recreating the original property. What I am looking for now is a a possibility to duplicate and kind of backup the original method and dynamically replace the old method with the new one or restore the original one.
Has anyone an idea how to implement this?
Edit:
I may should have clarified my situation further:
public static class ClassName
{
public static bool Property
{
get
{
// Conditions
}
}
}
I can't access ClassName and need to force Property to false in specific situations and need to replace it to the original return value in other situations. I have been using the ReplaceMethod above mentioned but don't want to decompile and rebuild Property from scratch (instead some kind of backup of the original Property)
First of all, you are handling properties instead of methods.
One easy approach to do this is to replace your properties type by Func<> and this will keep what you're wanting to do easier.
private static void Main(string[] args)
{
var a = new A();
a.Property = Method1;
Console.WriteLine(a.Property.Invoke());
a.Property = Method2;
Console.WriteLine(a.Property.Invoke());
Func<string> oldMethod = a.Property;
Console.WriteLine(oldMethod.Invoke());
Console.ReadLine();
}
public class A
{
public Func<string> Property { get; set; }
}
private static string Method1()
{
return "Method1";
}
private static string Method2()
{
return "Method2";
}
You can change the method as many times as you want and also keep the old one in one variable.

Is there any way to implement a get method inside a class in C#?

I would like to know if there is any way to implement a get method inside a class?
public class Element: IWebElement
{
IWebElement realElement;
//Question point is this get{}
//Everytime I access the instance of this class this get would be called
get
{
//This 'realElement' is not present yet
//So I cannot initialize it
//But when the properties of this class are accessed
//I'm telling the get method that it's time to initialize 'realElement'
realElement = webDriver.FindElement(...);
Visible = element.Visible;
return this;
}
public bool Visible {get; set;}
}
public class AnotherClass()
{
public void AccessElement()
{
Element element = new Element();
if(element.Visible) // At this point the 'element'
{
}
}
}
Usage:
I cannot initialize every property with their own get, because they are too many
Everytime I access the instance of this class this get would be called
If that could be done you'd be in trouble returning this since that would then access the instance, which would call the method, which would then access the instance, which would call the method… and so on until you get a StackOverflowException (or if it got tail-call optimised, forever).
More generally the question doesn't make sense.
A get method is a method identified as being the getter of a property. When C# is compiled to CIL then properties with getters are compiled so that there is a .property declaration with a .get declaration that refers to that method. If C# decided to change the rules to have getters on classes, it wouldn't have any corresponding CIL to compile it to.
The closest thing to a getter on a class in .NET is a default property, which in C# you can only have (and will always have) on a property called this (it becomes what is visible to other .NET languages or reflection property called Item), but it must have an indexer, and it does still exist as a property rather than with the getter directly applied to the class.
You could use the constructor, so it will be called everytime instance of object will be created.
public class Element()
{
public Element(){
AnyProperty = ""; //some value initialize
}
}
Added this new answer with my old answer because I got downvoted for trying to answer your original code which is now really different. Sheesh.
Usage: I cannot initialize every property with their own get, because
they are too many
So, this is actually not how you usually use get. Get is used mostly for access to a private method, or with a little logic, and oftentimes for data-binding such as in MVVM, etc.
I think your wording is not accurate. You said
Everytime I access the instance of this class this get would be called
But based on your code, what you mean is "Everytime I instantiate a class". The only thing you really need is a constructor.
public class Element: IWebElement
{
IWebElement realElement;
public bool Visible {get; set;}
public Element()
{
realElement = webDriver.FindElement(...);
Visible = element.Visible;
}
}
Old answer:
You're probably thinking of the Singleton Pattern
EDIT: This originally answered original question's code, seen below.
public class Element()
{
//Question point is this get{}
//Everytime I access the instance of this class this get would be called
get{
return this;
}
public string AnyProperty {get; set;}
}
public class AnotherClass()
{
public void AccessElement()
{
Element element = new Element();
element.AnyProperty = "";
}
}

C# Get property value without creating instance?

Is it possible to get value without creating an instance ?
I have this class:
public class MyClass
{
public string Name{ get{ return "David"; } }
public MyClass()
{
}
}
Now I need get the value "David", without creating instance of MyClass.
Real answer: no. It's an instance property, so you can only call it on an instance. You should either create an instance, or make the property static as shown in other answers.
See MSDN for more information about the difference between static and instance members.
Tongue-in-cheek but still correct answer:
Is it possible to get value without creating an instance ?
Yes, but only via some really horrible code which creates some IL passing in null as this (which you don't use in your property), using a DynamicMethod. Sample code:
// Jon Skeet explicitly disclaims any association with this horrible code.
// THIS CODE IS FOR FUN ONLY. USING IT WILL INCUR WAILING AND GNASHING OF TEETH.
using System;
using System.Reflection.Emit;
public class MyClass
{
public string Name { get{ return "David"; } }
}
class Test
{
static void Main()
{
var method = typeof(MyClass).GetProperty("Name").GetGetMethod();
var dynamicMethod = new DynamicMethod("Ugly", typeof(string),
Type.EmptyTypes);
var generator = dynamicMethod.GetILGenerator();
generator.Emit(OpCodes.Ldnull);
generator.Emit(OpCodes.Call, method);
generator.Emit(OpCodes.Ret);
var ugly = (Func<string>) dynamicMethod.CreateDelegate(
typeof(Func<string>));
Console.WriteLine(ugly());
}
}
Please don't do this. Ever. It's ghastly. It should be trampled on, cut up into little bits, set on fire, then cut up again. Fun though, isn't it? ;)
This works because it's using call instead of callvirt. Normally the C# compiler would use a callvirt call even if it's not calling a virtual member because that gets null reference checking "for free" (as far as the IL stream is concerned). A non-virtual call like this doesn't check for nullity first, it just invokes the member. If you checked this within the property call, you'd find it's null.
EDIT: As noted by Chris Sinclair, you can do it more simply using an open delegate instance:
var method = typeof(MyClass).GetProperty("Name").GetGetMethod();
var openDelegate = (Func<MyClass, string>) Delegate.CreateDelegate
(typeof(Func<MyClass, string>), method);
Console.WriteLine(openDelegate(null));
(But again, please don't!)
You can make that property static
public static string Name{ get{ return "David"; } }
Usage:
MyClass.Name;
You requirements do seem strange, but I think you're looking for some kind of metadata. You can use an attribute to achieve this:
public class NameAttribute : Attribute {
public string Name { get; private set; }
public NameAttribute(string name) {
Name = name;
}
}
[Name("George")]
public class Dad {
public string Name {
get {
return NameGetter.For(this.GetType());
}
}
}
[Name("Frank")]
public class Son : Dad {
}
public static class NameGetter {
public static string For<T>() {
return For(typeof(T));
}
public static string For(Type type) {
// add error checking ...
return ((NameAttribute)type.GetCustomAttributes(typeof(NameAttribute), false)[0]).Name;
}
}
Now this code can get names with and without instances:
Console.WriteLine(new Dad().Name);
Console.WriteLine(new Son().Name);
Console.WriteLine(NameGetter.For<Dad>());
Console.WriteLine(NameGetter.For<Son>());
You can make your property static, as pointed out by many others.
public static string Name{ get{ return "David"; } }
Be aware that this means your instances of MyClass will no longer have their own Name property, since static members belong to the class, not the individual object instances of it.
Edit:
In a note, you mentioned that you want to override the Name property in subclasses. At the same time, you want to be able to access it at the class level (access it without creating an instance of your class).
For the static properties, you would simply create a new Name property in each class. Since they are static, you're always (almost always, yay reflection) going to access them using a specific class, so you'd be specifying which version of Name you want to get. If you want to try and hack polymorphism in there and get the name from any given subclass of MyClass, you could do so using reflection, but I wouldn't recommend doing so.
Using the example from your comment:
public class Dad
{
public static string Name { get { return "George"; }
}
public class Son : Dad
{
public static string Name { get{ return "Frank"; }
}
public static void Test()
{
Console.WriteLine(Dad.Name); // prints "George"
Console.WriteLine(Son.Name); // prints "Frank"
Dad actuallyASon = new Son();
PropertyInfo nameProp = actuallyASon.GetType().GetProperty("Name");
Console.WriteLine(nameProp.GetValue(actuallyASon, null)); // prints "Frank"
}
As a side note, since you are declaring a property that has only a getter and it is returning a constant value, I recommend possibly using a const or static readonly variable instead.
public const string Name = "David";
public static readonly string Name = "David";
Usage for both would be the same:
string name = MyClass.Name;
The main benefit (and drawback) of const is that all references to it are actually replaced by its value when the code is compiled. That means it will be a little faster, but if you ever change its value, you will need to recompile ALL code that references it.
Whenever you write C# code, always check if your method and property getter/setter code does anything at all with other instance members of the class. If they don't, be sure to apply the static keyword. Certainly the case here, it trivially solves your problem.
The reason I really post to this question is that there's a bit of language bias at work in some of the answers. The C# rule that you can't call an instance method on a null object is a specific C# language rule. It is without a doubt a very wise one, it really helps to troubleshoot NullReferenceExceptions, they are raised at the call site instead of somewhere inside of a method where it gets very hard to diagnose that the this reference is null.
But this is certainly not a requirement to the CLR, nor of every language that run on the CLR. In fact, even C# doesn't enforce it consistently, you can readily bypass it in an extension method:
public static class Extensions {
public static bool IsNullOrEmpty(this string obj) {
return obj != null && obj.Length > 0;
}
}
...
string s = null;
bool empty = s.IsNullOrEmpty(); // Fine
And using your property from a language that doesn't have the same rule works fine as well. Like C++/CLI:
#include "stdafx.h"
using namespace System;
using namespace ClassLibrary1; // Add reference
int main(array<System::String ^> ^args)
{
MyClass^ obj = nullptr;
String^ name = obj->Name; // Fine
Console::WriteLine(name);
return 0;
}
Create a static property:
public class MyClass
{
public static string Name { get { return "David"; } }
public MyClass()
{
}
}
Get it like so:
string name1 = MyClass.Name;
That is not possible. As Name is an instance property, you can only get its value if you have an instance.
Also, note that you are not talking about a parameter, but about a property.
Create a static class or a static property, and you don't have to explicitly instantiate it.

Categories

Resources