20210827のAndroidに関する記事は4件です。

AndroidでDiscord Botを動かす

家にAndroid 5とかいう化石を搭載しているタブレットが2台ある。 片方はイヤホンジャックがタヒんでてYouTube専用機としても使いづらい。 なにか有効活用できないか。探した結果、Discord Botにたどり着いた。 動作環境 Android 5 UserLand 2.7.2 Python 3.6.9 Discord.py 1.7.3 本題 この記事ではBotアカウントの取得方法やBotのコードの書き方は書きません。環境構築の方法を超適当に書きます。 てことで、AndroidにDiscord Botを構築しよう! 1. UserLandのインストール これが無いとなにも始まりまらない。 ちなみに何故Termuxじゃないのかだが、TermuxはAndroid 5&6のサポートが打ち切られてしまったのと、Discord.pyが入れれなかった。 追記: clangを入れたらできた。(sudo apt install clang) F-droidかGoogle Play(https://play.google.com/store/apps/details?id=tech.ula)でインストールしてくる。 2. UserLandの準備 アプリを起動してリビジョンを選択する。 今回はトラブりたくなかったので無難にUbuntuを選択 ユーザー名とパスワードを設定してCONTINUEを2回押してしばらく待てば起動する。 儀式 $ sudo apt update $ sudo apt upgrade 必要なものをインストール $ sudo apt install python3 $ sudo apt install python3-pip $ sudo python3 -m pip install discord.py get-pip.pyでpipをインストールするとDiscord.pyがインストールできなかった。 追記: clangを入れ(ry テキストエディタについては論争に巻き込まれたくないので各自好きなのをインストールしてください。操作が簡単なのはnano Requestsとかも入れといても損はない。(というか入れたほうがいい) 日本語対応 デフォルトだと日本語に対応してない。 $ sudo apt install locales $ sudo dpkg-reconfigure locales //なんかいっぱい出てくるのでその中からja_JP.UTF-8ってのを見つけてその番号を入力 //環境変数にja_JP.UTF-8を設定 $ echo "export LANG=ja_JP.UTF-8" >> ~/.profile これで再ログインすれば日本語に対応してる。 環境構築はこれで終わり。 3. Wi-Fi接続が切れる スリープ状態にするとなんか接続が切れるのでこれhttps://m.apkpure.com/jp/advanced-wifi-lock-free/opotech.advancedwifilockfreeいれたら解決した。
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

Pepper SDK入門(32) Frameでメリーさんのように正確な現在地を把握する

はじめに 都市伝説に登場するメリーさんは、自分の現在地を丁寧に電話してきてくれます。Pepperもそのように正しい位置を把握できれば便利ですね!そこで登場するのがFrameです。 Frameは特定の位置を表します?それでは早速、順を追ってFrameについての理解を深めていきましょう。 FreeFrameかAttachedFrameで最先端 Frameの位置は後から更新されます。交信はしません?? FreeFrameは緯度と経度を表します。例えば本棚の位置にフレームを設定すれば、Pepperはどこに動いても本棚に戻ってきます。 AttachedFrameは対象の物体との相対位置を表します。人も設定することが可能で、その人が動けば一緒についていくピクミン的挙動を示します?画像は刷り込まれるひよこです。 作成後、AttachedFrameと親フレームの間にある偏りは更新され続けます。 下記のソースコードではAttachedFrameを作成しています↓ Frame baseFrame = ...; Transform transform1 = TransformBuilder.create().fromXTranslation(1); AttachedFrame attachedFrame = baseFrame.makeAttachedFrame(transform1); Transform transform2 = TransformBuilder.create().fromXTranslation(2); attachedFrame.update(transform2); 既存のFrameのGoToやLookAtアクションのため、ターゲットを特定します? Pepperに見せびらかそう✨ GoToアクションとFrameで特定の場所までおびき寄せる動いてもらうことができます。 Frame targetFrame = ...; GoTo goTo = GoToBuilder.with(qiContext) .withFrame(targetFrame) .build(); goTo.async().run(); LookAtで人の顔を見つめるなどしてもらいましょう?? Frame targetFrame = ...; LookAt lookAt = LookAtBuilder.with(qiContext) .withFrame(targetFrame) .build(); Future<Void> lookAtFuture = lookAt.async().run(); Robot Frame Pepperの位置を教えてくれます。 Actuationサービスで取り扱い可能です1。 Actuation actuation = qiContext.getActuation(); Frame robotFrame = actuation.robotFrame(); Human head Frame 人間の位置を表しています。Pepperが認知してくれます?‍?? Humanインスタンスでアクセス可能です。 Human human = ...; Frame headFrame = human.getHeadFrame(); Gaze Frame Pepperの胴体ではなく頭の位置を起点とするフレームで、Pepperの視線の位置と方向を表しています。ブラックホールのような目に吸収されそうですね??ちなみに首はかなり動く部分なので、使いにくいです。 Actuationサービスで取り扱い可能となっています。 Actuation actuation = qiContext.getActuation(); Frame gazeFrame = actuation.gazeFrame(); Map Frame Pepperの起点を表しています。ローカライズ(周辺地図の作成)が実行されていない場合は利用できません。Pepperはどこから来てどこへ行くのでしょう?? Mappingサービスで取り扱い可能です。 Mapping mapping = qiContext.getMapping(); Frame mapFrame = mapping.mapFrame(); Charging Station Frame Pepperの充電場所の位置と方向を表しています。 Pepperが充電場所を感知していない場合は利用できません。某電気ネズミは充電には利用できませんので注意してください?⚡️ Mappingサービスで取り扱い可能です。 Mapping mapping = qiContext.getMapping(); Frame chargingStationFrame = mapping.chargingStationFrame(); あとがき 今回もPepperSDKforAndroidを参考に書かせていただきました。 さらに詳しい情報はFrameのAPIリファレンスを参照してみてください! 次回はLookAtです、母音は同じですがCOOKPADのお話はありません。それでは〜?? RobotFrameを起点としてFreeFrameやAttachedFrameを作るため、Pepperの位置が分かるわけではなくPepperを起点の位置として使うフレームが取れるという意味になります。 ↩
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

Jetpack Composeの`@Stable`や`@Immutable`のバイトコード上の挙動を確かめてみる

どういうときにComposable関数がキャッシュされる?されない?ってすごく重要だと思っていますがみなさん理解されていますか? Compose 1.0.1で行っています。 これらのアノテーションについてはこちらで紹介しています。 また以下のドキュメントで言及されています 実際どうなるのみたいなところが気になったので、少し気になるパターンでまとめてみました。 キャッシュされているときはでコンパイルすると以下のようなskipのコードが入ります。 このGradle Pluginを使うと以下のようなJavaコードを簡単に見ることができます。 https://github.com/takahirom/decomposer if (($dirty & 11 ^ 2) == 0 && $composer.getSkipping()) { $composer.skipToGroupEnd(); } else { TextKt.Text-fLXpl1I(Intrinsics.stringPlus("Hello ", article), (Modifier)null, 0L, 0L, (FontStyle)null, (FontWeight)null, (FontFamily)null, 0L, (TextDecoration)null, (TextAlign)null, 0L, 0, false, 0, (Function1)null, (TextStyle)null, $composer, 0, 64, 65534); } チェックに用いたコード @Composable fun String(name: String) { Text(text = "Hello $name!") } data class Article(val title: String) @Composable fun DataClass(article: Article) { Text(text = "Hello $article") } data class MutableArticle(var title: String) @Composable fun MutableDataClass(article: MutableArticle) { Text(text = "Hello $article") } data class HasThrowableDataClass(val error:Throwable) @Composable fun HasThrowableDataClass(hasThrowableDataClass: HasThrowableDataClass) { Text(text = "Hello $hasThrowableDataClass") } @Immutable data class HasThrowableWithImmutableAnnotation(val error:Throwable) @Composable fun HasThrowableWithImmutableAnnotation(hasThrowable: HasThrowableWithImmutableAnnotation) { Text(text = "Hello $hasThrowable") } @Stable data class HasThrowableWithStableAnnotation(val error:Throwable) @Composable fun HasThrowableWithStableAnnotation(hasThrowable: HasThrowableWithStableAnnotation) { Text(text = "Hello $hasThrowable") } data class HasSimpleClass(val simpleClass: SimpleClass) class SimpleClass(val simpleText:String) @Composable fun HasSimpleClass(simpleClass: HasSimpleClass) { Text(text = "Hello $simpleClass") } data class HasHasThrowableDataClass(val obj: HasThrowableDataClass) @Composable fun HasHasThrowableDataClass(obj: HasHasThrowableDataClass) { Text(text = "Hello $obj") } 上記のコードは以下のリポジトリにおいてあり、ビルドすれば勝手にJavaコードがapp/build/decompiledにでコンパイルされたJavaコードが見られます。 https://github.com/takahirom/jetpack-compose-stability/blob/main/app/src/main/java/com/github/takahirom/jetpack_compose_stability_samples/StabilityChecks.kt デコンパイル結果はこちら package com.github.takahirom.jetpack_compose_stability_samples; import androidx.compose.material.TextKt; import androidx.compose.runtime.Composable; import androidx.compose.runtime.Composer; import androidx.compose.runtime.ComposerKt; import androidx.compose.runtime.ScopeUpdateScope; import androidx.compose.ui.Modifier; import androidx.compose.ui.text.TextStyle; import androidx.compose.ui.text.font.FontFamily; import androidx.compose.ui.text.font.FontStyle; import androidx.compose.ui.text.font.FontWeight; import androidx.compose.ui.text.style.TextAlign; import androidx.compose.ui.text.style.TextDecoration; import kotlin.Metadata; import kotlin.jvm.functions.Function1; import kotlin.jvm.functions.Function2; import kotlin.jvm.internal.Intrinsics; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; @Metadata( mv = {1, 5, 1}, k = 2, xi = 48, d1 = {"\u0000H\n\u0000\n\u0002\u0010\u0002\n\u0000\n\u0002\u0018\u0002\n\u0002\b\u0003\n\u0002\u0018\u0002\n\u0002\b\u0003\n\u0002\u0018\u0002\n\u0002\b\u0003\n\u0002\u0018\u0002\n\u0002\b\u0003\n\u0002\u0018\u0002\n\u0002\b\u0002\n\u0002\u0018\u0002\n\u0002\b\u0002\n\u0002\u0018\u0002\n\u0002\b\u0003\n\u0002\u0010\u000e\n\u0002\b\u0002\u001a\u0015\u0010\u0000\u001a\u00020\u00012\u0006\u0010\u0002\u001a\u00020\u0003H\u0007¢\u0006\u0002\u0010\u0004\u001a\u0015\u0010\u0005\u001a\u00020\u00012\u0006\u0010\u0006\u001a\u00020\u0007H\u0007¢\u0006\u0002\u0010\b\u001a\u0015\u0010\t\u001a\u00020\u00012\u0006\u0010\n\u001a\u00020\u000bH\u0007¢\u0006\u0002\u0010\f\u001a\u0015\u0010\r\u001a\u00020\u00012\u0006\u0010\u000e\u001a\u00020\u000fH\u0007¢\u0006\u0002\u0010\u0010\u001a\u0015\u0010\u0011\u001a\u00020\u00012\u0006\u0010\u0012\u001a\u00020\u0013H\u0007¢\u0006\u0002\u0010\u0014\u001a\u0015\u0010\u0015\u001a\u00020\u00012\u0006\u0010\u0012\u001a\u00020\u0016H\u0007¢\u0006\u0002\u0010\u0017\u001a\u0015\u0010\u0018\u001a\u00020\u00012\u0006\u0010\u0002\u001a\u00020\u0019H\u0007¢\u0006\u0002\u0010\u001a\u001a\u0015\u0010\u001b\u001a\u00020\u00012\u0006\u0010\u001c\u001a\u00020\u001dH\u0007¢\u0006\u0002\u0010\u001e¨\u0006\u001f"}, d2 = {"DataClass", "", "article", "Lcom/github/takahirom/jetpack_compose_stability_samples/Article;", "(Lcom/github/takahirom/jetpack_compose_stability_samples/Article;Landroidx/compose/runtime/Composer;I)V", "HasHasThrowableDataClass", "obj", "Lcom/github/takahirom/jetpack_compose_stability_samples/HasHasThrowableDataClass;", "(Lcom/github/takahirom/jetpack_compose_stability_samples/HasHasThrowableDataClass;Landroidx/compose/runtime/Composer;I)V", "HasSimpleClass", "simpleClass", "Lcom/github/takahirom/jetpack_compose_stability_samples/HasSimpleClass;", "(Lcom/github/takahirom/jetpack_compose_stability_samples/HasSimpleClass;Landroidx/compose/runtime/Composer;I)V", "HasThrowableDataClass", "hasThrowableDataClass", "Lcom/github/takahirom/jetpack_compose_stability_samples/HasThrowableDataClass;", "(Lcom/github/takahirom/jetpack_compose_stability_samples/HasThrowableDataClass;Landroidx/compose/runtime/Composer;I)V", "HasThrowableWithImmutableAnnotation", "hasThrowable", "Lcom/github/takahirom/jetpack_compose_stability_samples/HasThrowableWithImmutableAnnotation;", "(Lcom/github/takahirom/jetpack_compose_stability_samples/HasThrowableWithImmutableAnnotation;Landroidx/compose/runtime/Composer;I)V", "HasThrowableWithStableAnnotation", "Lcom/github/takahirom/jetpack_compose_stability_samples/HasThrowableWithStableAnnotation;", "(Lcom/github/takahirom/jetpack_compose_stability_samples/HasThrowableWithStableAnnotation;Landroidx/compose/runtime/Composer;I)V", "MutableDataClass", "Lcom/github/takahirom/jetpack_compose_stability_samples/MutableArticle;", "(Lcom/github/takahirom/jetpack_compose_stability_samples/MutableArticle;Landroidx/compose/runtime/Composer;I)V", "String", "name", "", "(Ljava/lang/String;Landroidx/compose/runtime/Composer;I)V", "app_release"} ) public final class StabilityChecksKt { @Composable public static final void String(@NotNull final String name, @Nullable Composer $composer, final int $changed) { Intrinsics.checkNotNullParameter(name, "name"); $composer = $composer.startRestartGroup(-1464156855); ComposerKt.sourceInformation($composer, "C(String)"); int $dirty = $changed; if (($changed & 14) == 0) { $dirty = $changed | ($composer.changed(name) ? 4 : 2); } if (($dirty & 11 ^ 2) == 0 && $composer.getSkipping()) { $composer.skipToGroupEnd(); } else { TextKt.Text-fLXpl1I("Hello " + name + '!', (Modifier)null, 0L, 0L, (FontStyle)null, (FontWeight)null, (FontFamily)null, 0L, (TextDecoration)null, (TextAlign)null, 0L, 0, false, 0, (Function1)null, (TextStyle)null, $composer, 0, 64, 65534); } ScopeUpdateScope var4 = $composer.endRestartGroup(); if (var4 != null) { var4.updateScope((Function2)(new Function2() { public final void invoke(@Nullable Composer $composer, int $force) { StabilityChecksKt.String(name, $composer, $changed | 1); } })); } } @Composable public static final void DataClass(@NotNull final Article article, @Nullable Composer $composer, final int $changed) { Intrinsics.checkNotNullParameter(article, "article"); $composer = $composer.startRestartGroup(-924370680); ComposerKt.sourceInformation($composer, "C(DataClass)"); int $dirty = $changed; if (($changed & 14) == 0) { $dirty = $changed | ($composer.changed(article) ? 4 : 2); } if (($dirty & 11 ^ 2) == 0 && $composer.getSkipping()) { $composer.skipToGroupEnd(); } else { TextKt.Text-fLXpl1I(Intrinsics.stringPlus("Hello ", article), (Modifier)null, 0L, 0L, (FontStyle)null, (FontWeight)null, (FontFamily)null, 0L, (TextDecoration)null, (TextAlign)null, 0L, 0, false, 0, (Function1)null, (TextStyle)null, $composer, 0, 64, 65534); } ScopeUpdateScope var4 = $composer.endRestartGroup(); if (var4 != null) { var4.updateScope((Function2)(new Function2() { public final void invoke(@Nullable Composer $composer, int $force) { StabilityChecksKt.DataClass(article, $composer, $changed | 1); } })); } } @Composable public static final void MutableDataClass(@NotNull final MutableArticle article, @Nullable Composer $composer, final int $changed) { Intrinsics.checkNotNullParameter(article, "article"); $composer = $composer.startRestartGroup(-738357243); ComposerKt.sourceInformation($composer, "C(MutableDataClass)"); TextKt.Text-fLXpl1I(Intrinsics.stringPlus("Hello ", article), (Modifier)null, 0L, 0L, (FontStyle)null, (FontWeight)null, (FontFamily)null, 0L, (TextDecoration)null, (TextAlign)null, 0L, 0, false, 0, (Function1)null, (TextStyle)null, $composer, 0, 64, 65534); ScopeUpdateScope var3 = $composer.endRestartGroup(); if (var3 != null) { var3.updateScope((Function2)(new Function2() { public final void invoke(@Nullable Composer $composer, int $force) { StabilityChecksKt.MutableDataClass(article, $composer, $changed | 1); } })); } } @Composable public static final void HasThrowableDataClass(@NotNull final HasThrowableDataClass hasThrowableDataClass, @Nullable Composer $composer, final int $changed) { Intrinsics.checkNotNullParameter(hasThrowableDataClass, "hasThrowableDataClass"); $composer = $composer.startRestartGroup(1081258760); ComposerKt.sourceInformation($composer, "C(HasThrowableDataClass)"); TextKt.Text-fLXpl1I(Intrinsics.stringPlus("Hello ", hasThrowableDataClass), (Modifier)null, 0L, 0L, (FontStyle)null, (FontWeight)null, (FontFamily)null, 0L, (TextDecoration)null, (TextAlign)null, 0L, 0, false, 0, (Function1)null, (TextStyle)null, $composer, 0, 64, 65534); ScopeUpdateScope var3 = $composer.endRestartGroup(); if (var3 != null) { var3.updateScope((Function2)(new Function2() { public final void invoke(@Nullable Composer $composer, int $force) { StabilityChecksKt.HasThrowableDataClass(hasThrowableDataClass, $composer, $changed | 1); } })); } } @Composable public static final void HasThrowableWithImmutableAnnotation(@NotNull final HasThrowableWithImmutableAnnotation hasThrowable, @Nullable Composer $composer, final int $changed) { Intrinsics.checkNotNullParameter(hasThrowable, "hasThrowable"); $composer = $composer.startRestartGroup(-1872658300); ComposerKt.sourceInformation($composer, "C(HasThrowableWithImmutableAnnotation)"); int $dirty = $changed; if (($changed & 14) == 0) { $dirty = $changed | ($composer.changed(hasThrowable) ? 4 : 2); } if (($dirty & 11 ^ 2) == 0 && $composer.getSkipping()) { $composer.skipToGroupEnd(); } else { TextKt.Text-fLXpl1I(Intrinsics.stringPlus("Hello ", hasThrowable), (Modifier)null, 0L, 0L, (FontStyle)null, (FontWeight)null, (FontFamily)null, 0L, (TextDecoration)null, (TextAlign)null, 0L, 0, false, 0, (Function1)null, (TextStyle)null, $composer, 0, 64, 65534); } ScopeUpdateScope var4 = $composer.endRestartGroup(); if (var4 != null) { var4.updateScope((Function2)(new Function2() { public final void invoke(@Nullable Composer $composer, int $force) { StabilityChecksKt.HasThrowableWithImmutableAnnotation(hasThrowable, $composer, $changed | 1); } })); } } @Composable public static final void HasThrowableWithStableAnnotation(@NotNull final HasThrowableWithStableAnnotation hasThrowable, @Nullable Composer $composer, final int $changed) { Intrinsics.checkNotNullParameter(hasThrowable, "hasThrowable"); $composer = $composer.startRestartGroup(340271846); ComposerKt.sourceInformation($composer, "C(HasThrowableWithStableAnnotation)"); int $dirty = $changed; if (($changed & 14) == 0) { $dirty = $changed | ($composer.changed(hasThrowable) ? 4 : 2); } if (($dirty & 11 ^ 2) == 0 && $composer.getSkipping()) { $composer.skipToGroupEnd(); } else { TextKt.Text-fLXpl1I(Intrinsics.stringPlus("Hello ", hasThrowable), (Modifier)null, 0L, 0L, (FontStyle)null, (FontWeight)null, (FontFamily)null, 0L, (TextDecoration)null, (TextAlign)null, 0L, 0, false, 0, (Function1)null, (TextStyle)null, $composer, 0, 64, 65534); } ScopeUpdateScope var4 = $composer.endRestartGroup(); if (var4 != null) { var4.updateScope((Function2)(new Function2() { public final void invoke(@Nullable Composer $composer, int $force) { StabilityChecksKt.HasThrowableWithStableAnnotation(hasThrowable, $composer, $changed | 1); } })); } } @Composable public static final void HasSimpleClass(@NotNull final HasSimpleClass simpleClass, @Nullable Composer $composer, final int $changed) { Intrinsics.checkNotNullParameter(simpleClass, "simpleClass"); $composer = $composer.startRestartGroup(790858239); ComposerKt.sourceInformation($composer, "C(HasSimpleClass)"); int $dirty = $changed; if (($changed & 14) == 0) { $dirty = $changed | ($composer.changed(simpleClass) ? 4 : 2); } if (($dirty & 11 ^ 2) == 0 && $composer.getSkipping()) { $composer.skipToGroupEnd(); } else { TextKt.Text-fLXpl1I(Intrinsics.stringPlus("Hello ", simpleClass), (Modifier)null, 0L, 0L, (FontStyle)null, (FontWeight)null, (FontFamily)null, 0L, (TextDecoration)null, (TextAlign)null, 0L, 0, false, 0, (Function1)null, (TextStyle)null, $composer, 0, 64, 65534); } ScopeUpdateScope var4 = $composer.endRestartGroup(); if (var4 != null) { var4.updateScope((Function2)(new Function2() { public final void invoke(@Nullable Composer $composer, int $force) { StabilityChecksKt.HasSimpleClass(simpleClass, $composer, $changed | 1); } })); } } @Composable public static final void HasHasThrowableDataClass(@NotNull final HasHasThrowableDataClass obj, @Nullable Composer $composer, final int $changed) { Intrinsics.checkNotNullParameter(obj, "obj"); $composer = $composer.startRestartGroup(1108688073); ComposerKt.sourceInformation($composer, "C(HasHasThrowableDataClass)"); TextKt.Text-fLXpl1I(Intrinsics.stringPlus("Hello ", obj), (Modifier)null, 0L, 0L, (FontStyle)null, (FontWeight)null, (FontFamily)null, 0L, (TextDecoration)null, (TextAlign)null, 0L, 0, false, 0, (Function1)null, (TextStyle)null, $composer, 0, 64, 65534); ScopeUpdateScope var3 = $composer.endRestartGroup(); if (var3 != null) { var3.updateScope((Function2)(new Function2() { public final void invoke(@Nullable Composer $composer, int $force) { StabilityChecksKt.HasHasThrowableDataClass(obj, $composer, $changed | 1); } })); } } } キャッシュされたかの結果 試したもの キャッシュされた? String ○ data class Article(val title: String) ○ data class MutableArticle(var title: String) ✗ data class HasThrowableDataClass(val error:Throwable) ✗ @Immutable data class HasThrowableWithImmutableAnnotation(val error:Throwable) ○ @Stable data class HasThrowableWithStableAnnotation(val error:Throwable) ○ data class HasSimpleClass(val simpleClass: SimpleClass)class SimpleClass(val simpleText:String) ○ data class HasHasThrowableDataClass(val obj: HasThrowableDataClass) ✗ valにしていて、変わらない想定でも、なにかinterfaceとかthrowableとかが入り込んじゃう場合は @Stableなどをつけたほうが良さそうに見えます。 StableとImmutableの違いをこのバイトコード上では見つけることができませんでした。 changed()は以下のようになっていたので、両方equalsが使われていそうに見えました。 @ComposeCompilerApi override fun changed(value: Any?): Boolean { return if (nextSlot() != value) { updateValue(value) true } else { false } }
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

現役AndroidエンジニアがAndroid Kotlin Fundamentalsコードラボに挑戦!その3

前回 Lesson 3: Navigation 03.1: Create a fragment 内容 クイズアプリの作成 フラグメントの追加        メモ フラグメントをコンパイルするには、バインディングオブジェクトを作成し、フラグメントのビューを拡張する アクティビティのレイアウトファイルに < fragment > 要素を追加する 1つのアクティビティで複数のフラグメントを使用したり、1つのフラグメントを複数のアクティビティで使用したりできる 03.2: Define navigation paths 内容 クイズアプリの作成 ナビゲーションコンポーネントの追加 ナビゲーションホストフラグメントの使用 条件付きナビゲーションの追加 → クイズの正誤で遷移先を変える バックキーの遷移先を指定 アクションバーに戻るボタン追加 アクションバーにオプションメニューの追加 ナビゲーションドロワーの追加 ハンバーガーボタンからナビゲーションドロワーを開く 宿題:タイトル画面にルールボタンとバージョン情報ボタンを追加する 宿題:ルール画面とバージョン情報画面にプレイボタンを追加、そこからの遷移でゲーム画面から戻ったときにタイトル画面を表示する                                        メモ ナビゲーションホストフラグメントは自作せず、androidx.navigation.fragment.NavHostFragmentを使用する アクションバーの戻るボタンは NavigationUI.setupActionBarWithNavController で追加できる bindingさせたいViewのレイアウトファイルはlayoutタグで全体を囲む! 03.3: Start an external Activity 内容 クイズアプリの作成 ゲーム結果を共有する →NavDirectionを活用して引数を渡す →暗黙的インテントを活用して他のアプリを呼び出す        メモ packageManagerを使って端末内のアプリを取得することができる! フラグメント間でデータを渡す時はSafeArgsを使用するとエラーをキャッチできる 感想 その2までは割と知っていることも多かったが、 今回は使ったことのないものばかりでてきて難しかった。 使ったことのない機能をたくさんつかってアプリを作っていくのはおもしろかった! クイズアプリの内容もAndroid開発に関することなので、動作テスト中にも勉強ができてよかった笑 個人的にnavigationのDesignをつくるときが結構楽しい↓ 今すぐ使いこなすのは難しそうだけど読めるようになったのは大きな成果だと思う!! 次はよくわからなくなりがちだけどとっても大事なライフサイクルのお勉強! がんばるぞ〜!? かかった時間 約6時間
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む