简体   繁体   English

NullPointerException由findViewById引起

[英]NullPointerException caused by findViewById

I'm having trouble finding why this line throws a NullPointerException exception: 我在查找为什么此行引发NullPointerException异常时遇到了麻烦:

ImageView imageView1 =  (ImageView) rootView.findViewById(R.id.imageView1);

It's all happening within a fragment This is the fragment: 这都是在一个片段中发生的这是片段:

public static class MyFragment extends Fragment {

    private View rootView;

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
            Bundle savedInstanceState) {

        rootView = inflater.inflate(R.layout.fragment_layout,
                container, false);

        return rootView;
    }

    public void setImage(Uri imageUri) {
        ImageView imageView1 =  (ImageView) rootView.findViewById(R.id.imageView1);
        imageView1.setImageURI(imageUri);
    }
}

And this is the fragment layout: 这是片段布局:

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="fill_parent"
android:layout_height="fill_parent">

<ScrollView
      android:layout_width="fill_parent"
      android:layout_height="wrap_content">

    <ImageView
        android:id="@+id/imageView1"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content" />

</ScrollView>
</RelativeLayout>

The method setImage() is called from outside the fragment. 从片段外部调用setImage()方法。

So, it looks like your rootView is null ; 因此,看来您的rootViewnull

Are you sure you are calling setImage() on the instance of your fragment that has had onCreateView called? 您确定要在已调用onCreateView片段实例上调用setImage()吗? You could test this by adding a println to both methods and checking the console/LogCat for their order. 您可以通过在两个方法中都添加一个println并检查控制台/ LogCat的顺序来进行测试。

You could post the code where you call setImage() . 您可以将代码张贴在调用setImage()

If it is indeed that, which is the problem, there are several solutions, some better than others. 如果确实是问题所在,那就有几种解决方案,其中一些比其他的要好。 For starters, you could try passing either the rootView or the imageView1 to the activity where you call setImage() and move setImage() to that activity. 对于初学者来说,你可以尝试通过任一rootViewimageView1到您拨打活动setImage()和移动setImage()该活动。 Not best practice, but try it and see if it works. 不是最佳做法,但请尝试一下,看看是否可行。

(Would have commented, but I don't have enough reputation. Comment back and I'll try to edit the answer according to your comments.) (本来可以发表评论,但是我没有足够的声誉。请发表评论,然后我将根据您的评论尝试编辑答案。)

This is happening because of this line private View rootView; 之所以发生这种情况,是因为这条线是private View rootView; which declares rootView but does not set it equal to anything so by default it has a value of NULL or rootView == NULL is true. 它声明了rootView但未将其设置为任何值,因此默认情况下其值为NULL或rootView == NULL为true。 Although you set it in onCreateView() what happens if onCreateView() is never called? 虽然你在设置onCreateView()会发生什么,如果onCreateView()不会被调用? rootView would still be NULL even though setImage() relies on it being set to something and this will cause a NULLPounterException . 即使setImage()依赖将NULLPounterException设置为某种值, rootView仍将为NULL,这将导致NULLPounterException There is no requirement that says onCreateView() is called before setImage() or even called at all meaning that rootView could potentially still be null and thus not have the .findViewById() method call. 没有要求说onCreateView()setImage()之前被调用甚至根本不被调用,这意味着rootView可能仍然为null,因此没有.findViewById()方法调用。 While it is technically true that onCreateView() is called first the Java compilier doesn't know this. 从技术上讲,确实首先调用了onCreateView()但是Java编译器并不知道这一点。 This has to do with how Android itself works not with the actual Java language. 这与Android本身与实际Java语言的工作方式无关。 In actuality onCreateView() is indeed run before you get a chance to run setImage() but the compilier will still complain. 实际上,在有机会运行setImage()之前,确实已运行onCreateView()但编译器仍然会抱怨。 This should be fixed if you just wrap the function with an if statement to make sure that rootView is never NULL before you do anything to it. 如果只用if语句包装函数,以确保rootView在执行任何操作之前绝不为NULL,则应该固定此问题。

Change this: 更改此:

public void setImage(Uri imageUri) {
        ImageView imageView1 =  (ImageView) rootView.findViewById(R.id.imageView1);
        imageView1.setImageURI(imageUri);
    }
}

To this: 对此:

public void setImage(Uri imageUri) {
        //Will only run if rootView isn't NULL so you won't be able to get a NULLPointer
        if(rootView != NULL){
        ImageView imageView1 =  (ImageView) rootView.findViewById(R.id.imageView1);
        imageView1.setImageURI(imageUri);
        }
    }
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM