无法实例化CustomView(编辑器预览中的错误,编译后没有显示)

时间:2017-04-26 17:11:23

标签: java android android-custom-view

所以,我创建了一个名为CustomView的{​​{1}},

ButtonWithCaption.xml

及其控制器<?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_weight="1" android:background="?attr/selectableItemBackground" android:paddingBottom="@dimen/spacing_normal" android:paddingLeft="@dimen/spacing_small" android:paddingRight="@dimen/spacing_small" android:paddingTop="@dimen/spacing_normal"> <ImageView android:id="@+id/bwc_icon" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_centerHorizontal="true" android:layout_marginBottom="2dp" android:scaleType="centerCrop" /> <TextView android:id="@+id/bwc_caption" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_below="@id/bwc_icon" android:textAlignment="center" />

ButtonWithCaption.java

没什么特别的。

然后,我在public class ButtonWithCaption extends RelativeLayout { private ImageView mImageView; private TextView mTextView; private int mIconSrc; private String mCaptionText; private boolean mShowIcon; private boolean mShowText; public ButtonWithCaption(Context context) { super(context); init(context, null, 0); } public ButtonWithCaption(Context context, AttributeSet attrs) { super(context, attrs); init(context, attrs, 0); } public ButtonWithCaption(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); init(context, attrs, defStyleAttr); } private void init(Context context, AttributeSet attrs, int defStyleAttr) { TypedArray a = context.getTheme().obtainStyledAttributes(attrs, R.styleable.ButtonWithCaption, 0, 0); try { mIconSrc = a.getResourceId(R.styleable.ButtonWithCaption_iconSrc, 0); mCaptionText = a.getString(R.styleable.ButtonWithCaption_captionText); mShowIcon = a.getBoolean(R.styleable.ButtonWithCaption_showIcon, mIconSrc != 0); mShowText = a.getBoolean(R.styleable.ButtonWithCaption_showText, !mCaptionText.isEmpty()); mImageView = (ImageView) findViewById(R.id.bwc_icon); mTextView = (TextView) findViewById(R.id.bwc_caption); mImageView.setImageResource(mIconSrc); mTextView.setText(mCaptionText); } finally { a.recycle(); } } }

中声明了自定义属性
attrs.xml

这是我的<resources> <declare-styleable name="ButtonWithCaption"> <attr name="iconSrc" format="reference" /> <attr name="captionText" format="string" /> <attr name="showIcon" format="boolean" /> <attr name="showText" format="boolean" /> </declare-styleable> </resources>

activity_main.xml

...但奇怪的是,Android Studio的预览给了我渲染错误:

  

无法实例化一个或多个类

with stacktrace:

  

显示java.lang.NullPointerException       在id.foodmap.foodmapcustomviews.ButtonWithCaption.init(ButtonWithCaption.java:54)       在id.foodmap.foodmapcustomviews.ButtonWithCaption。(ButtonWithCaption.java:29)       at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)       at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)       at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)       at java.lang.reflect.Constructor.newInstance(Constructor.java:423)       在org.jetbrains.android.uipreview.ViewLoader.createNewInstance(ViewLoader.java:475)       在org.jetbrains.android.uipreview.ViewLoader.loadClass(ViewLoader.java:262)       在org.jetbrains.android.uipreview.ViewLoader.loadView(ViewLoader.java:220)       在com.android.tools.idea.rendering.LayoutlibCallbackImpl.loadView(LayoutlibCallbackImpl.java:186)       在android.view.BridgeInflater.loadCustomView(BridgeInflater.java:334)       在android.view.BridgeInflater.loadCustomView(BridgeInflater.java:345)       在android.view.BridgeInflater.createViewFromTag(BridgeInflater.java:245)       在android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:727)       在android.view.LayoutInflater.rInflate_Original(LayoutInflater.java:858)       在android.view.LayoutInflater_Delegate.rInflate(LayoutInflater_Delegate.java:70)       在android.view.LayoutInflater.rInflate(LayoutInflater.java:834)       在android.view.LayoutInflater.rInflateChildren(LayoutInflater.java:821)       在android.view.LayoutInflater.inflate(LayoutInflater.java:518)       在android.view.LayoutInflater.inflate(LayoutInflater.java:397)       在com.android.layoutlib.bridge.impl.RenderSessionImpl.inflate(RenderSessionImpl.java:324)       在com.android.layoutlib.bridge.Bridge.createSession(Bridge.java:429)       在com.android.ide.common.rendering.LayoutLibrary.createSession(LayoutLibrary.java:368)       在com.android.tools.idea.rendering.RenderTask $ 2.compute(RenderTask.java:567)       在com.android.tools.idea.rendering.RenderTask $ 2.compute(RenderTask.java:549)       在com.intellij.openapi.application.impl.ApplicationImpl.runReadAction(ApplicationImpl.java:863)       在com.android.tools.idea.rendering.RenderTask.createRenderSession(RenderTask.java:549)       在com.android.tools.idea.rendering.RenderTask.lambda $ inflate $ 1(RenderTask.java:680)       at java.util.concurrent.FutureTask.run(FutureTask.java:266)       在java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)       at java.util.concurrent.ThreadPoolExecutor $ Worker.run(ThreadPoolExecutor.java:617)       在java.lang.Thread.run(Thread.java:745)

<?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-auto" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" tools:context="id.foodmap.foodmapcustomviews.MainActivity"> <id.foodmap.foodmapcustomviews.ButtonWithCaption android:id="@+id/button_with_caption" android:layout_width="match_parent" android:layout_height="match_parent" app:captionText="Test" app:iconSrc="@drawable/ic_email_gray_24dp" /> </RelativeLayout> findViewById() ButtonWithCaption.java查找TextViewImageView也会返回null。

有谁知道是什么造成的?因为它甚至没有显示在编辑器预览窗口中。

P.S。如果我使用,预览会正确显示元素。 P.S.S.它编译到我的手机没有错误,但没有显示ButtonWithCaption

提前致谢

2 个答案:

答案 0 :(得分:2)

您收到NullPointerException,因为您没有从ButtonWithCaption.xml夸大观看次数。解决此问题的一种方法是使用静态View.inflate()方法:

 private void init(Context context, AttributeSet attrs, int defStyleAttr) {
    TypedArray a = context.getTheme().obtainStyledAttributes(attrs, R.styleable.ButtonWithCaption, 0, 0);

    try {
        mIconSrc = a.getResourceId(R.styleable.ButtonWithCaption_iconSrc, 0);
        mCaptionText = a.getString(R.styleable.ButtonWithCaption_captionText);
        mShowIcon = a.getBoolean(R.styleable.ButtonWithCaption_showIcon, mIconSrc != 0);
        mShowText = a.getBoolean(R.styleable.ButtonWithCaption_showText, !mCaptionText.isEmpty());

        View v = View.inflate(context, R.layout.ButtonWithCaption, this);   // add this line
        mImageView = (ImageView) findViewById(R.id.bwc_icon);
        mTextView = (TextView) findViewById(R.id.bwc_caption);

        mImageView.setImageResource(mIconSrc);
        mTextView.setText(mCaptionText);
    } finally {
        a.recycle();
    }
}

答案 1 :(得分:-1)

您必须将标记<RelativeLayout>替换为您的类,如下所示:

<?xml version="1.0" encoding="utf-8"?>

<com.yourpackage.app.ButtonWithCaption xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    ...
    >
        ...
</com.yourpackage.app.ButtonWithCaption>

com.yourpackage.app应该是ButtonWithCaptionclass所在的路径。

编辑:

您发布的布局应该是您的活动布局,ButtonWithCaptionclass应该是您的xml元素,而不是您的xml名称,因此请更改名称,将RelativeLayout替换为您的自定义类并尝试使用。