关注 安卓007 ,免费获取全套安卓开发学习资料
支持对任何视图进行包裹后3D翻转.
class ThreeDLayout(context: Context?, attrs: AttributeSet? = null) : ViewGroup(context, attrs) {private val mCamera: Cameraprivate val mMatrix: Matrix//this viewgroup's centerprivate var mCenterX = 0private var mCenterY = 0//rotateDegreeprivate var mCanvasRotateY = 0fprivate var mCanvasRotateX = 0fprivate var mCanvasMaxRotateDegree = 50fprivate var mMode = MODE_BOTH_X_Yprivate val mDensity: Floatprivate val mValues = FloatArray(9)//the flag of touchprivate var isCanTouch = false//the degree of animationprivate var mDegreeY = 0fprivate var mDegreeX = 0f//the flag of animateprivate var isPlaying = false//the degree of longer animateprivate var mLoopAnimateY = 0override fun onMeasure(widthMeasureSpec: Int, heightMeasureSpec: Int) {check(childCount == 1) { "ThreeDLayout can only have one child" }val child = getChildAt(0)measureChild(child, widthMeasureSpec, heightMeasureSpec)//only one child view,so give the same asuredWidth, asuredHeight)}override fun onLayout(changed: Boolean,l: Int,t: Int,r: Int,b: Int) {val child = getChildAt(0)child.layout(0, 0, asuredWidth, asuredHeight)}override fun onSizeChanged(w: Int, h: Int, oldw: Int, oldh: Int) {SizeChanged(w, h, oldw, oldh)mCenterX = w / 2mCenterY = h / 2}override fun onDraw(canvas: Canvas) {set()mCamera.save()if (mMode == MODE_Y || mMode == MODE_BOTH_X_Y) {ateX(mCanvasRotateX)}if (mMode == MODE_X || mMode == MODE_BOTH_X_Y) {ateY(mCanvasRotateY)}ateY(ateX(mDegreeX)if (isPlaying) {ateY(mLoopAnimateY++.toFloat())if (mLoopAnimateY == 360) {mLoopAnimateY = 0}invalidate()}Matrix(mMatrix)// fix the Camera Values(mValues)mValues[6] = mValues[6] / mDensitymValues[7] = mValues[7] / mDensitymMatrix.setValues(store()mMatrix.preTranslate(-Float(), -Float())mMatrix.Float(), Float())at(Draw(canvas)}override fun onInterceptTouchEvent(ev: MotionEvent): Boolean {return if (isCanTouch) {true} else {InterceptTouchEvent(ev)}}override fun onTouchEvent(event: MotionEvent): Boolean {return if (isCanTouch) {val x = event.xval y = event.ywhen (event.action) {MotionEvent.ACTION_MOVE -> {rotateCanvasWhenMove(x, y)invalidate()return true}MotionEvent.ACTION_UP -> {mDegreeY = Float(), Float())invalidate()return true}}true} else {TouchEvent(event)}}/*** get the value to rotate*/private fun rotateCanvasWhenMove(x: Float, y: Float) {val dx = x - mCenterXval dy = y - mCenterYvar percentX = dx / mCenterXvar percentY = dy / mCenterYif (percentX > 1f) {percentX = 1f} else if (percentX < -1f) {percentX = -1f}if (percentY > 1f) {percentY = 1f} else if (percentY < -1f) {percentY = -1f}mCanvasRotateY = mCanvasMaxRotateDegree * percentXmCanvasRotateX = -(mCanvasMaxRotateDegree * percentY)}fun setTouchable(canTouch: Boolean) {isCanTouch = canTouch}fun setTouchMode(mode: Int) {mMode = modeisCanTouch = true}/*** set the max rotate degree*/fun setMaxRotateDegree(degree: Int) {mCanvasMaxRotateDegree = Float()}/*** start horizontal turn animate*/fun startHorizontalAnimate(duration: Long) {val animator = ValueAnimator.ofFloat(-180f, 0f)animator.addUpdateListener { animation ->mDegreeY = animation.animatedValue as Floatinvalidate()}animator.addListener(object : Animator.AnimatorListener {override fun onAnimationStart(animation: Animator) {}override fun onAnimationEnd(animation: Animator) {mDegreeY = veAllUpdateListeners()}override fun onAnimationCancel(animation: Animator) {}override fun onAnimationRepeat(animation: Animator) {}})animator.duration = durationanimator.start()}/*** start horizontal turn animate delayed*/fun startHorizontalAnimateDelayed(delayed: Long, duration: Long) {Thread(Runnable {try {Thread.sleep(delayed)} catch (e: InterruptedException) {e.printStackTrace()}post { startHorizontalAnimate(duration) }}).start()}/*** start vertical turn animate*/fun startVerticalAnimate(duration: Long) {val animator = ValueAnimator.ofFloat(-180f, 0f)animator.addUpdateListener { animation ->mDegreeX = animation.animatedValue as Floatinvalidate()}animator.addListener(object : Animator.AnimatorListener {override fun onAnimationStart(animation: Animator) {}override fun onAnimationEnd(animation: Animator) {mDegreeX = veAllUpdateListeners()}override fun onAnimationCancel(animation: Animator) {}override fun onAnimationRepeat(animation: Animator) {}})animator.duration = durationanimator.start()}/*** start vertical turn animate delayed*/fun startVerticalAnimateDelayed(delayed: Long, duration: Long) {Thread(Runnable {try {Thread.sleep(delayed)} catch (e: InterruptedException) {e.printStackTrace()}post { startVerticalAnimate(duration) }}).start()}/*** start loop animate*/fun startHorizontalAnimate() {isPlaying = trueinvalidate()}/*** stop the loop animate*/fun stopAnimate() {isPlaying = falsemLoopAnimateY = 0invalidate()}companion object {//the touch modevar MODE_X = 0var MODE_Y = 1var MODE_BOTH_X_Y = 2}init {//set a default background to make sure onDraw() dispatchif (background == null) {setBackgroundColor(Color.parseColor("#ffffff"))}var dm = DisplayMetrics()dm = resources.displayMetricsmDensity = dm.densitymCamera = Camera()mMatrix = Matrix()}
}
关注头条号,第一时间获取最新文章:
本文发布于:2024-01-29 02:02:39,感谢您对本站的认可!
本文链接:https://www.4u4v.net/it/170646496011927.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
留言与评论(共有 0 条评论) |