Skip to content

1.1.Activity

takafumi nanao edited this page Feb 4, 2018 · 1 revision

Activityとは

Activityは、電話をかける、写真を撮影する、メールを送る、マップを閲覧するといった操作をユーザーができる画面を提供するアプリケーションコンポーネントです。 一般的なアプリでは一番多く利用する重要なコンポーネントで主に画面の表示、画面のライフサイクルの管理を担います。 一般的にはアプリケーションに1つのメインのActivityクラスを用意し、アプリケーションを起動した時にそのActivityクラスの画面が表示されるようにします。 Activityクラスを作成するにはActivity(もしくはそのサブクラス)のサブクラスを作成する必要があります。 現在はActivityクラスを作る場合は、Activityのサブクラスではなく、AppCompatActivityのサブクラスとして定義することが推奨されています。

Activity作成時の注意点

ActivityはAndroidManifest.xml内に定義を行ったActivityのみアクセスが可能です。Manifestファイル内に記述がない場合はアクセス時にエラーになります。
AndroidStudioのActivityを新規作成するウィザードから作成した場合は自動で必要最低限のmanifestの記述を追記してくれるので、AndroidStudioのウィザードから作成することをおすすめします

Activityのライフサイクル

Activityのライフサイクル

Activityにはライフサイクルが存在します。
主に画面が呼び出されてから、必要なくなって破棄される(メモリ上から追い出される)までの一連の流れをライフサイクルとして扱います。
以下に上げるライフサイクルの各状態は、ライフサイクルコールバックとして、Activity クラスに同じ名前で定義されています。

Activityのライフサイクルの注意点

  • onCreateとonDestroy等、対になるライフサイクルのメソッドが存在します。
    確保したリソース等は対になるライフサイクルで適宜開放を行わないとメモリリークなどが発生します。
  • 一見ライフサイクルに変化のない画面回転時に一度onDestroyまで呼ばれてonCreateからもう一度呼ばれる
    どのような時にライフサイクルの変化が起きるかを一度調べておくことをおすすめします

onCreate

アクティビティが最初に作成されるときに呼び出されます。 ここで、ビューの作成、リストとのデータバインドといった、通常の静的なセットアップを行います。 アクティビティの前の状態を含む Bundle オブジェクトを取り出せた場合、それをメソッドに渡します(後半のアクティビティの状態を保存するをご覧ください)。 常に onStart() が後に続きます。

class MainActivity : AppCompatActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        // レイアウトを指定して、Activity がコントロールする View として扱うようにする
        setContentView(R.layout.activity_main);
    }
}

onStart

アクティビティがユーザーに見える状態になる直前に呼び出されます。 アクティビティがフォアグラウンドになったときは onResume() が後に続き、アクティビティが非表示になったときは onStop() が後に続きます。

onRestart

このライフサイクルは少し特殊でonStopが呼ばれた後にonStartが呼ばれる直前に呼び出されます。 そのため、Activityが最初に作成される場合には呼び出されません。 アクティビティが停止した後、再開する直前に呼び出されます。 常に onStart() が後に続きます。

onResume

アクティビティとユーザーのインタラクションが始まる直前に呼び出されます。
この時点で、アクティビティはアクティビティ スタックの先頭にあり、ユーザー入力の準備ができています。 常にonPause()が後に続きます。

onPause

システムが別のアクティビティを再開する直前に呼び出されます。 通常、このメソッドは永続化データへの未保存の変更をコミットしたり、アニメーションや CPU を消費する可能性のあるその他の動作を停止したりする際に使用されます。
それが完了するまで次のアクティビティが再開できないため、それらの操作は迅速に行う必要があります。
アクティビティが前面に戻るときは onResume() が後に続き、アクティビティが非表示になるときは onStop() が後に続きます。

onStop

アクティビティがユーザーに見えなくなると呼び出されます。 これは、アクティビティが破棄されたか、別のアクティビティ(既存のアクティビティや新しいアクティビティ)が再開されてこのアクティビティを覆っている場合に起こります。
アクティビティがユーザー操作が可能な状態に戻るときは onRestart() が後に続き、アクティビティがなくなるときは onDestroy() が後に続きます。

onDestroy

アクティビティが破棄される前に呼び出されます。
これはアクティビティが受け取る最後の呼び出しです。 アクティビティが終了した(finish() が呼び出された)か、アクティビティ領域を節約するためにシステムが一時的にこのアクティビティを破棄した場合に呼び出されます。 この 2 つのシナリオは、isFinishing() メソッドで区別できます。 一方、システムの要求によって、アプリのプロセスごと kill された場合には、この状態になることなくアプリケーションが終了します。

レイアウトの要素にアクセスをする

Activityからレイアウトの要素にアクセスする方法はいくつかあります。
DataBindingライブラリを利用したアクセスが便利なのですが、そちらについては後の章で説明します。
ここでは基礎的なfindViewByIdを使ったアクセスについて説明します。 ActivityのonCreate内のsetContentViewメソッドで読み込んだxml内に下記のような要素があった場合

<TextView
    android:id="@+id/greeting"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content" />

Activity内で下記のように記述するとxmlのTextViewの部分に、Hello Worldと表示されます

   val helloWorld:TextView = findViewById(R.id.greeting) // 1
   helloWorld.text =Hello World// 2

ここでは

  1. findViewById(R.id.greeting)でxml内のandroid:idid/greetingで定義されているTextViewを取得
  2. TextViewのtextの要素にHello Worldの文字列を設定

を行っています。

このように、プログラム側からレイアウト内の要素を書き換えることにより同じレイアウト定義でユーザー名、アイコンのようなユーザー毎に異なるものを表示することができます。

AndroidManifest内でActivityの宣言をする

AndroidManifest.xml内のActivityの記述の例

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    package="tokyo.punchdrunker.hocho">
    <!--  ↑のpackageでこのアプリケーションのパッケージを宣言するManifest内でのクラスパスを相対パスで扱う場合このパッケージからの相対パスになる -->

    <application
        android:name=".HochoApplication"
        android:allowBackup="false"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:roundIcon="@mipmap/ic_launcher_round"
        android:supportsRtl="true"
        android:theme="@style/AppTheme"
        tools:ignore="GoogleAppIndexingWarning">
        <!-- nameにActivityのクラスのパスを指定する 絶対パスまたはmanifestタグのpackage属性のパッケージからの相対パスで記述 -->
        <activity android:name=".MainActivity"
            android:theme="@style/AppTheme">
            <!-- アプリケーション起動時に開く画面はこのintent-filter設定を書く -->
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
        <!-- 外部からのintentを受け取らないActivityはintent-filterを書かなくても良い -->
        <activity android:name=".SettingsActivity"
            android:theme="@style/AppTheme"
            android:parentActivityName=".MainActivity">
            <meta-data android:name="android.support.PARENT_ACTIVITY"
                android:value="tokyo.punchdrunker.hocho.MainActivity" />
        </activity>
    </application>
</manifest>

NextStep

参考になりそうなセッション

Clone this wiki locally