Android: Inflate Custom View inside Fragment

浪尽此生 提交于 2019-12-12 03:49:15

问题


I have an application that uses a fragment view as part of its layout. Within this fragment, I want to instantiate a Paint Canvas where i can do custom drawing.

The problem is, my app crashes when I go to inflate the fragment with the error android.view.InflateException: Binary XML file line #15: Binary XML file line #15: Error inflating class com.example.xxxxx.NeckCanvasOverlay

I'm not sure what's causing my Paint class not to inflate properly. I know there are special rules about how you use findViewById inside a fragment, but I thought I was adhering to them since i'm calling findViewByid on the fragment's view itself (called "v" in my code).

How can I fix this issue?

FragmentNeckDisplayMenu.java (Fragment Class)

public class FragmentNeckDisplayMenu extends Fragment {
    private static View v;
    private NeckCanvasOverlay neckHUD;

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        v = inflater.inflate(R.layout.menu_fragment_neck_display,container,false);      //ERROR HERE
        NeckCanvasOverlay neckHUD = (NeckCanvasOverlay) v.findViewById(R.id.neckHUD);   //paint test
        ...
        return v;
    }
}

NeckCanvasOverlay.java (Paint Class)

class NeckCanvasOverlay extends View {
    private Paint mPainter;

    public NeckCanvasOverlay(Context context) {
        super(context);
        initView();
    }

    private void initView(){    //Initializes canvas & paint objects here to save performance
        mPainter = new Paint(Paint.ANTI_ALIAS_FLAG);
        mPainter.setColor(Color.BLUE);
        mPainter.setAlpha(128);
    }

    @Override
    public void onDraw(Canvas canvas) {
        super.onDraw(canvas);
        canvas.drawCircle(180, 900, 200, mPainter);
    }
}

menu_fragment_neck_display.xml (Fragment's Layout)

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    android:id="@+id/canvas"
    android:background="@drawable/image">

    <LinearLayout
        android:layout_width="148dp"
        android:layout_height="0dp"
        android:layout_gravity="center"
        android:layout_weight="4">
        !--Custom view for Canvas here -->
        <com.example.xxxxx.NeckCanvasOverlay
            android:id="@+id/neckHUD"
            android:layout_width="wrap_content"
            android:layout_height="match_parent"
            android:background="@drawable/neck_for_menu"/>
    </LinearLayout>

    <Button
        android:id="@+id/menuIcon"
        android:layout_width="wrap_content"
        android:layout_height="0dp"
        android:layout_marginTop="64dp"
        android:text="Menu"
        android:layout_alignParentLeft="true"
        android:layout_alignParentStart="true"
        android:layout_gravity="bottom"
        android:layout_weight="0.5"/>
</LinearLayout>

Full Stack Trace (Edit: Included full trace)

   08-06 21:47:24.894 26334-26334/com.example.xxxxx E/ACRA: ACRA caught a InflateException for com.example.xxxxx
                                                             android.view.InflateException: Binary XML file line #15: Binary XML file line #15: Error inflating class com.example.gu.NeckCanvasOverlay
                                                                 at android.view.LayoutInflater.inflate(LayoutInflater.java:551)
                                                                 at android.view.LayoutInflater.inflate(LayoutInflater.java:429)
                                                                 at com.example.xxxxx.FragmentNeckDisplayMenu.onCreateView(FragmentNeckDisplayMenu.java:32)
                                                                 at android.support.v4.app.Fragment.performCreateView(Fragment.java:1962)
                                                                 at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1067)
                                                                 at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1248)
                                                                 at android.support.v4.app.BackStackRecord.run(BackStackRecord.java:738)
                                                                 at android.support.v4.app.FragmentManagerImpl.execPendingActions(FragmentManager.java:1613)
                                                                 at android.support.v4.app.FragmentManagerImpl.executePendingTransactions(FragmentManager.java:570)
                                                                 at android.support.v4.app.FragmentPagerAdapter.finishUpdate(FragmentPagerAdapter.java:141)
                                                                 at android.support.v4.view.ViewPager.populate(ViewPager.java:1106)
                                                                 at android.support.v4.view.ViewPager.populate(ViewPager.java:952)
                                                                 at android.support.v4.view.ViewPager.setOffscreenPageLimit(ViewPager.java:733)
                                                                 at com.example.xxxxx.PlayFrets.configMenu(PlayFrets.java:150)
                                                                 at com.example.xxxxx.AsyncTask_NoteFileLoader.onPostExecute(AsyncTask_NoteFileLoader.java:125)
                                                                 at com.example.xxxxx.AsyncTask_NoteFileLoader.onPostExecute(AsyncTask_NoteFileLoader.java:9)
                                                                 at android.os.AsyncTask.finish(AsyncTask.java:651)
                                                                 at android.os.AsyncTask.access$500(AsyncTask.java:180)
                                                                 at android.os.AsyncTask$InternalHandler.handleMessage(AsyncTask.java:668)
                                                                 at android.os.Handler.dispatchMessage(Handler.java:102)
                                                                 at android.os.Looper.loop(Looper.java:158)
                                                                 at android.app.ActivityThread.main(ActivityThread.java:7229)
                                                                 at java.lang.reflect.Method.invoke(Native Method)
                                                                 at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1230)
                                                                 at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1120)
                                                              Caused by: android.view.InflateException: Binary XML file line #15: Error inflating class com.example.gu.NeckCanvasOverlay
                                                                 at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:788)
                                                                 at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:716)
                                                                 at android.view.LayoutInflater.rInflate(LayoutInflater.java:847)
                                                                 at android.view.LayoutInflater.rInflateChildren(LayoutInflater.java:810)
                                                                 at android.view.LayoutInflater.rInflate(LayoutInflater.java:855)
                                                                 at android.view.LayoutInflater.rInflateChildren(LayoutInflater.java:810)
                                                                 at android.view.LayoutInflater.inflate(LayoutInflater.java:527)
                                                                 at android.view.LayoutInflater.inflate(LayoutInflater.java:429) 
                                                                 at com.example.xxxxx.FragmentNeckDisplayMenu.onCreateView(FragmentNeckDisplayMenu.java:32) 
                                                                 at android.support.v4.app.Fragment.performCreateView(Fragment.java:1962) 
                                                                 at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1067) 
                                                                 at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1248) 
                                                                 at android.support.v4.app.BackStackRecord.run(BackStackRecord.java:738) 
                                                                 at android.support.v4.app.FragmentManagerImpl.execPendingActions(FragmentManager.java:1613) 
                                                                 at android.support.v4.app.FragmentManagerImpl.executePendingTransactions(FragmentManager.java:570) 
                                                                 at android.support.v4.app.FragmentPagerAdapter.finishUpdate(FragmentPagerAdapter.java:141) 
                                                                 at android.support.v4.view.ViewPager.populate(ViewPager.java:1106) 
                                                                 at android.support.v4.view.ViewPager.populate(ViewPager.java:952) 
                                                                 at android.support.v4.view.ViewPager.setOffscreenPageLimit(ViewPager.java:733) 
                                                                 at com.example.xxxxx.PlayFrets.configMenu(PlayFrets.java:150) 
                                                                 at com.example.xxxxx.AsyncTask_NoteFileLoader.onPostExecute(AsyncTask_NoteFileLoader.java:125) 
                                                                 at com.example.xxxxx.AsyncTask_NoteFileLoader.onPostExecute(AsyncTask_NoteFileLoader.java:9) 
                                                                 at android.os.AsyncTask.finish(AsyncTask.java:651) 
                                                                 at android.os.AsyncTask.access$500(AsyncTask.java:180) 
                                                                 at android.os.AsyncTask$InternalHandler.handleMessage(AsyncTask.java:668) 
                                                                 at android.os.Handler.dispatchMessage(Handler.java:102) 
                                                                 at android.os.Looper.loop(Looper.java:158) 
                                                                 at android.app.ActivityThread.main(ActivityThread.java:7229) 
                                                                 at java.lang.reflect.Method.invoke(Native Method) 
                                                                 at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1230) 
                                                                 at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1120) 
                                                              Caused by: java.lang.ClassNotFoundException: Didn't find class "com.example.gu.NeckCanvasOverlay" on path: DexPathList[[zip file "/data/app/com.example.xxxxx-2/base.apk"],nativeLibraryDirectories=[/data/app/com.example.xxxxx-2/lib/arm64, /vendor/lib64, /system/lib64]]
                                                                 at dalvik.system.BaseDexClassLoader.findClass(BaseDexClassLoader.java:56)
                                                                 at java.lang.ClassLoader.loadClass(ClassLoader.java:511)
                                                                 at java.lang.ClassLoader.loadClass(ClassLoader.java:469)
                                                                 at android.view.LayoutInflater.createView(LayoutInflater.java:595)
                                                                 at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:776)
                                                                 at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:716) 
                                                                 at android.view.LayoutInflater.rInflate(LayoutInflater.java:847) 
                                                                 at android.view.LayoutInflater.rInflateChildren(LayoutInflater.java:810) 
                                                                 at android.view.LayoutInflater.rInflate(LayoutInflater.java:855) 
                                                                 at android.view.LayoutInflater.rInflateChildren(LayoutInflater.java:810) 
                                                                 at android.view.LayoutInflater.inflate(LayoutInflater.java:527) 
                                                                 at android.view.LayoutInflater.inflate(LayoutInflater.java:429) 
                                                                 at com.example.xxxxx.FragmentNeckDisplayMenu.onCreateView(FragmentNeckDisplayMenu.java:32) 
                                                                 at android.support.v4.app.Fragment.performCreateView(Fragment.java:1962) 
                                                                 at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1067) 
                                                                 at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1248) 
                                                                 at android.support.v4.app.BackStackRecord.run(BackStackRecord.java:738) 
                                                                 at android.support.v4.app.FragmentManagerImpl.execPendingActions(FragmentManager.java:1613) 
                                                                 at android.support.v4.app.FragmentManagerImpl.executePendingTransactions(FragmentManager.java:570) 
                                                                 at android.support.v4.app.FragmentPagerAdapter.finishUpdate(FragmentPagerAdapter.java:141) 
                                                                 at android.support.v4.view.ViewPager.populate(ViewPager.java:1106) 
                                                                 at android.support.v4.view.ViewPager.populate(ViewPager.java:952) 
                                                                 at android.support.v4.view.ViewPager.setOffscreenPageLimit(ViewPager.java:733) 
                                                                 at com.example.xxxxx.PlayFrets.configMenu(PlayFrets.java:150) 
                                                                 at com.example.xxxxx.AsyncTask_NoteFileLoader.onPostExecute(AsyncTask_NoteFileLoader.java:125) 
                                                                 at com.example.xxxxx.AsyncTask_NoteFileLoader.onPostExecute(AsyncTask_NoteFileLoader.java:9) 
                                                                 at android.os.AsyncTask.finish(AsyncTask.java:651) 
                                                                 at android.os.AsyncTask.access$500(AsyncTask.java:180) 
                                                                 at android.os.AsyncTask$InternalHandler.handleMessage(AsyncTask.java:668) 
                                                                 at android.os.Handler.dispatchMessage(Handler.java:102) 
                                                                 at android.os.Looper.loop(Looper.java:158) 
                                                                 at android.app.ActivityThread.main(ActivityThread.java:7229) 
                                                                 at java.lang.reflect.Method.invoke(Native Method) 
                                                                 at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1230) 
                                                                 at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1120) 
                                                                Suppressed: java.lang.ClassNotFoundException: com.example.gu.NeckCanvasOverlay
                                                                 at java.lang.Class.classForName(Native Method)
                                                                 at java.lang.BootClassLoader.findClass(ClassLoader.java:781)
                                                                 at java.lang.BootClassLoader.loadClass(ClassLoader.java:841)
                                                                 at java.lang.ClassLoader.loadClass(ClassLoader.java:504)
                                                                        ... 33 more
                                                              Caused by: java.lang.NoClassDefFoundError: Class not found using the boot class loader; no stack trace available
08-06 21:47:24.954 26334-27123/? E/AndroidRuntime: FATAL EXCEPTION: main
                                                   Process: com.example.xxxxx, PID: 26334
                                                   android.view.InflateException: Binary XML file line #15: Binary XML file line #15: Error inflating class com.example.gu.NeckCanvasOverlay
                                                       at android.view.LayoutInflater.inflate(LayoutInflater.java:551)
                                                       at android.view.LayoutInflater.inflate(LayoutInflater.java:429)
                                                       at com.example.xxxxx.FragmentNeckDisplayMenu.onCreateView(FragmentNeckDisplayMenu.java:32)
                                                       at android.support.v4.app.Fragment.performCreateView(Fragment.java:1962)
                                                       at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1067)
                                                       at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1248)
                                                       at android.support.v4.app.BackStackRecord.run(BackStackRecord.java:738)
                                                       at android.support.v4.app.FragmentManagerImpl.execPendingActions(FragmentManager.java:1613)
                                                       at android.support.v4.app.FragmentManagerImpl.executePendingTransactions(FragmentManager.java:570)
                                                       at android.support.v4.app.FragmentPagerAdapter.finishUpdate(FragmentPagerAdapter.java:141)
                                                       at android.support.v4.view.ViewPager.populate(ViewPager.java:1106)
                                                       at android.support.v4.view.ViewPager.populate(ViewPager.java:952)
                                                       at android.support.v4.view.ViewPager.setOffscreenPageLimit(ViewPager.java:733)
                                                       at com.example.xxxxx.PlayFrets.configMenu(PlayFrets.java:150)
                                                       at com.example.xxxxx.AsyncTask_NoteFileLoader.onPostExecute(AsyncTask_NoteFileLoader.java:125)
                                                       at com.example.xxxxx.AsyncTask_NoteFileLoader.onPostExecute(AsyncTask_NoteFileLoader.java:9)
                                                       at android.os.AsyncTask.finish(AsyncTask.java:651)
                                                       at android.os.AsyncTask.access$500(AsyncTask.java:180)
                                                       at android.os.AsyncTask$InternalHandler.handleMessage(AsyncTask.java:668)
                                                       at android.os.Handler.dispatchMessage(Handler.java:102)
                                                       at android.os.Looper.loop(Looper.java:158)
                                                       at android.app.ActivityThread.main(ActivityThread.java:7229)
                                                       at java.lang.reflect.Method.invoke(Native Method)
                                                       at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1230)
                                                       at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1120)
                                                    Caused by: android.view.InflateException: Binary XML file line #15: Error inflating class com.example.gu.NeckCanvasOverlay
                                                       at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:788)
                                                       at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:716)
                                                       at android.view.LayoutInflater.rInflate(LayoutInflater.java:847)
                                                       at android.view.LayoutInflater.rInflateChildren(LayoutInflater.java:810)
                                                       at android.view.LayoutInflater.rInflate(LayoutInflater.java:855)
                                                       at android.view.LayoutInflater.rInflateChildren(LayoutInflater.java:810)
                                                       at android.view.LayoutInflater.inflate(LayoutInflater.java:527)
                                                       at android.view.LayoutInflater.inflate(LayoutInflater.java:429) 
                                                       at com.example.xxxxx.FragmentNeckDisplayMenu.onCreateView(FragmentNeckDisplayMenu.java:32) 
                                                       at android.support.v4.app.Fragment.performCreateView(Fragment.java:1962) 
                                                       at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1067) 
                                                       at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1248) 
                                                       at android.support.v4.app.BackStackRecord.run(BackStackRecord.java:738) 
                                                       at android.support.v4.app.FragmentManagerImpl.execPendingActions(FragmentManager.java:1613) 
                                                       at android.support.v4.app.FragmentManagerImpl.executePendingTransactions(FragmentManager.java:570) 
                                                       at android.support.v4.app.FragmentPagerAdapter.finishUpdate(FragmentPagerAdapter.java:141) 
                                                       at android.support.v4.view.ViewPager.populate(ViewPager.java:1106) 
                                                       at android.support.v4.view.ViewPager.populate(ViewPager.java:952) 
                                                       at android.support.v4.view.ViewPager.setOffscreenPageLimit(ViewPager.java:733) 
                                                       at com.example.xxxxx.PlayFrets.configMenu(PlayFrets.java:150) 
                                                       at com.example.xxxxx.AsyncTask_NoteFileLoader.onPostExecute(AsyncTask_NoteFileLoader.java:125) 
                                                       at com.example.xxxxx.AsyncTask_NoteFileLoader.onPostExecute(AsyncTask_NoteFileLoader.java:9) 
                                                       at android.os.AsyncTask.finish(AsyncTask.java:651) 
                                                       at android.os.AsyncTask.access$500(AsyncTask.java:180) 
                                                       at android.os.AsyncTask$InternalHandler.handleMessage(AsyncTask.java:668) 
                                                       at android.os.Handler.dispatchMessage(Handler.java:102) 
                                                       at android.os.Looper.loop(Looper.java:158) 
                                                       at android.app.ActivityThread.main(ActivityThread.java:7229) 
                                                       at java.lang.reflect.Method.invoke(Native Method) 
                                                       at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1230) 
                                                       at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1120) 
                                                    Caused by: java.lang.ClassNotFoundException: Didn't find class "com.example.gu.NeckCanvasOverlay" on path: DexPathList[[zip file "/data/app/com.example.xxxxx-2/base.apk"],nativeLibraryDirectories=[/data/app/com.example.xxxxx-2/lib/arm64, /vendor/lib64, /system/lib64]]
                                                       at dalvik.system.BaseDexClassLoader.findClass(BaseDexClassLoader.java:56)
                                                       at java.lang.ClassLoader.loadClass(ClassLoader.java:511)
                                                       at java.lang.ClassLoader.loadClass(ClassLoader.java:469)
                                                       at android.view.LayoutInflater.createView(LayoutInflater.java:595)
                                                       at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:776)
                                                       at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:716) 
                                                       at android.view.LayoutInflater.rInflate(LayoutInflater.java:847) 
                                                       at android.view.LayoutInflater.rInflateChildren(LayoutInflater.java:810) 
                                                       at android.view.LayoutInflater.rInflate(LayoutInflater.java:855) 
                                                       at android.view.LayoutInflater.rInflateChildren(LayoutInflater.java:810) 
                                                       at android.view.LayoutInflater.inflate(LayoutInflater.java:527) 
                                                       at android.view.LayoutInflater.inflate(LayoutInflater.java:429) 
                                                       at com.example.xxxxx.FragmentNeckDisplayMenu.onCreateView(FragmentNeckDisplayMenu.java:32) 
                                                       at android.support.v4.app.Fragment.performCreateView(Fragment.java:1962) 
                                                       at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1067) 
                                                       at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1248) 
                                                       at android.support.v4.app.BackStackRecord.run(BackStackRecord.java:738) 
                                                       at android.support.v4.app.FragmentManagerImpl.execPendingActions(FragmentManager.java:1613) 
                                                       at android.support.v4.app.FragmentManagerImpl.executePendingTransactions(FragmentManager.java:570) 
                                                       at android.support.v4.app.FragmentPagerAdapter.finishUpdate(FragmentPagerAdapter.java:141) 
                                                       at android.support.v4.view.ViewPager.populate(ViewPager.java:1106) 
                                                       at android.support.v4.view.ViewPager.populate(ViewPager.java:952) 
                                                       at android.support.v4.view.ViewPager.setOffscreenPageLimit(ViewPager.java:733) 
                                                       at com.example.xxxxx.PlayFrets.configMenu(PlayFrets.java:150) 
                                                       at com.example.xxxxx.AsyncTask_NoteFileLoader.onPostExecute(AsyncTask_NoteFileLoader.java:125) 

回答1:


The immediate problem is a ClassNotFoundException. When dealing with custom Views in a layout, a common cause for this is an incorrect class name in the layout XML, which seems to have been the issue here. Ensure that the XML tag has the correct, fully-qualified class name for the custom View class, which will be the class's package from the top of the file, prepended to the class name.

Additionally, Views inflated from your layout will be instantiated with a two-argument constructor that takes a Context and an AttributeSet. Your class definition needs to have at least that constructor to allow inflation, or you'll get a NoSuchMethodException. Also, it would make things a little simpler if you'd chain your constructors, if you're just extending View. For example:

public NeckCanvasOverlay(Context context) {
    this(context, null);
}

public NeckCanvasOverlay(Context context, AttributeSet attrs) {
    super(context, attrs);
    initView();
}



回答2:


It is safer to include all three constructors for the custom View. For example, include the following Constructors for your NeckCanvasOverlay.

public NeckCanvasOverlay(Context context) {
        super(context);
        initView();
    }

    public NeckCanvasOverlay(Context context, AttributeSet attrs) {
        super(context, attrs);
        initView();
    }

    public NeckCanvasOverlay(Context context, AttributeSet attrs, int defStyle) {
        super(context, attrs, defStyle);
        initView();
    }

I hope this helps. Give it a try and let me know if you get the same error.



来源:https://stackoverflow.com/questions/38809295/android-inflate-custom-view-inside-fragment

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!