質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.50%
C#

C#はマルチパラダイムプログラミング言語の1つで、命令形・宣言型・関数型・ジェネリック型・コンポーネント指向・オブジェクティブ指向のプログラミング開発すべてに対応しています。

MVVM

MVVM(Model View ViewModel)は構築上のデザインパターンで、表現ロジック(ViewModel)によってデータ(Model)からページ(View)を分離させます。

Xamarin

Xamarin(ザマリン)は、iPhoneなどのiOSやAndroidで動作し、C# 言語を用いてアプリを開発できるクロスプラットフォーム開発環境です。Xamarin Studioと C# 言語を用いて、 iOS と Android の両方の開発を行うことができます。

Q&A

解決済

1回答

323閲覧

【MVVM】センサーの起動と値の購読を分離したい

naritamago

総合スコア15

C#

C#はマルチパラダイムプログラミング言語の1つで、命令形・宣言型・関数型・ジェネリック型・コンポーネント指向・オブジェクティブ指向のプログラミング開発すべてに対応しています。

MVVM

MVVM(Model View ViewModel)は構築上のデザインパターンで、表現ロジック(ViewModel)によってデータ(Model)からページ(View)を分離させます。

Xamarin

Xamarin(ザマリン)は、iPhoneなどのiOSやAndroidで動作し、C# 言語を用いてアプリを開発できるクロスプラットフォーム開発環境です。Xamarin Studioと C# 言語を用いて、 iOS と Android の両方の開発を行うことができます。

0グッド

0クリップ

投稿2019/01/28 02:27

__Xamarin.Essentials__の利用の一環として、加速度センサーの値を取得するアプリを__Forms__で実装中です。

以前 __DeviceMotion.Plugin__を使用した際は、センサーの起動、Bindingプロパティの更新をViewModelが全て請け負っていたのですが、MVVMの学習として、以下のような形に変更したいと思います。

  • Model:加速度センサー(Accelerometer)の起動・イベントの登録
  • ViewModel:イベントの購読・値が変わったらプロパティを更新。

Model(例外処理は省略)

1using Xamarin.Essentials; 2 3namespace hogehoge 4{ 5 public class SensorAccel 6 { 7 public event EventHandler<AccelerometerData> AccelDataReceived; 8 SensorSpeed speed = SensorSpeed.UI; 9 10 public void StartAccel(){ 11 Accelerometer.Start(speed); 12 AccelDataReceived?.Invoke(this, new AccelerometerData()); 13 } 14 } 15}

上記のModelに書いたAccelerometer.Start(speed)
をViewModelから呼び出して、EventHandler<AccelerometerData>を購読すればいいのかと思ったのですが、そうするとViewModelの方に using Xamarin.Essentials を書かなければならず、上手く分離できていないように思います。Xamarin.Essentials のことを ViewModel が知らなくても良いように責務を分離したいのですが、まだC#のイベントへの理解が拙く、自力で実装できないため、ソースコードをご教示いただきたいです。

また、この実装方針に関して、MVVMの理念と違う・こうした方がいい等あればご指摘お願いします。

対象のプラットフォームはAndroid8.0.0です。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答1

0

ベストアンサー

Xamarin.Essentialsをラップするのであれば、AccelDataReceivedのイベントハンドラの引数も独自のクラスにするべきです。
例として以下のようになります。
AccelDataReceivedは、Accelerometer.Start(speed)の後に発火するようになっていますけど、名前から察するにデータを受けたら発火するでいいですよね?)

C#

1public class AccelDataReceivedEventArgs : EventArgs 2{ 3 public Vector3 Acceleration { get; } 4 5 public AccelDataReceivedEventArgs(Vector3 acceleration) 6 { 7 Acceleration = acceleration; 8 } 9} 10 11public class SensorAccel 12{ 13 public event EventHandler<AccelDataReceivedEventArgs> AccelDataReceived; 14 SensorSpeed speed = SensorSpeed.UI; 15 16 public SensorAccel() 17 { 18 Accelerometer.ReadingChanged += (sender, e) => 19 { 20 var data = e.Reading; 21 AccelDataReceived?.Invoke(this, new AccelDataReceivedEventArgs(data.Acceleration)); 22 }; 23 } 24 25 public void StartAccel() 26 { 27 Accelerometer.Start(speed); 28 } 29}

投稿2019/01/28 03:36

f-miyu

総合スコア1625

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

naritamago

2019/01/28 04:56

f-miyuさん、提示頂いたコードで無事動かすことが出来、ViewModelとModelの責務の分離を果たすことができました。 独自クラスについても、スマートな書き方を示していただきありがとうございます。Vector3は知らなかったのでまたひとつ勉強になりました。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.50%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問