【问题标题】:Force close on orientation change with ViewPager/Fragments/ViewPagerExtensions使用 ViewPager/Fragments/ViewPagerExtensions 强制关闭方向更改
【发布时间】:2013-01-23 22:00:06
【问题描述】:

我遇到了一个我似乎无法解决的问题(我以前没有以这种方式处理过片段)

我有一个主要的 FragmentActivity 如下:

package com.my.app;

import android.app.AlertDialog;
import android.content.DialogInterface; 
import android.os.Bundle;
import android.support.v4.app.FragmentActivity;
import android.support.v4.view.ViewPager;

import com.astuetz.viewpager.extensions.ScrollingTabsView;
import com.astuetz.viewpager.extensions.TabsAdapter;

public class MyTabsActivity extends FragmentActivity {

private ViewPager mPager;
private ScrollingTabsView mScrollingTabs;

private TabsAdapter mScrollingTabsAdapter;

@Override
public void onCreate(Bundle savedInstanceState) {

    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_my_tabs);

    mPager = (ViewPager) findViewById(R.id.pager);
    mScrollingTabs = (ScrollingTabsView) findViewById(R.id.my_tabs);
    mScrollingTabsAdapter = new MyTabsAdapter(this, mPager);
    addTabs();
    mScrollingTabs.setAdapter(mScrollingTabsAdapter);
    mScrollingTabs.setViewPager(mPager);
    mPager.setCurrentItem(1);
    mPager.setPageMargin(1);
}

private void addTabs() {
    mScrollingTabsAdapter.addTab("FirstFragment", "First");
    mScrollingTabsAdapter.addTab("SecondFragment", "Second");
}
}

XML如下(带有Viewpager和ScrollingTabsView:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res/com.my.package"
android:layout_width="fill_parent"
android:layout_height="fill_parent" >

<com.astuetz.viewpager.extensions.ScrollingTabsView
    android:id="@+id/ztc_tabs"
    android:layout_width="fill_parent"
    android:layout_height="wrap_content"
    android:background="@drawable/tab_unselected_holo"
    app:dividerDrawable="@drawable/divider"/>

<android.support.v4.view.ViewPager
    android:id="@+id/pager"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:layout_below="@+id/ztc_tabs" />

</RelativeLayout>

然后在 MyTabsAdapter 我有这个:

package com.my.app;

import com.my.app.R;

import java.util.ArrayList;

import android.app.Activity;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentActivity;
import android.support.v4.app.FragmentPagerAdapter;
import android.support.v4.view.ViewPager;
import android.view.LayoutInflater;
import android.view.View;
import android.widget.Button;

import com.astuetz.viewpager.extensions.TabsAdapter;

public class MyTabsAdapter extends FragmentPagerAdapter implements TabsAdapter {
private final ArrayList<TabInfo> mTabs = new ArrayList<TabInfo>();
private final ViewPager mPager;

private Activity mContext;

static final class TabInfo {
    private final String fragName;
    private final String title;

    TabInfo(String fragName, String title) {
        this.fragName = fragName;
        this.title = title;
    }
}

public MyTabsAdapter(FragmentActivity ctx, ViewPager pager) {
    super(ctx.getSupportFragmentManager());
    this.mContext = ctx;
    this.mPager = pager;
    this.mPager.setAdapter(this);
}

public View getView(int position) {
    Button tab;

    LayoutInflater inflater = mContext.getLayoutInflater();
    tab = (Button) inflater.inflate(R.layout.tab_scrolling, null);

    tab.setText(this.mTabs.get(position).title.toUpperCase());

    return tab;
}

public void addTab(String fragName, String title) {
    TabInfo info = new TabInfo(fragName, title);
    mTabs.add(info);
}

@Override
public Fragment getItem(int position) {
    TabInfo info = mTabs.get(position);
    if (info.fragName == "FirstFragment") {
        return FirstFragment.newInstance();
    } else if (info.fragName == "SecondFragment") {
        return SecondFragment.newInstance(t);
    }
    return null;
}

@Override
public int getCount() {
    return mTabs.size();
}

}

和 FirstFragment/SecondFragment 有自己的基本布局并且几乎相同,这里是 Fragment

package com.my.app;

import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;

public class FirstFragment extends Fragment {

public static Fragment newInstance() {
    FirstFragment frag = new FirstFragment();;
    return frag;
}

@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setRetainInstance(true);
}

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
                    Bundle savedInstanceState) {
    if (container == null)
        return null;
    return inflater.inflate(R.layout.fragment_first, container, false);
}

}

这里的一切都完全按照我的意愿工作。选项卡工作正常,ViewPager 页面正常,等等。

问题是,当我改变方向时,我得到了这个痕迹并强制关闭,但我不确定为什么。

E/AndroidRuntime(32431): FATAL EXCEPTION: main
E/AndroidRuntime(32431): java.lang.NullPointerException
E/AndroidRuntime(32431):    at android.support.v4.app.FragmentManagerImpl.saveFragmentBasicState(FragmentManager.java:1576)
E/AndroidRuntime(32431):    at android.support.v4.app.FragmentManagerImpl.saveAllState(FragmentManager.java:1617)
E/AndroidRuntime(32431):    at android.support.v4.app.FragmentActivity.onSaveInstanceState(FragmentActivity.java:481)
E/AndroidRuntime(32431):    at android.app.Activity.performSaveInstanceState(Activity.java:1147)
E/AndroidRuntime(32431):    at android.app.Instrumentation.callActivityOnSaveInstanceState(Instrumentation.java:1216)
E/AndroidRuntime(32431):    at android.app.ActivityThread.handleRelaunchActivity(ActivityThread.java:3666)
E/AndroidRuntime(32431):    at android.app.ActivityThread.access$700(ActivityThread.java:141)
E/AndroidRuntime(32431):    at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1240)
E/AndroidRuntime(32431):    at android.os.Handler.dispatchMessage(Handler.java:99)
E/AndroidRuntime(32431):    at android.os.Looper.loop(Looper.java:137)
E/AndroidRuntime(32431):    at android.app.ActivityThread.main(ActivityThread.java:5039)
E/AndroidRuntime(32431):    at java.lang.reflect.Method.invokeNative(Native Method)
E/AndroidRuntime(32431):    at java.lang.reflect.Method.invoke(Method.java:511)
E/AndroidRuntime(32431):    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:793)
E/AndroidRuntime(32431):    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:560)
E/AndroidRuntime(32431):    at dalvik.system.NativeStart.main(Native Method)
W/ActivityManager(  418):   Force finishing activity com.ada.ztc/.ZTCTabs

所以我需要帮助的是弄清楚为什么我会在方向更改时收到该错误。我做了一些研究,似乎没有找到任何具有类似设置的人。

任何帮助将不胜感激,如果需要,我很乐意提供更多信息。

【问题讨论】:

    标签: android android-viewpager fragment fragmentpageradapter


    【解决方案1】:
    @Override
            public void onSaveInstanceState(Bundle outState) {
                outState.putString("BUGFIX", "BUGFIX");
                super.onSaveInstanceState(outState);
            }
    

    试试这个。捆绑永远不会为空

    【讨论】:

    【解决方案2】:

    我似乎已经通过添加解决了这个问题

    android:configChanges="orientation|screenSize"
    

    在 FragmentActivity 的清单中

    【讨论】:

    • 这不能解决问题;这消除了触发问题的一种方式。当用户出于任何原因离开应用程序时,系统仍然可以终止该活动,并且您将遇到同样的崩溃(尝试打开开发人员设置中的“终止活动”选项以了解我的意思)。你仍然应该找出并解决根本问题,而不是绕开它,否则它会在以后咬你。
    • 当心 android:configChanges="orientation|screenSize" 这不会在屏幕更改后更新您的布局。有时我需要不同的局域网/端口布局,这不会自动改变它。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2013-02-14
    • 2015-05-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-12-03
    相关资源
    最近更新 更多