Eto.FormsでXAMLとデータバインドを使う
Eto.Formsのテンプレートでは、GUI定義の方法として次の3つを用意しています。
まず、テンプレートに基づいてプロジェクトを作成します。もちろんGUI定義は「XAML」を選びます。
VMを作る
一応バインドしている感を出すため、VMを用意します。単なるサンプルなので、モデルも含みます。
といっても、使うのは、string型プロパティ1つだけです。
//using System; //using System.Collections.Generic; //using System.Linq; //using System.Text; //using System.Threading.Tasks; using System.ComponentModel; // INotifyPropertyChanged using System.Runtime.CompilerServices; // CallerMemberName namespace EtoXamlSample1 { public class SampleViewModel : INotifyPropertyChanged { private string _message = ""; public string Message { get { return _message; } set { TrySetProperty(ref _message, value); } } #region VMの基礎 public event PropertyChangedEventHandler PropertyChanged; protected void RaisePropertyChanged( [CallerMemberName] string propertyName = null) { if (PropertyChanged == null) return; PropertyChanged(this, new PropertyChangedEventArgs(propertyName)); } protected bool TrySetProperty<T>( ref T storage, T value, [CallerMemberName] string propertyName = null) { if (object.Equals(storage, value)) return false; storage = value; RaisePropertyChanged(propertyName); return true; } #endregion } }
「VMの基礎」部分は、下記ページの「自作BindableBase」を使っています。
XAMLを書く
テンプレートの、StackLayoutの中身を書き換えて、2つのテキストボックスを作ります。
バインドできるように、Textプロパティには{Binding PropertyName}
の書式で指定します。
ここでは、2つのボックスの中身が同期するように、同じプロパティにバインドしてみました。
<?xml version="1.0" encoding="UTF-8"?> <Form xmlns="http://schema.picoe.ca/eto.forms" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" Title="My Eto Form" ClientSize="400, 350" > <StackLayout> <Label>String 1</Label> <TextBox Text="{Binding Message}" /> <Label>String 2</Label> <TextBox Text="{Binding Message}" /> </StackLayout> <Form.Menu> <MenuBar> <ButtonMenuItem Text="F&ile"> <Command x:Name="clickCommand" MenuText="Click Me!" ToolBarText="Click Me!" Executed="HandleClickMe" /> </ButtonMenuItem> <MenuBar.ApplicationItems> <ButtonMenuItem Text="Preferences.." Shortcut="{On Control+O, Mac=Application+Comma}" /> </MenuBar.ApplicationItems> <MenuBar.QuitItem> <ButtonMenuItem Text="Quit!" Shortcut="CommonModifier+Q" Click="HandleQuit" /> </MenuBar.QuitItem> </MenuBar> </Form.Menu> <Form.ToolBar> <ToolBar> <x:Reference Name="clickCommand"/> </ToolBar> </Form.ToolBar> </Form>
コードビハインドを書く
テンプレートに、VMを定義して、Form.DataContextにVMのインスタンスを設定しました。
using System; using System.Collections.Generic; using Eto.Forms; using Eto.Drawing; using Eto.Serialization.Xaml; namespace EtoXamlSample1 { public class MainForm : Form { SampleViewModel myModel; public MainForm() { XamlReader.Load(this); myModel = new SampleViewModel(); DataContext = myModel; } protected void HandleClickMe(object sender, EventArgs e) { MessageBox.Show("I was clicked!"); } protected void HandleQuit(object sender, EventArgs e) { Application.Instance.Quit(); } } }
動かす
ビルドして動かします。 片方のテキストボックスで文字を入力・編集すると、即座にもう片方にも反映されます。 IMEでの入力途中や変換途中も全て反映されています。
つまり、本家.NET(WPF,UWPなど)で言うところの「System.Windows.Data.UpdateSourceTrigger.PropertyChanged」でしょうか。
他の選択肢はないようなので、細かい制御が必要な場合は、色々とコードを書く必要がありそうです。