首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Android - invalidate()不会在CustomView中调用我的onDraw

Android - invalidate()不会在CustomView中调用我的onDraw
EN

Stack Overflow用户
提问于 2019-08-07 14:57:47
回答 2查看 101关注 0票数 0

我有一个content_main.xml:

代码语言:javascript
复制
<LinearLayout
    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"
    app:layout_behavior="@string/appbar_scrolling_view_behavior"
    tools:context=".MainActivity"
    tools:showIn="@layout/activity_main">

    <com.example.CustomView
        android:id="@+id/customView"
        android:layout_width="match_parent"
        android:layout_height="match_parent"/>

</LinearLayout >

在MainActivity.java中,在onCreate中,我调用CustomView:

代码语言:javascript
复制
@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);

    setContentView(R.layout.activity_main);
    Toolbar toolbar = findViewById(R.id.toolbar);
    setSupportActionBar(toolbar);

    customView = new CustomView(this, attributeSet);
    customView.init();
}

在CustomView中,我有一个onDraw:

代码语言:javascript
复制
@SuppressLint("DrawAllocation")
@Override
protected void onDraw(Canvas canvas) {
    canvas.drawColor(Color.BLUE);
    drawValidMoves(canvas, squareSize);
}

在MainActivity中,onTouch

代码语言:javascript
复制
@Override
public boolean onTouchEvent(MotionEvent event) {
    if(event.getAction() == MotionEvent.ACTION_DOWN) {
        int x = (int)event.getX();
        int y = (int)event.getY();

        String text = customView.isTouched(x, y, customView.getSquareSize());
        Toast.makeText(this, text, Toast.LENGTH_LONG).show();
    }
    return super.onTouchEvent(event);
}

从CustomView.java - isTouched调用一个方法,该方法更改了绘制元素矩阵中的一些内容,之后,我将执行以下操作:

代码语言:javascript
复制
  setWillNotDraw(false);
  invalidate();

但是我的游戏再也不能到达onDraw了..。如果我直接在onCreate中调用CustomView,那么无效将起作用:

代码语言:javascript
复制
customView = new CustomView(this, attributeSet);
customView.init();
setContentView(customView);

但是我不再有工具栏了,我需要它

稍后编辑:

content_main.xml:

代码语言:javascript
复制
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
    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:id="@+id/linearLayoutId"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    app:layout_behavior="@string/appbar_scrolling_view_behavior"
    tools:context=".MainActivity"
    tools:showIn="@layout/activity_main">

    <com.example.clotz.CustomView
        android:id="@+id/customView"
        android:layout_width="match_parent"
        android:layout_height="match_parent"/>

</LinearLayout >

MainActivity.java - onCreate -我把数据从init方法移到了构造器中,去掉了init。

代码语言:javascript
复制
public class MainActivity extends AppCompatActivity {

    CustomView customView;

    @SuppressLint("WrongViewCast")
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        setContentView(R.layout.activity_main);
        Toolbar toolbar = findViewById(R.id.toolbar);
        setSupportActionBar(toolbar);

        customView = findViewById(R.id.customView);
    }

但在onTouchEvent中,customView现在为空:

代码语言:javascript
复制
@Override
public boolean onTouchEvent(MotionEvent event) {
    if(event.getAction() == MotionEvent.ACTION_DOWN) {
        int x = (int)event.getX();
        int y = (int)event.getY();

        String text = customView.isTouched(x, y, customView.getSquareSize());
        Toast.makeText(this, text, Toast.LENGTH_LONG).show();
    }
    return super.onTouchEvent(event);
}
EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2019-08-07 17:24:05

@Mike M帮我解决了这个问题,我在content_main.xml中输入了linearLayout的id:

代码语言:javascript
复制
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
    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:id="@+id/linearLayoutId"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    app:layout_behavior="@string/appbar_scrolling_view_behavior"
    tools:context=".MainActivity"
    tools:showIn="@layout/activity_main">

    <com.example.clotz.CustomView
        android:id="@+id/customView"
        android:layout_width="match_parent"
        android:layout_height="match_parent"/>

</LinearLayout >

在MainActivity.java - onCreate中(我把数据从init方法转移到构造函数中,去掉了init),我用findViewById(R.id.customView)创建了自定义视图;

代码语言:javascript
复制
public class MainActivity extends AppCompatActivity {

    CustomView customView;

    @SuppressLint("WrongViewCast")
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        setContentView(R.layout.activity_main);
        Toolbar toolbar = findViewById(R.id.toolbar);
        setSupportActionBar(toolbar);

        customView = findViewById(R.id.customView);
    }

问题出在CustomView.java中,我忘了把attributeSet传递给超类:

代码语言:javascript
复制
public CustomView(Context context, AttributeSet attributeSet) {
    super(context);

    initializeMovedMatrix();
    setInitialPositionForPieces();
    // create the Paint to set its color
    paint = new Paint();
    piecesMoves = new PiecesMoves(this);
}

并将其与customView =findViewById(R.id.customView)相结合;

代码语言:javascript
复制
super(context, attributeSet);

解决了这个问题。再次感谢MikeM!

票数 1
EN

Stack Overflow用户

发布于 2019-08-07 16:15:52

不能删除onDraw方法中的super.onDraw(canvas)

代码语言:javascript
复制
@SuppressLint("DrawAllocation")
@Override
protected void onDraw(Canvas canvas) {
    super.onDraw(canvas);
    canvas.drawColor(Color.BLUE);
    drawValidMoves(canvas, squareSize);
}
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/57388578

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档