Android Fragment中SeekBar监听器应在哪个生命周期方法中添加?
解决Fragment中SeekBar监听器绑定的问题
嗨,作为Android新手遇到这个问题很正常,我来帮你搞定!你需要把SeekBar的监听器代码放在Fragment的onViewCreated()方法里,这才是绑定控件和监听器的正确时机。
为什么选onViewCreated()?
onCreateView()只是负责加载并返回Fragment的布局,此时布局里的控件还没有完全完成初始化,直接在这里获取控件可能会得到空指针;onViewCreated()会在onCreateView()执行完成、Fragment的视图完全创建好之后调用,这时候可以安全地通过根视图找到所有控件,并设置监听器。
修正后的完整SecondFragment代码
我帮你把代码修正并整合好了,注意几个关键点:
- 从Fragment的根视图
view中获取控件(你原来的seekBar.findViewById(R.id.seekBar)写法是错误的,控件本身不能用来查找自己); - 你的SeekBar最大进度是24(布局里设置了
android:max="24"),所以文本要对应改成progress+"/24",避免显示不一致; - 把监听器代码放在
onViewCreated()里:
package com.example.myapplication; import android.graphics.Color; import android.graphics.PorterDuff; import android.os.Bundle; import androidx.annotation.NonNull; import androidx.annotation.Nullable; import androidx.fragment.app.Fragment; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.SeekBar; import android.widget.TextView; /** * A simple {@link Fragment} subclass. * Use the {@link SecondFragment#newInstance} factory method to * create an instance of this fragment. */ public class SecondFragment extends Fragment { SeekBar seekBar; TextView textView; // TODO: Rename parameter arguments, choose names that match // the fragment initialization parameters, e.g. ARG_ITEM_NUMBER private static final String ARG_PARAM1 = "param1"; private static final String ARG_PARAM2 = "param2"; // TODO: Rename and change types of parameters private String mParam1; private String mParam2; public SecondFragment() { // Required empty public constructor } /** * Use this factory method to create a new instance of * this fragment using the provided parameters. * * @param param1 Parameter 1. * @param param2 Parameter 2. * @return A new instance of fragment SecondFragment. */ // TODO: Rename and change types and number of parameters public static SecondFragment newInstance(String param1, String param2) { SecondFragment fragment = new SecondFragment(); Bundle args = new Bundle(); args.putString(ARG_PARAM1, param1); args.putString(ARG_PARAM2, param2); fragment.setArguments(args); return fragment; } @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); if (getArguments() != null) { mParam1 = getArguments().getString(ARG_PARAM1); mParam2 = getArguments().getString(ARG_PARAM2); } } @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { // Inflate the layout for this fragment return inflater.inflate(R.layout.fragment_second, container, false); } @Override public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) { super.onViewCreated(view, savedInstanceState); // 从根视图中获取控件实例 seekBar = view.findViewById(R.id.seekBar); textView = view.findViewById(R.id.textView3); // 设置SeekBar监听器 seekBar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() { @Override public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) { // 匹配SeekBar的max值,显示正确的进度文本 textView.setText(progress + "/24"); } @Override public void onStartTrackingTouch(SeekBar seekBar) {} @Override public void onStopTrackingTouch(SeekBar seekBar) {} }); } }
额外提示
- 如果你担心Fragment重建时进度丢失,可以在
onSaveInstanceState()里保存当前进度,在onViewCreated()里恢复; - 确保你的布局文件
fragment_second.xml里的控件ID和代码中的完全对应,避免因ID不匹配导致的空指针。
内容的提问来源于stack exchange,提问作者Arian P
相关产品推荐
相关产品推荐

