20

私は DSLR カメラと Android Honeycomb を実行している Samsung Galaxy Tab を持っています。USB ケーブルを使用してタブレットに接続された DSLR (タブレットでホスト機能を有効にする USB キット経由)。この画像をタブレットにダウンロードしたり、画像から取得したメタ情報を含むトースト通知を表示するなど、何か他のことを行うために、ユーザーがこの外部カメラを使用して写真を撮ったときに通知を受けたいです。

変更を監視できるすべての既存のツール (基礎となるメカニズムのFileObserver使用など)を取得する限り、監視する特定のファイルまたはファイルシステム パスを要求します。2.x 以前の Android バージョンでブロック レイヤー プロトコルがサポートされるまでは、これで十分でした。デバイスを接続すると、デバイスのファイル システムのどこかにマウントされ、このマウントポイントをこれらのツールのウォッチ ポイントとして使用できました。 .inotifyMediaContentProvider

Honeycomb 以来、Google は外部 USB デバイスにアクセスする方法をこれのサブセットとして変更Media Transfer Protocolしました。PTP外部 USB デバイスを Android デバイスに接続すると、そのマウントポイントが表示されません (それらを取得するためのadb shell後続のmountコマンドを使用しています)。さらに、MTP実装では、明らかに高レベルの抽象化として機能し、単なる整数値であるストレージ ID を使用します。これらのストレージIDを実際のパス/マウントポイント/その他に変換する方法があることを望んでいましたが、明らかに存在しないようです。

MediaScanner私のデバイスで既に実行されているAndroid について考えてみると、デバイスからアクセスできるメディア ファイルに変更があった場合に特別なブロードキャストでこの問題を管理できるのではないかと考えたので、既に存在し、通知を受けるIntentのに適したものを探し始めましたが、うまくいきませんでした。 Intents-デバイスが接続されている場合と切断されている場合にのみブロードキャストされるACTION_MEDIA_MOUNTEDとのみが見つかりました。ACTION_MEDIA_REMOVEDつまりMediaScanner、再マウントするまでデバイスの変更に気付かないことを意味します(ストックギャラリーアプリを使用して再確認しました-プラグを抜いてAndroidデバイスにプラグインするまで、カメラに新しく作成された画像は表示されませんまた)。

この外部 SD カードのマウント パスを取得しようとして、API 呼び出しを使用しましたが、カメラのものではなく、Environment.getExternalStorageDirectory()エミュレートされた Galaxy の SD カード パスが生成されます。/mnt/sdcardだから私にとってもうまくいきません。

Timerとして機能する定期的なイベントを開始しただけで、この問題を解決することができましAsyncTaskTimerTask。このタスクは、USB 接続の初期化、デバイスのオープン、デバイス メモリ全体のスキャン、最後に撮影した写真のみの取得、デバイス記述子と USB 接続のクローズを行います。

これらすべてのアクションを毎回実行する必要があることを考慮すると、5 秒または 10 秒ごとなど、かなり頻繁に実行する必要があることを考慮すると、これは最善かつ効率的な方法のようには見えません。それは間違いなくバッテリーをすぐに消耗させ、最後に撮った写真を撮って前回最後に撮った写真と比較するためだけに不必要なシステム I/O を生成します (99% で同じ画像でした)。これを行うため。イベントベースの通知を備えたオブザーバーメカニズムを用意する方がはるかに良いでしょう。

私の質問は、上記の方法ではなく、Honeycom 以降の Android バージョンの外部 USB ストレージの変更について通知を受けるより効率的な方法はありますか?

4

1 に答える 1

2

より効率的な方法が必要な場合は、カメラが写真を撮ったことを示す何らかの信号を USB 経由で送信する必要があります。私はそれをしていないと思います。

したがって、あなたが説明している方法で手動で確認する必要があります:

ストレージをマウントします->変更を確認します->検出された変更を処理します。

「MTPの方法」を何と読んでいたかはわかりませんが、ここにアプリケーションの例を示します。

https://github.com/ynakanishi/Honeycomb-MTP-sample

毎回ストレージ全体をスキャンしないようにするには、たとえば、ファイル名を確認して比較して新しいファイルを見つけるたびに、読み取ったファイル名の結果を保存できます。通常、ファイルの名前もカメラの同じ番号で始まります。そのため、空の SD カードでセッションを開始すると、写真のファイル名がすでにわかっています。img0001.jpg としましょう。したがって、成功するまでそのファイルを取得する関数を作成するだけです。次の img0002.jpg が必要な場合は、成功するまでそのファイルを取得するタスク/サービス/関数を記述できます。

バッテリーを節約したい場合は、USB ポートに電力を供給するために間に追加のバッテリー/電源を実装できます。

Async タスクまたは timerTask の代わりに、ScheduledExecutorService を試して、消費電力が少ないかどうかを確認できます。

それがあなたにいくつかの新しい考えを与えたことを願っています

于 2012-09-25T08:01:43.103 に答える