月別アーカイブ: 2016年7月
Xamarin、ザマリン、青空、晴れた空 -Xamarinで次世代mobile版データベースRealmを使う-
こちらのサイトのメロディーとともにお楽しみください。
Realmは、SQLite+ORMに変わるモバイルデータベースです。Realmは、NoSQLデータベース(非リレーショナルデータベース)ですので、オブジェクトを生成して手軽に永続化できます。
現在、RealmはAndroidとiOSに対応しているので、Xamarinで使ってみます。Build Insiderに掲載されているXamarinでSQLiteを使うコンパクトなサンプルと同様なアプリをXamarin.Forms Portableで作成してみます。
まず、Visual StudioでXamarin.Forms Portableなプロジェクトを作成します。
作成したら、NuGetパッケージマネージャで、realmを検索してインストールします。
最初にModelクラスを作ります。グループ名だけを記録するGroup.csです。
using Realms; using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; namespace UseRealmApp { public class Group : RealmObject { [ObjectId] public string ID { get; set; } public string Name { get; set; } } }
Realmにはいわゆるオートインクリメントな値を振る機能はありませんので、IDもStringにしてGUID値を記録することにします。
次ぎにデータベースを操作するMemoDatabaseクラスを作成します。将来的にGroupクラスだけでなく、メモを記録するクラスなどを追加していくのでMemoDatabaseというクラス名にしました。
GetGroups()メソッドはGroupクラスの全オブジェクトを取得します。GetGroups()メソッドの戻り値をListViewに表示します。GetGroupは指定したIDのオブジェクトを取得します。以降のメソッドについてはソースコードの下に解説を記します。
using Realms; using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; namespace UseRealmApp { public class MemoDatabase { Realm realm; public MemoDatabase() { realm = Realm.GetInstance(); } public IEnumerable<Group> GetGroups() { return realm.All<Group>().ToList(); } public Group GetGroup(string id) { return realm.All<Group>() .ToList() .FirstOrDefault(x => x.ID == id); } public string SaveGroup(Group group) { var newGroup = realm.All<Group>() .ToList() .FirstOrDefault(x => x.ID == group.ID); using (var trans = realm.BeginWrite()) { if (newGroup == null) { newGroup = realm.CreateObject<Group>(); newGroup.ID = Guid.NewGuid().ToString(); } newGroup.Name = group.Name; trans.Commit(); } return newGroup?.ID; // ? Nullable型 } public string DeleteGroup(string id) { var item = realm.All<Group>() .ToList() .FirstOrDefault(x => x.ID == id); if (item == null) return null; using (var trans = realm.BeginWrite()) { realm.Remove(item); trans.Commit(); } return id; } } }
SaveGroupメソッドはオブジェクトを保存します。usingでトランザクション処理を囲みます。DeleteGroupメソッドは指定したIDのオブジェクトを削除します。
app.csでページを表示します。
using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; using Xamarin.Forms; namespace UseRealmApp { public class App : Application { public App() { MainPage = new MyPage(); } } class MyPage : ContentPage { readonly MemoDatabase _db = new MemoDatabase(); public MyPage() { var listView = new ListView { ItemsSource = _db.GetGroups(), ItemTemplate = new DataTemplate(typeof(TextCell)) }; listView.ItemTemplate.SetBinding(TextCell.TextProperty, "Name"); listView.ItemTapped += async (s, a) => { var group = (Group)a.Item; if (await DisplayAlert("削除してよろしいですか", group.Name, "OK", "キャンセル")) { _db.DeleteGroup(group.ID); // groupの削除 listView.ItemsSource = _db.GetGroups(); // リストの更新 } }; var entry = new Entry { HorizontalOptions = LayoutOptions.FillAndExpand }; var buttonAdd = new Button { WidthRequest = 60, Text = "追加" }; buttonAdd.Clicked += (s, a) => { if (!String.IsNullOrEmpty(entry.Text)) { // Entryに文字列が入力されている場合に保存 var group = new Group { Name = entry.Text }; _db.SaveGroup(group); listView.ItemsSource = _db.GetGroups(); //リストの更新 entry.Text = ""; } }; Content = new StackLayout { Padding = new Thickness(0, Device.OnPlatform(20, 0, 0), 0, 0), Children = { new StackLayout { Padding = 5, Orientation = StackOrientation.Horizontal, Children = {entry, buttonAdd} }, listView } }; } } }
ListViewにはグループ名を一覧表示し、タップしたら削除確認のダイアログを表示します。
Entryにグループ名を入力して追加ボタンをタップしたら、データベースに記録してListViewを更新します。
XamarinでもRealmを簡単に使うことができました。