FrameworkElement.Name problem - wpf

I am attempting to set the Name property of a Page in the constructor:
public partial class PageListView : Page
{
public PageListView(string title)
{
InitializeComponent();
Name = title;
}
}
However, I often get the following error message.
'x' is not a valid value for property 'Name'.
Where x seems to be almost anything, drilling down into the exception details doesn't seem to provide any useful information (e.g. the InnerException is null.)
Does anyone know what is happening here?

The Name property generally follows the rules of C#/VB.NET identifiers (i.e. fields). Based on the documentation:
The string values used for Name have some restrictions, as imposed by
the underlying x:Name Directive defined by the XAML specification.
Most notably, a Name must start with a letter or the underscore character
(_), and must contain only letters, digits, or underscores.
Based on the parameter you are passing (i.e. title), it seems like you may violate that. But you'd have to give some specific examples to be sure.

Of course, moments after posting this I realised what's going on.
Because FrameworkElement.Name is used for creating object references, you have to ensure that the string contains only valid chars for an object instance variable name.
Use Title or another plain text property instead, unless you really want to set the x:Name property for referencing.

Related

OmitAutoProperties affects non auto property

I have a class that has property like this
public string Foo
{
get { return _foo; }
set
{
if (!string.Equals(_foo, value))
{
_foo= value;
OnPropertyChanged();
}
}
}
When I create object with _fixture = new Fixture {OmitAutoProperties = true};, I expect it has value but it's null and setter never hit. Do I miss something?
This is by design. As the documentation states:
Gets or sets if writable properties should generally be assigned a value when generating an anonymous object.
In other words, in AutoFixture, the term auto-property refers the the feature of AutoFixture that automatically populates writable properties. Perhaps a better word would have been DoNotAutomaticallyPopulateProperties.
I can understand the confusion, as in C#, auto-property can also be interpreted as meaning Auto-Implemented Properties.
Frankly, AutoFixture's terminology should, perhaps, have been chosen with greater care, but in all these years, I don't think this has ever been brought to my attention before.
Specifically in the OP Foo is a writable property, and when you disable auto-properties, the setter is never invoked.
The OmitAutoProperties setting determines if a writable property should be set or not:
Gets or sets if writable properties should generally be assigned a value when generating an anonymous object.
So, if it's true, AutoFixture does not try to set any property values and that is by design.

Querying database in Grails

The values in database are saved as such
::{"rating1":"2","rating2":"4","rating3":"5","rating4":"0","rating5":"0"},
Now I need to acces the individual values like 2,4,5 etc.
I made a variable "rating" of the Domain Class type and tried accesing as object using (.) operator but it wont work and gives error:
:exception::groovy.lang.MissingPropertyException: No such property: rating1 for class: java.lang.String
, I tried casting to array and list (as Array, as ArrayList, as List) etc but that wont work either.
Casting to List gives exception:exception::org.codehaus.groovy.runtime.typehandling.GroovyCastException: Cannot cast object '{"rating1":"2","rating2":"4","rating3":"5","rating4":"0","rating5":"0"}' with class 'java.lang.String' to class 'java.util.List' .
Accessing like "rating[3]" gives answer "a". Should I use "rating[11]" to get value 2 or is there any way around.
What could be the possible solution. Please help.
You're storing a string, so you only have string operations available. You need to parse that string to get at the attributes individually (JsonSlurper perhaps?).
rating[character-position] is a bad idea IMO.
Maybe transients (check the GORM docs) would be useful.
class YourDomain {
String yourField
String getRating1() { new JsonSlurper().parseText(yourField).rating1 }
}
Maybe. Totally untested, just an idea.

How to allocate string including comma to control.Name property in wpf

Image im=new Image();
string ii="123456789";
im.Name=ii;
It's ok
but
Image im=new Image();
string ii="123.456.789";
im.Name=ii;
It throw exception. Why is it denied to allocate comma "." to control Name property?
The code you wrote is probably not what you want. As MDoobie said, there are restrictions on what the value of Name can be. The Image class is inheriting the Name property from its immediate parent class, "System.Windows.FrameworkElement." Follow MDoobie's "msdn" link to see what the purpose of that Name attribute is. Near the end of the Remarks you will see a link that will lead you to the specific information about Name restrictions.
In WPF, Names have some restrictions (for instance it cannot contains dots).
"The string values used for Name have some restrictions, as imposed by the underlying x:Name Directive defined by the XAML specification. Most notably, a Name must start with a letter or the underscore character (_), and must contain only letters, digits, or underscores. " (from msdn)

MarkupExtension that uses a DataBinding value

I'm trying to create a WPF MarkupExtension class that provides translated text from my text translation class. The translation stuff works great, but requires a static method call with a text key to return the translated text. Like this:
ImportLabel.Text = Translator.Translate("import files");
// will be "Dateien importieren" in de or "Import files" in en
Its speciality is that it accepts a counting value to provide better wordings.
ImportLabel.Text = Translator.Translate("import n files", FileCount);
// will be "Import 7 files" or "Import 1 file"
Another example: If something takes yet 4 minutes, it's a different word than if it only takes one minute. If a text key "minutes" is defined as "Minuten" for any number and as "Minute" for a count of 1, the following method call will return the right word to use:
Translator.Translate("minutes", numberOfMinutes)
// will be "minute" if it's 1, and "minutes" for anything else
Now in a WPF application, there's a lot of XAML code and that contains lots of literal texts. To be able to translate them without getting nuts, I need a markup extension which I can pass my text key and that will return the translated text at runtime. This part is fairly easy. Create a class inheriting from MarkupExtension, add a constructor that accepts the text key as argument, store it in a private field, and let its ProvideValue method return a translation text for the stored key.
My real problem is this: How can I make my markup extension accept a counting value in such a way that it's data-bound and the translation text will update accordingly when the count value changes?
It should be used like this:
<TextBlock Text="{t:Translate 'import files', {Binding FileCount}}"/>
Whenever the binding value of FileCount changes, the TextBlock must receive a new text value to reflect the change and still provide a good wording.
I've found a similar-looking solution over there: http://blogs.microsoft.co.il/blogs/tomershamam/archive/2007/10/30/wpf-localization-on-the-fly-language-selection.aspx But as hard as I try to follow it, I can't understand what it does or why it even works. Everything seems to happen inside of WPF, the provided code only pushes it in the right direction but it's unclear how. I can't get my adaption of it to do anything useful.
I'm not sure whether it could be useful to let the translation language change at runtime. I think I'd need another level of bindings for that. To keep complexity low, I would not seek to do that until the basic version works.
At the moment there's no code I could show you. It's simply in a terrible state and the only thing it does is throwing exceptions, or not translating anything. Any simple examples are very welcome (if such thing exists in this case).
Nevermind, I finally found out how the referenced code works and could come up with a solution. Here's just a short explanation for the record.
<TextBlock Text="{t:Translate 'import files', {Binding FileCount}}"/>
This requires a class TranslateExtension, inherited from MarkupExtension, with a constructor accepting two parameters, one String and one Binding. Store both values in the instance. The classes' ProvideValue method then uses the binding it gets, adds a custom converter instance to it and returns the result from binding.ProvideValue, which is a BindingExpression instance IIRC.
public class TranslateExtension : MarkupExtension
{
public TranslateExtension(string key, Binding countBinding)
{
// Save arguments to properties
}
public override object ProvideValue(IServiceProvider serviceProvider)
{
countBinding.Converter = new TranslateConverter(key);
return countBinding.ProvideValue(serviceProvider);
}
}
The converter, say of class TranslateConverter, has a constructor that accepts one parameter, a String. This is my key argument from the TranslateExtension above. It remembers it for later.
Whenever the Count value changes (it comes through the binding), WPF will request its value anew. It seems to walk from the source of the binding, through the converter, to the surface where it's displayed. By using a converter, we don't have to worry about the binding at all, because the converter gets the binding's current value as a method argument and is expected to return something else. Counting value (int) in, translated text (string) out. This is my code.
So it's the converter's task to adapt the number to a formulated text. It uses the stored text key for that. So what happens is basically a kinda backwards data flow. Instead of the text key being the main information and the count value being added to it, we need to treat the count value as the primary information and just use the text key as a side parameter to make it whole. This isn't exactly straightforward, but the binding needs to be the primary trigger. Since the key won't change, it can be stored for good in the instance of the converter. And every occurence of a translated text gets its own copy of the converter, each with an individual key programmed in.
This is what the converter could look like:
class TranslateConverter : IValueConverter
{
private string key;
public TranslateConverter(string key)
{
this.key = key;
}
public object Convert(object value, ...)
{
return Translator.Translate(key, (int) value);
}
}
That's the magic. Add the error handling and more features to get the solution.

How to assignTo a setter in Salesforce that requires an index parameter, such as a List<>?

In a controller I have two values:
public List<String> StringValue {get; set;}
public List<String> ListValue {get; set;}
The ListValue is initialized in the constructor and several strings are added. At this point in a value I can refer to these with {!StringValue} and {!ListValue[1]} in a VisualForce page. The list one in particular is the focus - I can even add pseudo-constants (getters) as indexes, making {!ListValue[nameIndex]} a valid reference.
However I've run into an exception when trying to set a list value instead of a simple string value.
<apex:param value="123" assignTo="{!ListValue[1]}" />
The exception is java.lang.ClassCastException: java.lang.String cannot be cast to common.formula.FormulaFieldReference
I think I understand the basics of the problem - Salesforce can't create a setter reference that includes an index parameter (meaning only setters that take a single parameter can be referenced).
Is there any way around this, or do I just have to create a massive amount of ListValue1, ListValue2 variables and associated code?
It's a hack, but it avoids you having to create dozens of variables.
<apex:param value="1:123" assignTo="{!smartAssigner}" />
Then in your controller:
public void setSmartAssigner(String myval) { // parse the colon, set list value appropriately.
You get the idea.
I've never come across a way to do this in the style you're requesting, I'd suggest that to get this going the easiest thing to do would be to concatenate the values you want into one parameter and then split them back up inside the controller.
You might find a suitable way to do this with <apex:repeat> but I'm not sure on your full use case.

Resources