Android 如何配置特定片段';当方向改变时,什么是方向?

Android 如何配置特定片段';当方向改变时,什么是方向?,android,orientation,android-fragments,Android,Orientation,Android Fragments,我在MainActivity中有多个片段,我只想在DetailFragment public class DetailFragment extends Fragment{ @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { WindowMan

我在
MainActivity
中有多个片段,我只想在
DetailFragment

public class DetailFragment extends Fragment{
        @Override
        public View onCreateView(LayoutInflater inflater, ViewGroup container,
                Bundle savedInstanceState) {

            WindowManager wm = getActivity().getWindowManager();

            Display d = wm.getDefaultDisplay();
            if(d.getWidth() > d.getHeight()){
                mDetailView = inflater.inflate(R.layout.detail, container, false);
            }else{
                mDetailView = inflater.inflate(R.layout.detail_port, container, false);
            }
            gridView = (GridView)mDetailView.findViewById(R.id.grid);
        return mDetailView;
        }
}
@Override
public void onConfigurationChanged(Configuration newConfig) {
    super.onConfigurationChanged(newConfig);

    updateDetial(topic_index, args.getString("group_id"), args.getString("group_name"));
}

public void updateDetial(int subTopicPosition,String groupID, String groupName){
    FragmentManager fragmentManager = getFragmentManager();
    FragmentTransaction ft = fragmentManager.beginTransaction();
    DetailFragment detailView = (DetailFragment)getFragmentManager()
                                .findFragmentById(R.id.detailFrame);
    DetailFragment detailFrag = new DetailFragment(topic_index, subTopicPosition, groupID, groupName);

    if(detailView==null){

        ft.add(R.id.detailFrame, detailFrag);
        ft.commit();
    }else{
        ft.replace(R.id.detailFrame, detailFrag);
        ft.commit();
    }
}
因此,我必须覆盖
SubTopicFragment
中的
onConfigurationChanged
,下面是
SubTopicFragment extend list fragment

public class DetailFragment extends Fragment{
        @Override
        public View onCreateView(LayoutInflater inflater, ViewGroup container,
                Bundle savedInstanceState) {

            WindowManager wm = getActivity().getWindowManager();

            Display d = wm.getDefaultDisplay();
            if(d.getWidth() > d.getHeight()){
                mDetailView = inflater.inflate(R.layout.detail, container, false);
            }else{
                mDetailView = inflater.inflate(R.layout.detail_port, container, false);
            }
            gridView = (GridView)mDetailView.findViewById(R.id.grid);
        return mDetailView;
        }
}
@Override
public void onConfigurationChanged(Configuration newConfig) {
    super.onConfigurationChanged(newConfig);

    updateDetial(topic_index, args.getString("group_id"), args.getString("group_name"));
}

public void updateDetial(int subTopicPosition,String groupID, String groupName){
    FragmentManager fragmentManager = getFragmentManager();
    FragmentTransaction ft = fragmentManager.beginTransaction();
    DetailFragment detailView = (DetailFragment)getFragmentManager()
                                .findFragmentById(R.id.detailFrame);
    DetailFragment detailFrag = new DetailFragment(topic_index, subTopicPosition, groupID, groupName);

    if(detailView==null){

        ft.add(R.id.detailFrame, detailFrag);
        ft.commit();
    }else{
        ft.replace(R.id.detailFrame, detailFrag);
        ft.commit();
    }
}
它工作得很好。但是当我移动到另一个活动,改变方向并按下后退按钮时,就会出现问题,这会导致强制关闭我如何解决这个问题

06-13 10:15:54.758: E/AndroidRuntime(1050): FATAL EXCEPTION: main
06-13 10:15:54.758: E/AndroidRuntime(1050): java.lang.IllegalStateException: Can not perform this action after onSaveInstanceState
06-13 10:15:54.758: E/AndroidRuntime(1050):     at android.app.FragmentManagerImpl.checkStateLoss(FragmentManager.java:1192)
06-13 10:15:54.758: E/AndroidRuntime(1050):     at android.app.FragmentManagerImpl.enqueueAction(FragmentManager.java:1203)
06-13 10:15:54.758: E/AndroidRuntime(1050):     at android.app.BackStackRecord.commitInternal(BackStackRecord.java:557)
06-13 10:15:54.758: E/AndroidRuntime(1050):     at android.app.BackStackRecord.commit(BackStackRecord.java:541)
06-13 10:15:54.758: E/AndroidRuntime(1050):     at com.april.android.SubTopicFragment.updateDetial(SubTopicFragment.java:120)
06-13 10:15:54.758: E/AndroidRuntime(1050):     at com.april.android.SubTopicFragment.onConfigurationChanged(SubTopicFragment.java:259)
06-13 10:15:54.758: E/AndroidRuntime(1050):     at android.app.FragmentManagerImpl.dispatchConfigurationChanged(FragmentManager.java:1706)
06-13 10:15:54.758: E/AndroidRuntime(1050):     at android.app.Activity.onConfigurationChanged(Activity.java:1402)
06-13 10:15:54.758: E/AndroidRuntime(1050):     at android.app.ActivityThread.performConfigurationChanged(ActivityThread.java:3298)
06-13 10:15:54.758: E/AndroidRuntime(1050):     at android.app.ActivityThread.handleActivityConfigurationChanged(ActivityThread.java:3427)
06-13 10:15:54.758: E/AndroidRuntime(1050):     at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1113)
06-13 10:15:54.758: E/AndroidRuntime(1050):     at android.os.Handler.dispatchMessage(Handler.java:99)
06-13 10:15:54.758: E/AndroidRuntime(1050):     at android.os.Looper.loop(Looper.java:132)
06-13 10:15:54.758: E/AndroidRuntime(1050):     at android.app.ActivityThread.main(ActivityThread.java:4123)
06-13 10:15:54.758: E/AndroidRuntime(1050):     at java.lang.reflect.Method.invokeNative(Native Method)
06-13 10:15:54.758: E/AndroidRuntime(1050):     at java.lang.reflect.Method.invoke(Method.java:491)
06-13 10:15:54.758: E/AndroidRuntime(1050):     at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:841)
06-13 10:15:54.758: E/AndroidRuntime(1050):     at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:599)
06-13 10:15:54.758: E/AndroidRuntime(1050):     at dalvik.system.NativeStart.main(Native Method)

您不应该在onCreateView中加载两个不同的布局id

为两个布局使用一个布局Id

你能做的就是

布局文件夹中的R.layout.detail

R.layout.detail_端口将其重命名为R.layout.detail并将其放置在res的layout端口文件夹中

然后充气。充气(右布局图、详图、容器、假);将根据方向自动给出特定布局


阅读此文档

几乎所有关于代码的内容都是错误的

        Display d = wm.getDefaultDisplay();
        if(d.getWidth() > d.getHeight()){
            mDetailView = inflater.inflate(R.layout.detail, container, false);
        }else{
            mDetailView = inflater.inflate(R.layout.detail_port, container, false);
        }
        gridView = (GridView)mDetailView.findViewById(R.id.grid);
不要这样做-平台有自己的方式使用命名约定加载布局。您的代码应该如下所示:

    mDetailView = inflater.inflate(R.layout.detail, container, false);
    gridView = (GridView)mDetailView.findViewById(R.id.grid);
如果您希望它在不同方向上看起来不同,请在
布局端口
布局区域
中放置两个detail.xml文件,操作系统将加载正确的文件(并处理可能是您的问题的所有资源ID的重复数据)。此外:

您已获得对当前片段的访问权限。然后创建一个全新的片段。然后在添加新片段之前检查第一个片段是否为空。add()和.replace()是不同的,因为add()特别不删除以前的片段-replace()不会抛出错误,但是如果没有要删除的以前的片段,那么每次都可以使用它

    ft.replace(R.id.detailFrame, new DetailFragment(topic_index, subTopicPosition, groupID, groupName);
    ft.commit();

线索在“onSaveInstanceState之后无法执行此操作”中,但我们需要更多的堆栈跟踪行来查看实际发生的情况。它与执行操作的顺序有关,例如在旋转过程中关闭片段,以及之后,代码的另一部分调用片段中的方法。我根据您的建议更改代码。我忘了做这件事是件好事。无论如何,我尝试旋转设备,网格细节仍然使用它第一次开始的初始值,我需要选择另一个主题,以便它将替换与is方向相对应的新网格。你有什么想法,如何让细节的视图在方向改变后立即更新它的视图?