片段与活动的交互

一、让片段与活动交互

修改片段显示一个项目的详细信息而不是目前的占位文本。更新fragment_workout_detail.xml:

xml 复制代码
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:textAppearance="?android:attr/textAppearanceLarge"
        android:id="@+id/textTitle" />

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

</LinearLayout>

相比之前的,删掉了两个android:text。

二、Workout类

我们将训练项目数据保存在一个名为Workout.java的文件,这是一个纯java类,应用将从这个文件获得训练项目数据。这个类定义了一个包含4个训练项目的数组,每个训练项目包括一个名字和一个描述。

在com.hfad.workout中新建一个java类即可。

java 复制代码
public class Workout {
    private String name;
    private String description;

    public static final Workout[] workouts = {
            new Workout("The Limb Loosener",
                    "5 Handstand push-ups\n10 1-legged squats\n15 Pull-ups"),
            new Workout("Core Agony",
                    "100 Pull-ups\n100 Push-ups\n100 Sit-ups\n100 Squats"),
            new Workout("The Wimp Special",
                    "5 Pull-ups\n10 Push-ups\n15 Squats"),
            new Workout("Strength and Length",
                    "500 meter run\n21 x 1.5 pood kettleball swing\n21 x pull-ups")
    };

    //Each Workout has a name and description
    private Workout(String name, String description) {
        this.name = name;
        this.description = description;
    }

    public String getDescription() {
        return description;
    }

    public String getName() {
        return name;
    }

    public String toString() {
        return this.name;
    }
}

三、向片段传递训练项目ID

通过ID来标识唯一的一个项目,所以修改WorkoutDetailFragment如下:

java 复制代码
package com.hfad.workout;

import android.os.Bundle;
import androidx.fragment.app.Fragment;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;

public class WorkoutDetailFragment extends Fragment {

    //用来表示用户选择的训练项目的ID
    private long workoutId;

    @Override
    //Android需要这个片段的布局时会调用这个方法
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {
        // 这会告诉Android这个片段使用哪个布局
        return inflater.inflate(R.layout.fragment_workout_detail, container, false);
    }

    public void setWorkoutId(long id) {
        this.workoutId = id;
    }
}

四、使用片段管理器管理片段

在活动与片段交互之前,活动首先需要得到这个片段的一个引用。可以使用活动的片段管理器来得到活动片段的引用。片段管理器用于跟踪和处理活动使用的所有片段。

要得到片段管理器的一个引用,可以使用getFragmentManager()和getSupportFragmentManager()。后者会得到处理支持库片段的片段管理器的一个引用,前者得到处理其他片段的片段管理器的引用,这些片段使用原生的Android片段类。然后可以使用片段管理器的fingFragmentById方法得到片段的一个引用。

其使用方法如下:

java 复制代码
getSupportFragmentManager().findFragmentById()

首先、在activity_detail.xml中为片段增加一个ID。

xml 复制代码
<?xml version="1.0" encoding="utf-8"?>
<fragment xmlns:android="http://schemas.android.com/apk/res/android"
    android:name="com.hfad.workout.WorkoutDetailFragment"
    android:id="@+id/detail_frag"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

</fragment>

然后在DetailActivity.java中设置训练项目ID。

java 复制代码
package com.hfad.workout;

import androidx.appcompat.app.AppCompatActivity;
import android.os.Bundle;

public class DetailActivity extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_detail);
        WorkoutDetailFragment frag = (WorkoutDetailFragment)getSupportFragmentManager().findFragmentById(R.id.detail_frag);
        frag.setWorkoutId(1);
    };
}

五、片段生命周期

片段的生命周期和活动的生命周期很类似,不过片段生命周期中还有另外几个步骤。这是因为他需要包含这个片段的活动的生命周期交互。

在安卓开发中,片段(Fragment)的生命周期主要包含以下几种方法:

onAttach():片段被附加到活动时调用。
onCreate():在创建片段时调用,可以在这里进行初始化的操作。
onCreateView():用于创建并返回该片段的视图。
onActivityCreated():在活动创建片段之后调用。
onStart():当片段可见时调用。
onResume():当片段恢复到前台并可以与用户交互时调用。
onPause():当片段暂停并且用户交互停止时调用。
onStop():当片段不可见时调用。
onDestroyView():在销毁片段之前调用,可以在这里释放视图资源。
onDestroy():在销毁片段时调用,可以在这里进行清理操作。
onDetach():片段从活动中分离时调用。

另外的,Fragment类是继承自java.lang.Object类的,并不扩展Activity类,这表明活动可用的一些方法在片段中无法使用。

需要说明的是:Fragment没有实现context类。与活动不同,片段并不是一个上下文类型,不能直接访问有关应用环境的全局信息。实际上,片段必须使用其他对象的上下文来访问这个信息,如它的父活动。

六、在onStart方法中设置视图的值

要在活动可见时完成片段视图的更新,所以要使用片段的onStart方法。更新WorkoutDetailFragment代码如下:

java 复制代码
package com.hfad.workout;

import android.os.Bundle;
import androidx.fragment.app.Fragment;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.TextView;

public class WorkoutDetailFragment extends Fragment {

    //用来表示用户选择的训练项目的ID
    private long workoutId;

    @Override
    //Android需要这个片段的布局时会调用这个方法
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {
        // 这会告诉Android这个片段使用哪个布局
        return inflater.inflate(R.layout.fragment_workout_detail, container, false);
    }

    public void onStart() {
        super.onStart();
        //得到片段的根视图,然后使用这个根视图得到两个文本视图的引用
        View view = getView();
        if (view != null) {
            TextView title = (TextView) view.findViewById(R.id.textTitle);
            Workout workout = Workout.workouts[(int)workoutId];
            title.setText(workout.getName());
            TextView description = (TextView) view.findViewById(R.id.textDescription);
            description.setText(workout.getDescription());
        }
    }

    public void setWorkoutId(long id) {
        this.workoutId = id;
    }
}

由于片段于活动不同,因此片段没有包含活动的所有方法,片段没有findViewById方法,要得到片段中视图的引用,首先必须使用geyView方法得到片段根视图的引用,然后使用根视图查找它的子视图。

现在可以运行一下应用。

相关推荐
小蜜蜂嗡嗡28 分钟前
Android Studio flutter项目运行、打包时间太长
android·flutter·android studio
aqi0034 分钟前
FFmpeg开发笔记(七十一)使用国产的QPlayer2实现双播放器观看视频
android·ffmpeg·音视频·流媒体
zhangphil2 小时前
Android理解onTrimMemory中ComponentCallbacks2的内存警戒水位线值
android
你过来啊你2 小时前
Android View的绘制原理详解
android
移动开发者1号5 小时前
使用 Android App Bundle 极致压缩应用体积
android·kotlin
移动开发者1号5 小时前
构建高可用线上性能监控体系:从原理到实战
android·kotlin
ii_best10 小时前
按键精灵支持安卓14、15系统,兼容64位环境开发辅助工具
android
美狐美颜sdk10 小时前
跨平台直播美颜SDK集成实录:Android/iOS如何适配贴纸功能
android·人工智能·ios·架构·音视频·美颜sdk·第三方美颜sdk
恋猫de小郭15 小时前
Meta 宣布加入 Kotlin 基金会,将为 Kotlin 和 Android 生态提供全新支持
android·开发语言·ios·kotlin
aqi0016 小时前
FFmpeg开发笔记(七十七)Android的开源音视频剪辑框架RxFFmpeg
android·ffmpeg·音视频·流媒体