tmytのらくがき

個人の日記レベルです

Aristea 1.5.24 リリースしました

前回1月中頃だったので約1か月も空いてしまいました。バグとかいっぱいあって早くリリースしないといけないのに遅くなっちゃってごめんなさい。ということで今回の更新内容です。

  • 長文DMが表示されない問題を修正しました
  • miil.me のURLが表示できないことがある問題を修正しました
  • トーストをタップしてもなにも表示されない問題を修正しました
  • 320px表示にしたときアカウントのアイコンが表示されない問題を修正しました
  • アカウントが増えてしまう問題を修正しました
  • クイック投稿エリアのレイアウトを修正しました
  • ブロック/スパム報告ができるようになりました
  • NuAns NEO、Every Phone などで画像ポップアップのレイアウトを修正しました
  • 画像への透かし書き込み処理を修正ました
  • アプリ終了時の安定性を向上しました
  • 画像のリサイズ処理を修正しました
  • 送信ボタンのサイズが大きくなりました
  • AppBarのヒットテストを調整しました (Phoneのみ)
  • ローカル通知が廃止になりました
  • 返信時のデフォルト文字列が変更されてます*1
  • クイック投稿エリアのレイアウトを調整しました
  • 複数画像の並び順を変更しました

わりともりだくさん。主にバグ修正。あとレイアウトの修正。それから使いやすくしました。という感じです。複数画像の並び順についてなんですが、いままでのAristeaはこうでした。

1 3
2 4

で、これって公式クライアントと並び順違って、なおさないとなー。と思っていたのを今回入れました。なので今回からはこう並びます。

1 2
3 4

次に、ローカル通知が削除されました。ローカル通知自体は、AristeaでPush通知が実装される前にあったものでアプリが実行中でないといけないというものでした。*2で、そのあとPush通知が実装されるのですが機能を特に削除してなかったので似たような機能が複数存在する状態になっていました。そんでもってよく、通知が複数出るんだけど。という話をよくいただいていて、それ通知2個ONにしてるからでしょ。と回答していたのですがやっとまぁ消しました。というだけです。これからはPush通知をご利用ください。

ちなみにWindows 10でPush通知を有効にしていると通知領域からふぁぼったりリツイートしたり、リプライ送れたりします。結構便利なのでおすすめです。さらにちなみに、Windows 10 のトーストの挙動かなり怪しくて、アクションセンターに20個ぐらい通知がたまっているとAristeaのトーストが出なくなります。どう見てもバグなんですけど仕様という話があります。ほんまかいなというところです。

*1:複数アカウントをAristeaへ登録していて、そのアカウントを含む他人のツイートに返信したとき、Aristeaに登録されているすべてのアカウントがデフォルト文字列から除かれていました

*2:バックグラウンドでAPIアクセスしたりできないのでそうなってます

Adaptive and Interactive Toast でアプリの起動を正しくハンドルしよう

NuAnsの話もいいけどちゃんとでべろっぷめんとの話もたまにはしたいよね。ということで、Windows 8.xのころのトーストでタップされた時の引数を設定するには、

<toast launch="ここが引数">
  <visual>
    <!-- いろいろ -->
  </visual>
</toast>

こんなXMLを書いて、App.xaml.csのOnLaunchedでこうやってあげて、MainPage.xaml.csとかのOnNavigatedToとかでハンドリングすればいいんですが

protected override void OnLaunched(LaunchActivatedEventArgs e)
{
    // e.Arguments にlaunch で指定した文字列が入ってます。
    var args = e.Arguments;
    // Navigateとかで適当に引き渡す
    ...
    rootFrame.Navigate(typeof(MainPage), args);
}

Windows 10で追加された新しいトーストだとうまく動きません。とりあえずXMLはこんな感じに書いたとします。

<toast launch="好きな文字列">
  <visual>
    <binding template="ToastGeneric">
    </binding>
  </visual>
  <actions>
    <!-- 1) foreground -->
    <action content="yes" arguments="yes" />
    <!-- 2) background -->
    <action content="no" arguments="no" activationType="background" />
    <!-- 3) protocol -->
    <action content="web" arguments="https://example.com/" activationType="protocol" />
  </actions>
</toast>

このとき、actions の中の3つは、それぞれOnActivated、BackgroundTask、Protocolなのでなにもしない。でハンドリングしますが、 ボタンじゃないところを触った時はどうしたらいいの。というと、activationType="foreground" (何も指定しない場合はforeground)と同じように OnActivatedでハンドリングしないといけなくなりました。

つまるところ古いトーストのOnLaunchedのままにしておくとトーストタップしたときスプラッシュすら出ずにアプリが起動しなくなります。

なので、他にOnActivated使わないようなアプリなのであればApp.xaml.csをこんな感じに書くといいかもしれません。

protected override void OnLaunched(LaunchActivatedEventArgs e)
{
    OnActivated(e);
}

protected override void OnActivated(IActivatedEventArgs e)
{
    // ** OnLaunched のなかみをコピペしてちょっと修正したもの
    Frame rootFrame = Window.Current.Content as Frame;

    if (rootFrame == null)
    {
        // Create a Frame to act as the navigation context and navigate to the first page
        rootFrame = new Frame();

        rootFrame.NavigationFailed += OnNavigationFailed;

        if (e.PreviousExecutionState == ApplicationExecutionState.Terminated) { }

        Window.Current.Content = rootFrame;
    }

    if (rootFrame.Content == null)
    {
        // ** 適当にキャストして値を取り出しますよ
        rootFrame.Navigate(typeof(MainPage), 
            (e as LaunchActivatedEventArgs)?.Arguments ?? (e as ToastNotificationActivatedEventArgs).Argument);
    }
    Window.Current.Activate();
}

LaunchActivatedEventArgsはIActivatedEventArgsを実装しているので、こんな感じに書いてあげるとちょっと楽かも。 という感じですが、もしかするとOnLaunchedと、OnActivatedから呼び出すIActivatedEventArgsとArgumentを受け取る関数としたほうがいいかも? たとえばこんなかんじで。

protected override void OnLaunched(LaunchActivatedEventArgs e)
{
    OnLaunchedCore(e, e.Arguments);
}

protected override void OnActivated(IActivatedEventArgs e)
{
    if(e is ToastNotificationActivatedEventArgs){
        OnLaunchedCore(e, ((ToastNotificationActivatedEventArgs)e).Argument);
        return;
    }
    base.OnActivated();
}

private void OnLaunchedCore(IActivatedEventArgs e, object parameter)
{
    // ** OnLaunched のなかみをコピペしてちょっと修正したもの
    Frame rootFrame = Window.Current.Content as Frame;

    if (rootFrame == null)
    {
        // Create a Frame to act as the navigation context and navigate to the first page
        rootFrame = new Frame();

        rootFrame.NavigationFailed += OnNavigationFailed;

        if (e.PreviousExecutionState == ApplicationExecutionState.Terminated) { }

        Window.Current.Content = rootFrame;
    }

    if (rootFrame.Content == null)
    {
        // ** 適当にキャストして値を取り出しますよ
        rootFrame.Navigate(typeof(MainPage), parameter);
    }
    Window.Current.Activate();
}

ちなみに、古いトーストを使っている場合は従来どおりの挙動になります。つまりOnLaunchedで引数を取得します。

NuAns NEO がやってきた!

ついに、ついについに!やっとうちにもNuAns NEOがやってきた!!!!!ついったーだけで満足してたら、こういうところ からリンクされてしまっているのでちゃんと書きます!!

箱。おしゃれですね! 僕みたいなひきこもりは箱見ただけで蒸発しそうです。

中身はマニュアルとケーブルと本体。コネクタは両端両面刺さるタイプ。ケーブルは布?っぽいの巻いてあってなかなかいい。

さて本体。SIMスロットにはあらかじめNanoSIMアダプタが1枚ついてます。NanoSIMしか持ってないよ!って人でも安心。しかもSIMスロットは上に引き上げるタイプなのでアダプタが原因でスロットが壊れたりしない安心なやつ。とてもいいですね。

ケースはツートンカラーで、黄色と木目。ちょっと明るい感じで。

外観のついでに、12月ごろに3Dプリンタで作ったモックアップとサイズ比較して、ぴったりだったね!という答え合わせ。

ここからは電源入れてセットアップとか。でも、セットアップの中身はみんなもう見飽きてるだろうし省略するね。ちなみにバックアップは使わずに新規設定。

ちなみに電池はちょっとすくなめ。

というわけでセットアップが終わって最初のホーム画面。いわゆるデフォルトホームでシンプルですね。

OSバージョンは10586.0でした。1時間ぐらいちょっとおでかけして帰ってきたら10586.29がダウンロードされていたので、みなさんの電話もすぐに10586.29になると思います。すぐにアップデートしましょう!!*1ついでにストアの更新もたくさんありました。

あとは、Continuumの動きがみたいですよねってことでとりあえずそこらに転がってたMicrosoft Wireless Display Adapterに接続!ちなみに、Microsoftのワイヤレスディスプレイアダプタだと遅延が結構あれげでした。うちの無線環境も影響してるかもです。

そんなこんなでアップデートが落ちてきました。

と、問題なく更新できて問題なく使えてます。大丈夫です。NuAnsの普通のお話はここまでです。

最後に、ちゃんとでべろっぱーふうなことをして締めます。NuAns NEOをはじめとするContinuumに対応したデバイスは、ディスプレイやプロジェクタをサブディスプレイのようにして、大画面でアプリを利用できます。さて、Continuumでアプリを利用したときアプリのDeviceFamilyはどうなるのでしょうか。その答えはこちら。

はい。Mobileと出てますね。DeviceFamily=Mobileです。つまり、XAML Viewを使って、DesktopとMobileで別々なXAMLを使ったとすると、Continuum環境ではMobileが選択され、Mobile向けのビューが大画面に広がったものが利用できる。という結果になりました。みなさんXAML Viewでがんばらずに1枚のXAMLをAdaptive Triggerでレイアウト変えて頑張りましょう。

*1:ちなみに、10586.29未満はIME周りにバグがあって、Aristeaとか旧WindowsPhone8.x向けアプリでキーボードが正しく動きません。自分でコントロールできるわけではないですが、Windows Updateで配信されたら即アップデートをお勧めします。

UWPのLightとDarkでリソースを切り替える

LightなテーマとDarkなテーマでリソースを切り替えるにはx:Keyで指定するのが楽です。

こんな感じに使います。

<ResourceDictionary>
  <ResourceDictionary.ThemeDictionaries>
    <ResourceDictionary x:Key="Dark">
      <!-- Darkなリソースをここへ -->
    </ResourceDictionary>
    <ResourceDictionary x:Key="Light">
      <!-- Lightなリソースをここへ -->
    </ResourceDictionary>
  </ResourceDictionary.ThemeDictionaries>
</ResourceDictionary>

App.xamlとかに書いておけばStaticResourceまたはThemeResourceマークアップ拡張で参照できます。ちなみに、StaticResourceだとWindowsPhoneでテーマカラー変えたときに反応しないのでThemeResourceをおすすめします。

ThemeDictionariesの中はx:Keyが指定されたResourceDictionaryであればよいので、Sourceで別のファイルを参照もできます。

<ResourceDictionary>
  <ResourceDictionary.ThemeDictionaries>
    <ResourceDictionary x:Key="Dark" Source="/Themes/Dark.xaml" />
    <ResourceDictionary x:Key="Light" Source="/Themes/Light.xaml" />
  </ResourceDictionary.ThemeDictionaries>
</ResourceDictionary>

こうしておくと、リソースがぐっちゃぐちゃにならないのでおすすめです。

AdaptiveToastのライブラリでnpmデビューしました

Windows 10 でToastから文字入力できたり、ボタン置いたりいろいろ便利な感じになりました。Push通知でも使えるので、AristeaではWindows 10で実行するとToast通知から直接リプライできるようになってます。

さて、Push通知みたいなサーバを何で書きますか?わたしはnodejsで書きます。そんなとき、Windows Notification Service(WNS)に向けて通知なげるときはwnsモジュールを使うのがお手軽です。ちなみにたぶんこれAzure Mobile Servicesで動いてるのとほぼおんなじなんじゃないのって思っています。

ところがこのモジュール、Windows 8.x のころからアップデートされていないのでWindows 10な高機能な通知を投げられません。というより、Windows 10向けの通知に対応したXMLが組み立てられません。ので、それをいい感じにするライブラリをnpmに公開してしまいました。

npmのページにも使い方かいてますけど、こんなんでいいです。

var AdaptiveToast = require('adaptive-toast');
var builder = new AdaptiveToast();
 
builder
  .addText('foo')
  .addText('bar');

// xml でてきます
console.log(builder.build());

// wnsモジュールで送信する場合はこうやります。
 wns.send(channel, builder.build(), 'wns/toast', options, function(error, result){});

XMLで指定する順番にaddTextとかしていくといい感じに仕上がるはずです。Aristeaの通知で運用している分には問題なさそうなのでいまのところたぶん大丈夫です。同じようにAdaptiveTileってのもWindows 10でサポートされてますが、今のところ使い道思いついてないので作ってません。

今年買ってよかったもの

年の瀬ですね。2015年いろいろありましたけど、ふりかえりがてら2015年買ってよかったもの3つ挙げてみましょう。

Surface Book

やっぱりSurface Bookですよね。為替レートの都合で日本円で約36万でしたがそんなことはどうでもよくなるくらいいいデバイスです。なにがいいんだっていわれると、こんなところ。

  • キーボードが熱くならない(CPUは上半分なので)
  • 思ったよりスピーカがまとも(上半分についてるから手でこもらない)
  • 思ったより電池もつ(6時間くらい?)
  • キーボードのタッチがとてもいい
  • とても高解像度なモニタ

いまいちなところもあげとくと

  • おもたい
  • 重心がやっぱし上より

こんなかんじ。すごくよくできてると思います。Windowsを使うのであればまずお勧めしたいデバイスです。

da vinci Jr

次はXYZPrintingの3Dプリンタ da vinci Jr。Amazonのプライムデーでたまたま買えたのですが、普通にかっても5万円。十分手の届く価格だと思います。 フィラメントが専用のものしか使えないのですが、200m3000円程度なのでそんなにむちゃくちゃ高くないのかなって感じ。

あまりCAD力が向上していないので大したものは作れてないですがRaspberry Pi 2 のケースとか出力したりしてあそんでます。そういえばMADOSMAのケース作って遊んだこともありましたね。

手軽に立体物を出力できてすごく楽しいんですけど、やっぱりまだ工作機械なのかなー。という感じ。気温とかの環境に影響されたり、細かく調整してあげないといけなかったり、出力しやすそうな置き方を考えてあげないといけないし… でもまぁそこが楽しいんですよね。そのうちカラープリンタのように普及する日がくるのかな?

Nexus 5X

最後は悩んだけどもNexus 5Xを挙げてみました。画面OFFから指紋認証でロック画面を経由せずに画面ONされるの、すごくいい。今年の後半から虹彩認証を搭載したスマートフォンがいくつかリリースされてますけど、やっぱりスマートフォン指紋認証だとおもいます。虹彩認証はいまのところ、画面ONにする、カメラを見つめるというプロセスが必要。でも指紋認証ならポケットから取り出したら認証完了している。ということでやっぱスマートフォン指紋認証がいいなーって。

指紋認証Windows Hello対応したWindows 10 Mobile デバイスを待ち望んでいますよ。

おまけ

3つといわれて悩んだけどもどうしてもやっぱりあげたかったものたち。

MADOSMA Q501

たぶんみんなMADOSMAって答えると思ったのであえて外してみた。MADOSMAはとてもよくて、まず筐体が白なのがすばらしい。次に液晶パネルがきれい。そんでもって軽いってところがおすすめポイントだと思います。Windows 10 Mobile のOTAももう少ししたら来るのかな…?という感じですが、Windows 10 Mobile がほしいのであれば現時点だとまずおすすめしたいのがMADOSMA。

アップデートも積極的でサポートが手厚いところもいいところですね。

TAMRON SP 70-300mm F/4-5.6 Di VC USD

最後これだけ電子機器じゃなくてカメラのレンズなんですが、安い70-300mm。高いレンズなんて買えないので…Nikon純正でもよかったけどあちらは手振れ補正2.5段、TAMRONは4段だったのでTAMRONにしてしまいました。4段手振れ補正はファインダーをのぞけばびっくりしてしまうほどの精度で、フォーカスがあったらその瞬間絵がぴたっととまります。けっこうびっくり。

カナダで動物撮影するのにつかったけどわりとよかった、しいて言えばテレコンほしいな!って思いました。

Windows 10 TH2上でWindows8.1アプリのListViewが並び替えられないバグを回避する

Windows10 TH2、ビルド10586と呼ばれてるやつでWindows 8.1向けなアプリのListViewが並び替えられないバグを回避するコード書きました。

本来であれば、こうすれば並び替えられます。

<ListView CanReorderItems="True" CanDragItems="True" AllowDrop="True" />

これをTH2上で実行すると並び替えられそうな動きはするけども実際並び替えられません。ちなみにランタイムのバグだそうです。

この問題は以下の条件がそろった場合に発生します。

Windows 8.1 ターゲットのアプリが問題なのでWindows 10向け、つまりUWPでは発生しません。というわけでこのバグを回避するコードです。

プロジェクトに追加して適当な感じで使ってください。たとえばこんな感じ。

<ListView CanReorderItems="True" CanDragItems="True" AllowDrop="True" 
          extension:TH2Workarounds.ReorderListViewItem="True"/>

ItemsSourceにObservableCollectionがBindingされてる場合でしか試してません。たぶんGridViewでも動くかもしれませんが試してません。

*1:2015/12/12 時点のビルド10586.29 で未修正