• 片段与活动的交互


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

    
    <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>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18

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

    二、Workout类
    我们将训练项目数据保存在一个名为Workout.java的文件,这是一个纯java类,应用将从这个文件获得训练项目数据。这个类定义了一个包含4个训练项目的数组,每个训练项目包括一个名字和一个描述。
    在com.hfad.workout中新建一个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;
        }
    }
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34

    三、向片段传递训练项目ID
    通过ID来标识唯一的一个项目,所以修改WorkoutDetailFragment如下:

    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;
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25

    四、使用片段管理器管理片段
    在活动与片段交互之前,活动首先需要得到这个片段的一个引用。可以使用活动的片段管理器来得到活动片段的引用。片段管理器用于跟踪和处理活动使用的所有片段。
    要得到片段管理器的一个引用,可以使用getFragmentManager()和getSupportFragmentManager()。后者会得到处理支持库片段的片段管理器的一个引用,前者得到处理其他片段的片段管理器的引用,这些片段使用原生的Android片段类。然后可以使用片段管理器的fingFragmentById方法得到片段的一个引用。
    其使用方法如下:

    getSupportFragmentManager().findFragmentById()
    
    • 1

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

    
    <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>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8

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

    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);
        };
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15

    五、片段生命周期
    片段的生命周期和活动的生命周期很类似,不过片段生命周期中还有另外几个步骤。这是因为他需要包含这个片段的活动的生命周期交互。
    在安卓开发中,片段(Fragment)的生命周期主要包含以下几种方法:

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

    另外的,Fragment类是继承自java.lang.Object类的,并不扩展Activity类,这表明活动可用的一些方法在片段中无法使用。
    需要说明的是:Fragment没有实现context类。与活动不同,片段并不是一个上下文类型,不能直接访问有关应用环境的全局信息。实际上,片段必须使用其他对象的上下文来访问这个信息,如它的父活动。

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

    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;
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39

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

  • 相关阅读:
    【ES专题】Logstash与FileBeat详解以及ELK整合详解
    深度神经网络压缩与加速技术
    linux下sqlplus登录oracle显示问号处理办法
    【英语:基础高阶_全场景覆盖表达】K8.口语主题陈述——自然与环境类
    【Spring】Spring事务失效原因及解决方法
    Redis入门完整教程:复制配置
    基于机器学习和OpenCV的激光雷达数据分割和分类
    Python之杨辉三角
    独立产品灵感周刊 DecoHack #040 - Google公布2022年度最佳应用榜单
    CUDA 从入门到放弃(一)
  • 原文地址:https://blog.csdn.net/weixin_44014982/article/details/132613081