我设计了一个名为
PaintView
的自定义类。我的目标是加载用户选择的图像并允许用户像画笔一样绘画或在其上放置不同的形状。
这是我实现该课程的方法:
package com.image.plotter
import android.content.Context
import android.graphics.Canvas
import android.graphics.Color
import android.graphics.Paint
import android.graphics.Path
import android.util.AttributeSet
import android.util.Log
import android.view.MotionEvent
import androidx.appcompat.widget.AppCompatImageView
class PaintView @JvmOverloads constructor(
context: Context,
attrs: AttributeSet? = null,
defStyle: Int = 0
) : AppCompatImageView(context, attrs, defStyle) {
companion object {
private const val TAG = "PaintView"
var pathList = ArrayList<Path>()
var colorList = ArrayList<Int>()
var paintBrush = Paint()
var path = Path()
}
init {
paintBrush.isAntiAlias = true
paintBrush.color = Color.BLACK
paintBrush.style = Paint.Style.STROKE
paintBrush.strokeJoin = Paint.Join.ROUND
paintBrush.strokeWidth = 8f
}
override fun onTouchEvent(event: MotionEvent?): Boolean {
if (event == null) return false
var x = event.x
var y = event.y
Log.d(TAG, "onTouchEvent: touched at ($x, $y)")
when (event.action) {
MotionEvent.ACTION_DOWN -> {
path.moveTo(x, y)
return true
}
MotionEvent.ACTION_MOVE -> {
path.lineTo(x, y)
pathList.add(path)
colorList.add(Color.BLACK)
}
else -> return false
}
postInvalidate()
return super.onTouchEvent(event)
}
override fun onDraw(canvas: Canvas) {
Log.d(TAG, "onDraw: drawing")
// super.onDraw(canvas)
for (i in pathList.indices) {
paintBrush.color = colorList[i]
canvas.drawPath(pathList[i], paintBrush)
invalidate()
}
}
}
它主要包括像画笔这样徒手绘画的逻辑。
我可以在 xml 中包含 PaintView,甚至可以在 Activity 的代码中以编程方式更改其背景颜色。但是,当我尝试从可绘制资源加载图像时,它没有显示图像的任何痕迹。
这是我的 MainActivity 的 xml 代码:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/main"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MainActivity">
<!-- <androidx.appcompat.widget.AppCompatImageView-->
<com.image.plotter.PaintView
android:id="@+id/canvas"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_alignParentTop="true"
android:layout_centerHorizontal="true"
android:layout_marginBottom="12dp"
android:layout_above="@id/image_picker_button"/>
<com.google.android.material.button.MaterialButton
android:id="@+id/image_picker_button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginBottom="48dp"
android:text="Select image"
android:layout_alignParentBottom="true"
android:layout_centerHorizontal="true"/>
</RelativeLayout>
这是我尝试加载图像的方法:
(binding.canvas as ImageView).setImageDrawable(ContextCompat.getDrawable(this, R.drawable.ic_launcher_background))
// binding.canvas.setImageResource(R.drawable.ic_launcher_background)
binding.canvas.setBackgroundColor(Color.GRAY)
如果我使用
androidx.appcompat.widget.AppCompatImageView
而不是 com.image.plotter.PaintView
,图像会正确加载。我在设计时错过了什么com.image.plotter.PaintView
?
结果它不起作用,因为我注释掉了
super.onDraw()
。
该函数应如下所示:
override fun onDraw(canvas: Canvas) {
Log.d(TAG, "onDraw: drawing")
super.onDraw(canvas)
for (i in pathList.indices) {
paintBrush.color = colorList[i]
canvas.drawPath(pathList[i], paintBrush)
invalidate()
}
}