Skip to content

Commit

Permalink
update long click logic
Browse files Browse the repository at this point in the history
  • Loading branch information
goyourfly committed Jul 20, 2017
1 parent 398335c commit b2ff408
Show file tree
Hide file tree
Showing 4 changed files with 167 additions and 5 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,7 @@ class MainActivity : AppCompatActivity() {
.with(this)
.adapter(demoAdapter)
.decorateFactory(CheckBoxFactory(color = resources.getColor(R.color.colorPrimary)))
.ignoreViewType(arrayOf(demoAdapter.TYPE_SECTION))
.linkList(demoAdapter.list)
.customMenu(SimpleDeleteSelectAllMenuBar(this, resources.getColor(R.color.colorPrimary)))
.build()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,21 +2,32 @@ package com.goyourfly.multiple.adapter.viewholder

import android.os.Handler
import android.support.v7.widget.RecyclerView
import android.util.Log
import android.view.MotionEvent
import android.view.View
import android.view.ViewGroup
import com.goyourfly.multiple.adapter.MultipleAdapter
import com.goyourfly.multiple.adapter.ViewState

/**
* Created by gaoyufei on 2017/6/8.
*/
abstract class BaseViewHolder(val view: View,
abstract class BaseViewHolder(val root: View,
val viewHolder: RecyclerView.ViewHolder,
val adapter: MultipleAdapter) : RecyclerView.ViewHolder(view) {
val adapter: MultipleAdapter) : RecyclerView.ViewHolder(InterceptFrameLayout(root.context,adapter,root)) {

val onTouchListener = OnTouchListener(adapter,this)
init {
viewHolder.itemView.setOnTouchListener(onTouchListener)
// viewHolder.itemView.setOnTouchListener(onTouchListener)
if(itemView is InterceptFrameLayout){
itemView.setLongClickCallback {
Log.d("...","onLongClickCallback")
adapter.onItemLongClick(viewHolder.adapterPosition)
}
itemView.setSelectStateClickCallback {
adapter.onItemClick(viewHolder.adapterPosition)
}
}
}

abstract fun selectStateChanged(state: Int)
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,150 @@
package com.goyourfly.multiple.adapter.viewholder

import android.content.Context
import android.support.v4.view.MotionEventCompat
import android.util.Log
import android.view.MotionEvent
import android.view.View
import android.widget.FrameLayout
import com.goyourfly.multiple.adapter.MultipleAdapter
import com.goyourfly.multiple.adapter.ViewState

/**
* Created by gaoyufei on 2017/7/20.
*/

class InterceptFrameLayout(context: Context, val adapter: MultipleAdapter, child: View) : FrameLayout(context) {
val CLICK_ACTION_THRESHHOLD = 20
val CLICK_LONG_TIME = 500L

var startX = 0F
var startY = 0F
var moveX = 0F
var moveY = 0F
var downTime = 0L
var isTouching = false
var isLongClick = false
var touchDownTime = 0L

private var onLongClicked: (() -> Unit)? = null
private var onClick: (() -> Unit)? = null

val run = Runnable {
if (isTouching && !isLongClick && isAClick()) {
// 制作一个假的事件
val event = MotionEvent.obtain(
downTime,
System.currentTimeMillis(),
MotionEvent.ACTION_MOVE,
moveX,
moveY,
0)
isLongClick = true
onTouchEvent(event)
}
}

init {
val childParams = child.layoutParams
val params =
if (childParams != null)
LayoutParams(childParams)
else
LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT)
layoutParams = params
addView(child)
}

override fun onInterceptTouchEvent(ev: MotionEvent): Boolean {
Log.d("...", "onIntercept:$ev")
val action = MotionEventCompat.getActionMasked(ev)
when (action) {
MotionEvent.ACTION_DOWN -> {
isLongClick = false
isTouching = true
startX = ev.x
startY = ev.y
moveX = ev.x
moveY = ev.y
downTime = System.currentTimeMillis()
handler.postDelayed(run, CLICK_LONG_TIME)
}
MotionEvent.ACTION_MOVE -> {
moveX = ev.x
moveY = ev.y
if (isInterceptLong() && isAClick()) {
isLongClick = true
}
}
MotionEvent.ACTION_UP, MotionEvent.ACTION_CANCEL -> {
isTouching = false
handler.removeCallbacks(run)
}
}
return isLongClick || adapter.showState == ViewState.SELECT
}


override fun onTouchEvent(ev: MotionEvent): Boolean {
val action = MotionEventCompat.getActionMasked(ev)
Log.d("...", "onTouch:$ev")
if (isTouching
&& isLongClick
&& action != MotionEvent.ACTION_CANCEL) {
handler.removeCallbacks(run)
handler.post {
onLongClicked?.invoke()
}
return true
}
when (action) {
MotionEvent.ACTION_DOWN -> {
isTouching = true
startX = ev.x
startY = ev.y
moveX = ev.x
moveY = ev.y
touchDownTime = System.currentTimeMillis()
}
MotionEvent.ACTION_MOVE -> {
moveX = ev.x
moveY = ev.y
}
MotionEvent.ACTION_UP -> {
isTouching = false
handler.removeCallbacks(run)
if (adapter.showState == ViewState.SELECT
&& !isTouchLong()
&& isAClick()) {
onClick?.invoke()
}
}
MotionEvent.ACTION_CANCEL -> {
isTouching = false
handler.removeCallbacks(run)
}
}
return true
}


fun setLongClickCallback(callback: () -> Unit): Unit {
onLongClicked = callback
}

fun setSelectStateClickCallback(callback: () -> Unit): Unit {
onClick = callback
}

private fun isInterceptLong() = System.currentTimeMillis() - downTime > CLICK_LONG_TIME
private fun isTouchLong() = System.currentTimeMillis() - touchDownTime > CLICK_LONG_TIME

private fun isAClick(): Boolean {
val differenceX = Math.abs(startX - moveX)
val differenceY = Math.abs(startY - moveY)
if (differenceX > CLICK_ACTION_THRESHHOLD/* =5 */ || differenceY > CLICK_ACTION_THRESHHOLD) {
return false
}
return true
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -12,13 +12,13 @@ import com.goyourfly.multiple.adapter.viewholder.BaseViewHolder
/**
* Created by gaoyufei on 2017/6/8.
*/
class CustomViewHolder(view: View,
class CustomViewHolder(root: View,
viewHolder: RecyclerView.ViewHolder,
adapter: MultipleAdapter,
val animationInterface: AnimationInterface,
val selectViewContainer: View,
val selectView: View,
val unSelectView: View) : BaseViewHolder(view, viewHolder, adapter) {
val unSelectView: View) : BaseViewHolder(root, viewHolder, adapter) {
init {
selectView.setOnTouchListener(onTouchListener)
unSelectView.setOnTouchListener(onTouchListener)
Expand Down

0 comments on commit b2ff408

Please sign in to comment.