как правильно добавить нескольких обьектов SurfaceView к ConstraintLayout по нажиманию пальцами

Моя программа сейчас рисует овал по нажатию пальца и водит его за пальцем.
Я хочу добавить мульти-нажатия, что бы не отпуская первого овала, нажав вторым пальцем добавить следующий.

Как сейчас работает мой код:
Здесь я создаю 20 овалов:

var ovalsViews = Array(20) { OvalsView(this) }

В функции MotionEvent.ACTION_DOWN, MotionEvent.ACTION_POINTER_DOWN (здесь я ставлю палец на экран) я добавляю овалы из таблицы овалов к layout (ConstraintLayout):

layout.addView(ovalsViews[ID])

В функции MotionEvent.ACTION_MOVE (здесь я двигаю пальцем на экран) я меняю координаты каждого овала который держу пальцем:

ovalsViews[ID]._top = motionEvent.getY(ID)
ovalsViews[ID]._left = motionEvent.getX(ID)

И на конец, в функции MotionEvent.ACTION_UP, MotionEvent.ACTION_POINTER_UP (здесь я отпускаю палец с экрана) я хочу удалить овал который держу пальцем:

layout.removeView(ovalsViews[ID])

Сейчас моя программа работает странно, когда я нажимаю один раз то все работает ок, но следующие нажатия не добавляют новый овалов. Так же когда я отпускаю первый палец то овал пропадает и что бы потом получить овал первый раз то тепер нужно будет надать два раза, потом три и так далее. Что я делаю не так?

Вот весь код:

package com.example.lab10

import android.annotation.SuppressLint
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle


import android.content.Context
import android.graphics.Canvas
import android.graphics.Color
import android.graphics.Paint
import android.util.DisplayMetrics
import android.util.Log
import android.view.MotionEvent
import android.view.SurfaceHolder
import android.view.SurfaceView
import android.view.View
import android.view.WindowManager
import androidx.constraintlayout.widget.ConstraintLayout

class TaskSevenNEW : AppCompatActivity() {
    @SuppressLint("ClickableViewAccessibility")
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_task_seven_new)

        title = "Task#7 NEW"

        val layout = findViewById<ConstraintLayout>(R.id.layout_7_NEW)

        var ovalsViews = Array(20) { OvalsView(this) }

        layout.setOnTouchListener(View.OnTouchListener { view, motionEvent ->
            when (motionEvent.getActionMasked()) {
                MotionEvent.ACTION_DOWN, MotionEvent.ACTION_POINTER_DOWN -> {
                    Log.d("touchInfo", "down")

                    val ID: Int = motionEvent.getPointerId(motionEvent.getActionIndex())
                    Log.d("touchInfo", "down ID: " + ID)

                    layout.addView(ovalsViews[ID])
                }
                MotionEvent.ACTION_MOVE -> {
                    Log.d("touchInfo", "move")

                    var idx = 0
                    while (idx < motionEvent.pointerCount) {
                        val ID: Int = motionEvent.getPointerId(idx) // pobranie unikalnego id dla każdego dotyku
                        idx++

                        Log.d("touchInfo", "move ID: " + ID)

                        ovalsViews[ID]._top = motionEvent.getY(ID)
                        ovalsViews[ID]._left = motionEvent.getX(ID)
                    }
                }
                MotionEvent.ACTION_UP, MotionEvent.ACTION_POINTER_UP -> {
                    Log.d("touchInfo", "up")

                    val ID: Int = motionEvent.getPointerId(motionEvent.getActionIndex())
                    Log.d("touchInfo", "up ID: " + ID)

                    layout.removeView(ovalsViews[ID])
                }
                else -> Log.d("touchInfo", "unhandled")
            }
            return@OnTouchListener true
        })

    }

    private class OvalsView(context: Context) : SurfaceView(context), SurfaceHolder.Callback {
        private val mSurfaceHolder: SurfaceHolder 
        private val mPainter = Paint() 
        private var mDrawingThread: Thread? = null 
        private val mDisplay = DisplayMetrics() 
        private var mDisplayWidth: Int 
        private var mDisplayHeight: Int 
        private var mRotation = 0f 

        private var running = true

        var _top: Float = 0f
        var _left: Float = 0f

        init {
            val wm = context.getSystemService(Context.WINDOW_SERVICE) as WindowManager
            wm.defaultDisplay.getMetrics(mDisplay)
            mDisplayWidth = mDisplay.widthPixels
            mDisplayHeight = mDisplay.heightPixels
            mPainter.isAntiAlias = true
            mPainter.color = Color.RED
            mSurfaceHolder = holder
            mSurfaceHolder.addCallback(this)
        }

        private fun animateOvals(): Boolean {
            mRotation += 1
            return true
        }

        private fun drawWheel(canvas: Canvas) {
            canvas.drawColor(Color.WHITE)
//            canvas.rotate(mRotation, mDisplayWidth / 2f, mDisplayHeight / 2f)

            //drawOval(float left, float top, float right, float bottom, @NonNull Paint paint)

//            canvas.drawOval(mDisplayWidth/2f - 100f/2f - 100f, mDisplayHeight/2 + 100f/2f,
//                mDisplayWidth/2f + 100f/2f + 100f, mDisplayHeight/2f - 100/2f, mPainter)

            if (_top > 0f && _left > 0f)
                canvas.drawOval(_left, _top, _left + 200f, _top + 350f, mPainter)
        }

        override fun onSizeChanged(w: Int, h: Int, oldw: Int, oldh: Int) {
            mDisplayWidth = w
            mDisplayHeight = h
            super.onSizeChanged(w, h, oldw, oldh)
        }

        override fun surfaceChanged(holder: SurfaceHolder, format: Int, width: Int, height: Int) {
        }

        override fun surfaceDestroyed(holder: SurfaceHolder) {
            if (mDrawingThread != null) {
                mDrawingThread!!.interrupt()
                running = false
                mDrawingThread!!.join()
                Log.e("qqq", "Thread done")
            }
        }

        override fun surfaceCreated(holder: SurfaceHolder) {

            mDrawingThread = Thread(Runnable {

                var frameStartTime = System.nanoTime();
                var frameTime: Long = 0
                var canvas: Canvas? = null
                while (!Thread.currentThread().isInterrupted && animateOvals() && running) {

                    canvas = mSurfaceHolder.lockCanvas()
                    if (canvas != null) {
                        drawWheel(canvas)
                        mSurfaceHolder.unlockCanvasAndPost(canvas)
                    }


                    frameTime = (System.nanoTime() - frameStartTime) / 1000000
                    if (frameTime < MAX_FRAME_TIME) // faster than the max fps - limit the FPS
                    {
                        try {
                            Thread.sleep(MAX_FRAME_TIME - frameTime)
                        } catch (e: InterruptedException) {
                            // ignore
                        }
                    }
                }
            })
            mDrawingThread!!.start()
        }
    }
}

Ответы (0 шт):