2022/5/23/Flutter/Adaptive Apps in Flutterの訳パート1

 

Contents

Adaptive Apps in Flutter

1. Introduction

In this codelab, you’ll learn how to build a Flutter app that adapts to the platform that it is running on, be that Android, iOS, the web, Windows, macOS, or Linux.

このコードラボでは、Android、iOS、Web、Windows、macOS、Linuxなど、実行するプラットフォームに適応する(adaptive)Flutterアプリを構築する方法を学びます。

What you’ll learn

  • How to grow a Flutter app designed for mobile to work on all six platforms supported by Flutter.

モバイル向けにデザインされたFlutterアプリを、Flutterがサポートする6つのプラットフォームすべてで動作するように成長させる方法。

 

  • The different Flutter APIs for detecting the platform and when to use each API.

プラットフォームを検出するためのFlutter APIの種類と、各APIを使用するタイミングについて説明します。

 

  • Adapting to the restrictions and expectations of running an app on the web.

ウェブ上でアプリを実行する際の制約や期待に適応すること。

 

  • How to use different packages alongside each other to support the full range of Flutter’s platforms.

FLutterのそれぞれのプラットフォームの全ての範囲をサポートするために、それぞれの異なるパッケージを使用する方法。

 

What you’ll build

あなたが作るもの

 

In this codelab, you’ll initially build a Flutter app for Android and iOS that explores Flutter’s YouTube playlists.

このコードラボでは、FlutterのYouTubeプレイリストを探索するFlutterアプリ(iOSとAndroid向け)を一から作ります。

 

You will then adapt this application to work on the three desktop platforms (Windows, macOS, and Linux) by modifying how information is displayed given the size of the application window.

そして、このアプリケーションを3つのデスクトッププラットフォーム(Windows、macOS、Linux)で動作するように、アプリケーションのウィンドウサイズに応じた情報の表示方法を変更することで適応させます。

 

Then you will adapt the application for the web by making text displayed in the app selectable, as web users expect.

そして、Webユーザーが期待するように、アプリに表示されるテキストを選択可能にすることで、アプリケーションをWeb用に適合させます。

 

Finally, you will add authentication to the app so you can explore your own Playlists, as opposed to the ones created by the Flutter team, which requires different approaches to authentication for Android, iOS, and the web, versus the three desktop platforms Windows, macOS, and Linux.

最後に、Flutterチームが作成したプレイリストとは対照的に、自分のプレイリストを探索できるようにアプリに認証を追加します。この認証は、Android、iOS、Webと、Windows、macOS、Linuxの3つのデスクトッププラットフォームで異なるアプローチで認証を行うことを必要とします。

Here is a screenshot of the Flutter app on Android and iOS:

 


This codelab focuses on transforming a mobile Flutter app into an adaptive app that works across all six Flutter platforms. Non-relevant concepts and code blocks are glossed over, and are provided for you to simply copy and paste.

このコードラボは、モバイルFlutterアプリを、6つのFlutterプラットフォームすべてで動作するアダプティブアプリに変換することに重点を置いています。関連性のないコンセプトやコードブロックは排除し、コピー&ペーストするだけで利用できるように提供されています。


2. Set up your Flutter environment

This codelab covers developing Flutter apps across multiple operating systems. While one can reach four of the six target platforms from a macOS laptop or desktop (Android, iOS, web, and macOS), to reach all six will require multiple systems. Developers on all development platforms should be able to develop for Android, the web, and the desktop operating system you are developing on. This is enough to cover all of the lessons of this codelab.

このコードラボでは、複数のオペレーティングシステムにまたがるFlutterアプリの開発について説明します。macOSのラップトップやデスクトップから6つのターゲットプラットフォームのうち4つ(Android、iOS、Web、macOS)に到達できますが、6つすべてに到達するためには複数のシステムが必要です。すべての開発プラットフォームの開発者は、Android、Web、そして開発しているデスクトップOS向けに開発できるようにする必要があります。これだけあれば、このコードラボの全レッスンをカバーすることができます。

 

You must install software to compile for various targets. For example, you need access to Xcode tooling for iOS and macOS development, Android Studio to install Android tooling, Visual Studio for Win32 compilation tooling, and so forth. For details, please refer to Flutter’s getting started documentation, then follow that with flutter.dev/desktop.

様々なターゲットにコンパイルするためのソフトウェアをインストールする必要があります。例えば、iOSやmacOSの開発にはXcodeのツール、AndroidのツールをインストールするにはAndroid Studio、Win32のコンパイルツールにはVisual Studio、といった具合にアクセスする必要があります。詳しくはFlutterのgeting startedドキュメントを参照し、それに沿ってflutter.dev/desktopをインストールしてください。


3. Get started

工事中🏗

 


Creating a Flutter project

An easy way to get started writing Flutter for desktop apps is to use the Flutter command-line tool to create a Flutter project. Alternatively, your IDE may provide a workflow for creating a Flutter project through its UI.

デスクトップアプリケーション用のFlutterを書き始める簡単な方法は、Flutterコマンドラインツールを使用してFlutterプロジェクトを作成することです。あるいは、IDEがUIを通してFlutterプロジェクトを作成するワークフローを提供している場合もあります。

 

To make sure everything is working, run the boilerplate Flutter application as a mobile app as shown below. Alternatively, open this project in your IDE, and use its tooling to run the application. Thanks to the previous step, running as a desktop application should be the only available option.

すべてがうまくいっていることを確認するために、以下のようにボイラープレートのFlutterアプリケーションをモバイルアプリとして実行します。または、IDEでこのプロジェクトを開き、そのツールでアプリケーションを実行します。前のステップのおかげで、デスクトップアプリケーションとして実行することが唯一の利用可能なオプションであるはずです。

 

You should now see the app running. Modify the content in lib/main.dart as follows, and perform a hot reload to update the content. How to perform a hot reload changes depending on whether you are running the app via the command line (type ‘r’ into the console window) or via an editor (in which case, saving the file is probably enough to trigger hot reload).

これで、アプリが動作しているのが確認できるはずです。lib/main.dart の内容を以下のように変更し、ホットリロードを実行して内容を更新します。ホットリロードの実行方法は、アプリをコマンドライン経由で実行しているか(コンソールウィンドウに ‘r’ と入力)、エディタ経由で実行しているか(その場合、ファイルを保存するだけでホットリロードが開始されます)によって異なります。

import 'dart:io' show Platform;
import 'package:flutter/foundation.dart' show kIsWeb;
import 'package:flutter/material.dart';

void main() {
  runApp(const MyApp());
}

class MyApp extends StatelessWidget {
  const MyApp({Key? key}) : super(key: key);

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Flutter Demo',
      theme: ThemeData(
        primarySwatch: Colors.blue,
      ),
      home: const ResizeablePage(),
    );
  }
}

class ResizeablePage extends StatelessWidget {
  const ResizeablePage({Key? key}) : super(key: key);

  @override
  Widget build(BuildContext context) {
    final mediaQuery = MediaQuery.of(context);
    final themePlatform = Theme.of(context).platform;

    return Scaffold(
      body: Center(
        child: Column(
          mainAxisAlignment: MainAxisAlignment.center,
          children: <Widget>[
            Text(
              'Window properties',
              style: Theme.of(context).textTheme.headline5,
            ),
            const SizedBox(height: 8),
            SizedBox(
              width: 350,
              child: Table(
                textBaseline: TextBaseline.alphabetic,
                children: <TableRow>[
                  _fillTableRow(
                    context: context,
                    property: 'Window Size',
                    value: '${mediaQuery.size.width.toStringAsFixed(1)} x '
                        '${mediaQuery.size.height.toStringAsFixed(1)}',
                  ),
                  _fillTableRow(
                    context: context,
                    property: 'Device Pixel Ratio',
                    value: mediaQuery.devicePixelRatio.toStringAsFixed(2),
                  ),
                  _fillTableRow(
                    context: context,
                    property: 'Platform.isXXX',
                    value: platformDescription(),
                  ),
                  _fillTableRow(
                    context: context,
                    property: 'Theme.of(ctx).platform',
                    value: themePlatform.toString(),
                  ),
                ],
              ),
            ),
          ],
        ),
      ),
    );
  }

  TableRow _fillTableRow(
      {required BuildContext context,
      required String property,
      required String value}) {
    return TableRow(
      children: [
        TableCell(
          verticalAlignment: TableCellVerticalAlignment.baseline,
          child: Padding(
            padding: const EdgeInsets.all(8.0),
            child: Text(property),
          ),
        ),
        TableCell(
          verticalAlignment: TableCellVerticalAlignment.baseline,
          child: Padding(
            padding: const EdgeInsets.all(8.0),
            child: Text(value),
          ),
        ),
      ],
    );
  }

  String platformDescription() {
    if (kIsWeb) {
      return 'Web';
    } else if (Platform.isAndroid) {
      return 'Android';
    } else if (Platform.isIOS) {
      return 'iOS';
    } else if (Platform.isWindows) {
      return 'Windows';
    } else if (Platform.isMacOS) {
      return 'macOS';
    } else if (Platform.isLinux) {
      return 'Linux';
    } else if (Platform.isFuchsia) {
      return 'Fuchsia';
    } else {
      return 'Unknown';
    }
  }
}

The above app is designed to give you a feeling for how different platforms can be detected and adapted to. Here is the app running natively on Android and iOS:

上記のアプリは、異なるプラットフォームをどのように検出し、適応させることができるかを感じていただくためのものです。ここでは、AndroidとiOSでネイティブに動作するアプリを紹介します。


And here is the same code running natively on macOS and inside of Chrome, again running on macOS.

そして、同じコードがmacOS上でネイティブに動作している様子と、Chromeの内部で、やはりmacOS上で動作している様子をご紹介します。

The important point to note here is that, at first glance, Flutter is doing what it can to adapt the content to the display it is running on.

ここで重要なのは、一見するとFlutterはコンテンツを実行中のディスプレイに適応させるためにできることをしているように見えるという点です。

 

The laptop on which these screenshots were taken has a high resolution Mac display, which is why both the macOS and web versions of the app are rendered at Device Pixel Ratio of 2. Meanwhile, on the iPhone 12, you see a ratio of 3, and 2.63 on the Pixel 2. In all cases the displayed text is roughly similar, making our job as developers a lot easier.

これらのスクリーンショットを撮影したノートパソコンには高解像度のMacディスプレイが搭載されており、そのためmacOS版とウェブ版のアプリはどちらもデバイスピクセル比2.00でレンダリングされています。一方、iPhone 12では3.00、Pixel 2では2.63の比率で表示されています。いずれの場合も、表示されるテキストはほぼ同じで、開発者としての仕事がとてもやりやすくなっています。

 

The second point to note is that the two options for checking out which platform the code is running on results in different values.

2つ目のポイントは、コードがどのプラットフォームで実行されているかをチェックするための2つのオプションが、異なる値になっていることです。

 

The first option inspects the Platform object imported from dart:io, while the second option (available only inside the Widget’s build method), retrieves the Theme object from the BuildContext argument.

最初のオプションはdart:ioからインポートされたPlatformオブジェクトを検査し、2番目のオプション(Widgetのビルドメソッド内でのみ利用可能)はBuildContext引数からThemeオブジェクトを取得します。

 

The reason that these two methods return different results is that their intent is different.

この2つの方法が異なる結果を返すのは、その意図が異なるからです。

 

The Platform object imported from dart:io is meant to be used for making decisions that are independent of rendering choices.

dart:ioからインポートされたPlatformオブジェクトは、レンダリングの選択に依存しない意思決定を行うために使用されることを意図しています。

 

A prime example of this is deciding which plugins to use, which may or may not have matching native implementations for a specific physical platform.

この典型的な例は、使用するプラグインを決定することです。プラグインは、特定の物理プラットフォームに一致するネイティブ実装を備えている場合と備えていない場合があります。

 

Extracting the Theme from the BuildContext is intended for implementation decisions that are Theme centric.

BuildContextからテーマを抽出することは、Themeを中心とした実装の意思決定を目的としています。

 

A prime example of this is deciding whether to use the Material slider, or the Cupertino slider, as discussed in Slider.adaptive.

この典型的な例は、Slider.adaptiveで説明されているように、マテリアルスライダーを使用するか、クパチーノスライダーを使用するかを決定することです。


Best Practices

  • For decisions that are not dependent on platform specific capabilities, use Theme.of(context).platform. A primary example of this is adapting the ordering of buttons to conform to operating system idioms. Most of your adaptive code should use this approach to adapt to different platforms.

プラットフォーム固有の機能に依存しない決定には、Theme.of(context).platformを使用します。この主な例は、オペレーティングシステムのイディオムに適合するようにボタンの順序を適応させることです。ほとんどのアダプティブコードは、異なるプラットフォームに適応するために、このアプローチを使用する必要があります。

 

  • For decisions that depend on platform specific capabilities, use the kIsWeb constant along with isAndroid, isIOS and friends from dart:io‘s Platform class. A capability difference example is the browser requirement for CORS headers on cross domain requests.

プラットフォーム固有の機能に依存する決定には、dart:ioのPlatformクラスのisAndroid、isIOSなどと一緒にkIsWeb定数を使用します。能力の違いの例としては、クロスドメインリクエストにおけるCORSヘッダに対するブラウザの要件があります。

 

In the next section you’ll build a basic YouTube playlist explorer app that is optimized purely for Android and iOS. In the following sections you will add various adaptations to make the app work better on desktop and the web.

次のセクションでは、Android と iOS 向けに純粋に最適化された基本的な YouTube プレイリスト エクスプローラー アプリを作成します。その次のセクションでは、このアプリをデスクトップやウェブでよりよく動作させるために、さまざまな改良を加えます。


4. Build a mobile app

Add packages

このアプリでは、YouTube Data APIへのアクセス、ステート管理、そしてテーマ設定のタッチを得るために、さまざまなFlutterパッケージを使用します。

$ flutter pub add googleapis
Resolving dependencies...
+ _discoveryapis_commons 1.0.2
+ googleapis 7.0.0
+ http 0.13.4
+ http_parser 4.0.0
  test_api 0.4.3 (0.4.8 available)
Changed 4 dependencies!

 

The first package, googleapis is a generated Dart library for accessing Google APIs.

最初のパッケージであるgoogleapisは、GoogleのAPIにアクセスするためのDartライブラリを生成したものです。


$ flutter pub add http
Resolving dependencies...
  test_api 0.4.3 (0.4.8 available)
Got dependencies!

The http package will be instrumental for building out the ability to access the YouTube Data API using API keys.

httpパッケージはAPIキーを利用してYouTube Data APIにアクセスする機能を構築するために必要なものです。


$ flutter pub add provider

providerパッケージは状態管理に使用します。

$ flutter pub add url_launcher

Use url_launcher as a way of jumping into a video from a playlist. As you can see from the resolved dependencies, url_launcher has implementations for Windows, macOS, Linux, and the web, in addition to the default Android and iOS. This is one capability you won’t need to create platform specific code for.

プレイリストから動画にジャンプする方法として、url_launcherを使用します。解決された依存関係からわかるように、url_launcher には、デフォルトの Android と iOS に加えて、Windows、macOS、Linux、Web のための実装があります。これは、プラットフォーム固有のコードを作成する必要がない機能の 1 つです。


$ flutter pub add flex_color_scheme

This last package is purely about giving the app a nice default color scheme. See the flex_color_schemedocumentation to get an understanding of the full range of capabilities.

この最後のパッケージは純粋にアプリに素敵なデフォルトのColorSchemeを与えるためのものです。flex_color_scheme のドキュメントを参照し、すべての機能を理解してください。


Configuring the mobile apps for url_launcher

The url_launcher plugin requires configuration of the Android and iOS runner applications. In the iOS Flutter runner, add the following lines to the plist dictionary.

url_launcher プラグインは、Android と iOS のrunnerアプリケーションの設定が必要です。iOSのFlutter runnerで、plist dictionaryに以下の行を追加します。

ios/Runner/Info.plist

<key>LSApplicationQueriesSchemes</key>
<array>
        <string>https</string>
        <string>http</string>
        <string>tel</string>
        <string>mailto</string>
</array>

In the Android Flutter runner, add the following lines to the Manifest.xml. Add this queries node as a direct child of the manifest node and a peer of the application node.

Android Flutter runnerで、Manifest.xml に次の行を追加します。このクエリノードをマニフェストノードの直接の子として、またアプリケーションノードのピアとして追加します。

android/app/src/main/AndroidManifest.xml

<queries>
    <intent>
        <action android:name="android.intent.action.VIEW" />
        <data android:scheme="https" />
    </intent>
    <intent>
        <action android:name="android.intent.action.DIAL" />
        <data android:scheme="tel" />
    </intent>
    <intent>
        <action android:name="android.intent.action.SEND" />
        <data android:mimeType="*/*" />
    </intent>
</queries>

For more details about these required configuration changes, please see the url_launcher documentation.

さらに詳しい情報はurl_launcherのドキュメントをご覧ください。


工事中🏗

 

 

 

パート2へ >>

参考

https://codelabs.developers.google.com/codelabs/flutter-adaptive-app?hl=en#0

コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です