在一个PreferenceFragment,Android的onViewCreated中findViewById失败

问题描述 投票:2回答:2

我有两个片段: - 扩展片段的HomeFragment - 扩展PreferenceFragment的SettingsFragment

每个都包含一个TextView,我希望在Java代码中访问和修改其内容。我通过调用onViewCreated然后在findViewById上使用setTextTextView中进行此修改。 这适用于HomeFragment,但它不适用于SettingsFragment。 有关信息,TextViewSettingsFragment在与Preference相关联的布局中定义。奇怪的是,似乎PreferenceFragment类型的视图层次结构在onViewCreated中还没有完全准备好!为了更进一步,我尝试将修改TextView的代码放一些延迟(使用postDelay),这样就可以了!

下面,我将测试我刚刚提出的问题所需的所有代码。

main activity.Java

public class MainActivity extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        final HomeFragment homeFragment = new HomeFragment();
        final SettingsFragment settingsFragment = new SettingsFragment();

        getFragmentManager().beginTransaction()
                .add(R.id.fragmentContainer, homeFragment).commit();

        // Just a simple button to switch between the two fragments
        Button button = findViewById(R.id.activityButton);
        button.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                if(homeFragment.isAdded()) {
                    getFragmentManager().beginTransaction()
                            .replace(R.id.fragmentContainer, settingsFragment).commit();
                } else {
                    getFragmentManager().beginTransaction()
                            .replace(R.id.fragmentContainer, homeFragment).commit();
                }
            }
        });
    }
}

home fragment.Java

public class HomeFragment extends Fragment {

    public HomeFragment() {
        // Required empty public constructor
    }

    @Override
    public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {
        // Inflate the layout for this fragment
        return inflater.inflate(R.layout.fragment_home, container, false);
    }

    @Override
    public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) {
        super.onViewCreated(view, savedInstanceState);

        TextView textView = view.findViewById(R.id.homeText);
        if(textView != null) {
            textView.setText("Home fragment text (modified)");
        }
    }
}

settings fragment.Java

public class SettingsFragment extends PreferenceFragment {


    public SettingsFragment() {
        // Required empty public constructor
    }

    @Override
    public void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        addPreferencesFromResource(R.xml.fragment_settings);
    }

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {
        return super.onCreateView(inflater, container, savedInstanceState);
    }

    @Override
    public void onViewCreated(final View view, @Nullable Bundle savedInstanceState) {
        super.onViewCreated(view, savedInstanceState);

        // ---- BLOCK 1 -----
        TextView textView = view.findViewById(R.id.settingsText);
        if (textView != null) {
            textView.setText("Preference 1 (modified)");
        }

        // ---- BLOCK 2 -----
//        view.post(new Runnable() {
//            @Override
//            public void run() {
//                TextView textView = view.findViewById(R.id.settingsText);
//                if (textView != null) {
//                    textView.setText("Preference 1 (modified)");
//                }
//            }
//        });

        // ---- BLOCK 3 -----
//        view.postDelayed(new Runnable() {
//            @Override
//            public void run() {
//                TextView textView = view.findViewById(R.id.settingsText);
//                if (textView != null) {
//                    textView.setText("Preference 1 (modified)");
//                }
//            }
//        }, 100);
    }
}

activity_main.xml中

<?xml version="1.0" encoding="utf-8"?>
<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context=".MainActivity">

    <TextView
        android:id="@+id/activityText"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        app:layout_constraintLeft_toLeftOf="parent"
        app:layout_constraintRight_toRightOf="parent"
        app:layout_constraintTop_toTopOf="parent"
        android:gravity="center_horizontal"
        android:text="MainActivity" />

    <Button
        android:id="@+id/activityButton"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        app:layout_constraintLeft_toLeftOf="parent"
        app:layout_constraintRight_toRightOf="parent"
        app:layout_constraintTop_toBottomOf="@id/activityText"
        android:text="Change fragment"/>

    <FrameLayout
        android:id="@+id/fragmentContainer"
        android:layout_width="match_parent"
        android:layout_height="0dp"
        app:layout_constraintTop_toBottomOf="@id/activityButton"
        app:layout_constraintBottom_toBottomOf="parent">

    </FrameLayout>

</android.support.constraint.ConstraintLayout>

fragment_home.xml

<?xml version="1.0" encoding="utf-8"?>
<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    tools:context=".HomeFragment">

    <TextView
        android:id="@+id/homeText"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        app:layout_constraintLeft_toLeftOf="parent"
        app:layout_constraintRight_toRightOf="parent"
        app:layout_constraintTop_toTopOf="parent"
        app:layout_constraintBottom_toBottomOf="parent"
        android:text="Home fragment text" />

</android.support.constraint.ConstraintLayout>

fragment_settings.xml

<?xml version="1.0" encoding="utf-8"?>
<PreferenceScreen xmlns:android="http://schemas.android.com/apk/res/android">
    <PreferenceCategory
        android:layout="@layout/preference_layout_category">

        <Preference
            android:enabled="true"
            android:layout="@layout/preference_layout" />

    </PreferenceCategory>
</PreferenceScreen>

preference_layout.xml

<?xml version="1.0" encoding="utf-8"?>
<android.support.constraint.ConstraintLayout
    xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent"
    android:layout_height="match_parent"
    xmlns:app="http://schemas.android.com/apk/res-auto">

    <TextView
        android:id="@+id/settingsText"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        app:layout_constraintLeft_toLeftOf="parent"
        app:layout_constraintRight_toRightOf="parent"
        app:layout_constraintTop_toTopOf="parent"
        android:textAllCaps="true"
        android:text="Preference 1"/>

</android.support.constraint.ConstraintLayout>

preference_layout_category.xml

<?xml version="1.0" encoding="utf-8"?>
<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    xmlns:app="http://schemas.android.com/apk/res-auto">

    <TextView
        android:id="@+id/settingsTextContainer"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        app:layout_constraintLeft_toLeftOf="parent"
        app:layout_constraintRight_toRightOf="parent"
        app:layout_constraintTop_toTopOf="parent"
        android:textAllCaps="true"
        android:background="@android:color/background_dark"
        android:textColor="@android:color/background_light"
        android:text="Category 1"/>

</android.support.constraint.ConstraintLayout>
android android-fragments fragment preference preferencefragment
2个回答
1
投票

前几天我有类似的东西。在片段的onCreateView上使用findViewById()而不是onViewCreated方法。祝好运。


0
投票

在onCreateView()中绑定您的视图,就像这样

View view= inflater.inflate(R.layout.your_fragment, container, false);
TextView textView = view.findViewById(R.id.settingsText);
return view;
© www.soinside.com 2019 - 2024. All rights reserved.