Действительно, это добилось цели. Спасибо за помощь, я ценю это.
я есть собственный тип C #, как (просто пример):
public class MyVector
{
public double X {get; set;}
public double Y {get; set;}
public double Z {get; set;}
//...
}
И я хочу, чтобы он привязал данные к TextBox.Text:
TextBox textBox;
public MyVector MyVectorProperty { get; set;}
//...
textBox.DataBindings.Add("Text", this, "MyVectorProperty");
По сути, мне нужно преобразование в и из строки для моего пользовательского типа значения. В текстовом поле я хочу что-то вроде «x, y, z», которое можно редактировать для обновления типа вектора. Я предположил, что я мог бы сделать это, добавивTypeConverter
производный класс:
public class MyVectorConverter : TypeConverter
{
public override bool CanConvertFrom(ITypeDescriptorContext context,
Type sourceType)
{
if (sourceType == typeof(string))
return true;
//...
return base.CanConvertFrom(context, sourceType);
}
public override bool CanConvertTo(ITypeDescriptorContext context,
Type destinationType)
{
if (destinationType == typeof(string))
return true;
//...
return base.CanConvertTo(context, destinationType);
}
public override object ConvertFrom(ITypeDescriptorContext context,
System.Globalization.CultureInfo culture,
object value)
{
if (value is string)
{
MyVector MyVector;
//Parse MyVector from value
return MyVector;
}
return base.ConvertFrom(context, culture, value);
}
public override object ConvertTo(ITypeDescriptorContext context,
System.Globalization.CultureInfo culture,
object value,
Type destinationType)
{
if (destinationType == typeof(string))
{
string s;
//serialize value to string s
return s;
}
//...
return base.ConvertTo(context, culture, value, destinationType);
}
}
и связывая это с моей структурой:
[TypeConverter(typeof(MyVectorConverter))]
public class MyVector { //... }
Похоже, это завершит половину битвы. я могу видетьMyVectorConverter
быть призванным, но что-то не так. Он вызывается, чтобы узнать, знает ли он, как преобразовать в строку, а затем вызывается для преобразования в строку. Тем не менее, он никогда не запрашивается, может ли он преобразовать строку FROM или выполнить преобразование. Кроме того, сразу после редактирования в текстовом поле старое значение немедленно заменяется (другая последовательность CanConvertTo и ConvertTo, восстанавливая старое значение). Конечный результат заключается в том, что вновь введенная запись в текстовом поле возвращается сразу после ее применения.
Я чувствую, что просто чего-то не хватает. Есть? Весь этот проект / подход обречен на провал? Кто-нибудь еще пытается такое безумие? Как можно двунаправленно связать пользовательский многоэлементный тип со строковым элементом управления?
Решение: Как ни странно, все, что нужно, это включить «форматирование» для объекта Binding. (спасибо, Джон Скит):
textBox.DataBindings.Add("Text", this, "MyVectorProperty"); //FAILS
textBox.DataBindings.Add("Text", this, "MyVectorProperty", true); //WORKS!
Как ни странно, все, что мой MSDN упоминает об этом параметре (formattingEnabled):
"true для форматирования отображаемых данных; в противном случае - false"
В нем ничего не говорится о том, что это требование возврата данных из контроля (в этих условиях).