在使用ViewPager时尝试从其父活动修改片段时出现空指针异常

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了在使用ViewPager时尝试从其父活动修改片段时出现空指针异常相关的知识,希望对你有一定的参考价值。

我在手机和平​​板电脑上做了一个不同布局的应用程序。对于手机,我有ViewPager with Fragments和平板电脑,我在.xml布局文件中有片段。当我尝试获取特定片段并使用该片段中的活动方法时,我得到Null Pointer Exception。 我该如何解决?当我使用ViewPager在手机上运行应用程序时,我得到Null Pointer但是当我的平板电脑包含.xml布局的片段时,它是可以的。

MainActivity中的方法:

  private ViewPager viewPager;
    private PagerAdapter adapter;
    private TabLayout tableLayout;

    private void setViewPager(){
            viewPager = findViewById(R.id.viewpager);
            adapter = new PagerAdapter(getSupportFragmentManager(), 2);
            adapter.addFragment(new SunFragment(), "Sun");
            adapter.addFragment(new MoonFragment(), "Moon");

            tableLayout = findViewById(R.id.tabLayout);

            if(viewPager != null) {
                viewPager.setAdapter(adapter);
            }
            if(tableLayout != null){
                tableLayout.setupWithViewPager(viewPager);
            }


        }

        private void refreshView(){
            if(viewPager != null) {
                adapter.getSunFragment().calculateWeather();
                adapter.getMoonFragment().calculateWeather();
            }else if(sunFragment != null){
                sunFragment.calculateWeather();
                moonFragment.calculateWeather();
            }

        }

当我尝试从activity使用方法并获得double值时,使用Null指针部分片段:

 public void calculateWeather(){
        longitude = ((MainActivity)getActivity()).getLon();
        latitude = ((MainActivity)getActivity()).getLat();

    }

Viewpager适配器:

public class PagerAdapter extends FragmentStatePagerAdapter {

    private int fragmentNumber;
    private List<Fragment> fragmentList = new ArrayList<>();
    private List<String> fragmentsNameList = new ArrayList<>();


    public PagerAdapter(FragmentManager fm, int fragmentNumber){
        super(fm);
        this.fragmentNumber = fragmentNumber;
    }

    public void addFragment(Fragment fragment, String name){
        fragmentList.add(fragment);
        fragmentsNameList.add(name);
    }

    public SunFragment getSunFragment(){
        return (SunFragment)fragmentList.get(0);
    }

    public MoonFragment getMoonFragment(){
        return (MoonFragment)fragmentList.get(1);
    }
    @Override
    public Fragment getItem(int position) {
        return fragmentList.get(position);
    }

    @Override
    public int getCount() {
        return fragmentNumber;
    }

    @Override
    public CharSequence getPageTitle(int position) {
        return fragmentsNameList.get(position);
    }
}

//编辑

E/androidRuntime: FATAL EXCEPTION: main
                                                 Process: com.example.mariusz.astroweather, PID: 4970
                                                 java.lang.RuntimeException: Unable to start activity ComponentInfo{com.example.mariusz.astroweather/com.example.mariusz.astroweather.MainActivity}: java.lang.NullPointerException: Attempt to invoke virtual method 'double com.example.mariusz.astroweather.MainActivity.getLon()' on a null object reference
                                                     at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2416)
                                                     at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2476)
                                                     at android.app.ActivityThread.-wrap11(ActivityThread.java)
                                                     at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1344)
                                                     at android.os.Handler.dispatchMessage(Handler.java:102)
                                                     at android.os.Looper.loop(Looper.java:148)
                                                     at android.app.ActivityThread.main(ActivityThread.java:5417)
                                                     at java.lang.reflect.Method.invoke(Native Method)
                                                     at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:726)
                                                     at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:616)
                                                  Caused by: java.lang.NullPointerException: Attempt to invoke virtual method 'double com.example.mariusz.astroweather.MainActivity.getLon()' on a null object reference
                                                     at com.example.mariusz.astroweather.SunFragment.calculateWeather(SunFragment.java:56)
                                                     at com.example.mariusz.astroweather.MainActivity.refreshView(MainActivity.java:124)
                                                     at com.example.mariusz.astroweather.MainActivity.onCreate(MainActivity.java:49)
                                                     at android.app.Activity.performCreate(Activity.java:6237)
                                                     at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1107)
                                                     at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2369)
                                                     at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2476) 
                                                     at android.app.ActivityThread.-wrap11(ActivityThread.java) 
                                                     at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1344) 
                                                     at android.os.Handler.dispatchMessage(Handler.java:102) 
                                                     at android.os.Looper.loop(Looper.java:148) 
                                                     at android.app.ActivityThread.main(ActivityThread.java:5417) 
                                                     at java.lang.reflect.Method.invoke(Native Method) 
                                                     at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:726) 
                                                     at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:616) 


com.example.mariusz.astroweather.SunFragment.calculateWeather(SunFragment.java:56) 

是行:

longitude =((MainActivity)getActivity())。getLon();

添加onAreate of MainActivity:

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

        setViewPager();
        refreshView();
    }
答案

根据你的意见,如果。你可以在活动中使用片段的权力然后你必须做这样的事情

YourFragment fragment = (YourFragment) getFragmentManager().findFragmentById(R.id.YourFragment);
//any mothed of your fragment that you like
fragment.calculateWeather(); 

对于调用片段内部的Activity方法,这是要走的路

因为你的logCat我预见到你在错误的地方使用你的片段来调用活动方法!你应该在片段的OnActivityCreated()中使用你的这个方法,而不是在其他地方使用它吗?

// use this 
    public void calculateWeather(){
        longitude = ((MainActivity)getActivity()).getLon();
        latitude = ((MainActivity)getActivity()).getLat();

    }
   //as

  //in your fragment

   @Override

   public void OnActvityCreated(){
   // .... super()....
     //......
     calculateWeather();
     //......
  }

以上是关于在使用ViewPager时尝试从其父活动修改片段时出现空指针异常的主要内容,如果未能解决你的问题,请参考以下文章

选择片段 A 时如何在 ViewPager 上不一起启动所有片段

包含viewpager的android活动缓慢打开

使用 ViewPager 滑动时,片段没有调用 OnResume()

滑动 ViewPager 时如何清除片段相关状态

使用viewpager时,片段不会全屏显示

ViewPager - 将数据从片段发送到活动时出现 Android 错误 setCurrentItem(int,boolean)