我正在使用android studio创建一个简单的七巧板游戏,我希望用户在android的recyclerview或listView中通过拖放来重新排列单词。但是我不希望用户在能够拖动视图之前先触摸并按住它,我希望视图在用户触摸后立即可拖动。
我在这里遵循了来自github的drag_and_reorder示例代码:https://github.com/trulymittal/RecyclerView/tree/drag_and_reorder 但它要求用户在移动项目之前先触摸并按住视图
公共类PlayGame扩展了AppCompatActivity {
RecyclerView recyclerView;
RecyclerAdapter recyclerAdapter;
List<String> moviesList;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_play_game);
//工具栏工具栏= findViewById(R.id.toolbar); // setSupportActionBar(toolbar);
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE);
recyclerView = (RecyclerView) findViewById(R.id.recyclerView);
moviesList = new ArrayList<>();
moviesList.add("A");
moviesList.add("N");
moviesList.add("A");
moviesList.add("G");
moviesList.add("R");
moviesList.add("A");
moviesList.add("M");
recyclerView = findViewById(R.id.recyclerView);
recyclerAdapter = new RecyclerAdapter(moviesList);
recyclerView.setAdapter(recyclerAdapter);
DividerItemDecoration dividerItemDecoration = new
DividerItemDecoration(this, DividerItemDecoration.VERTICAL);
recyclerView.addItemDecoration(dividerItemDecoration);
ItemTouchHelper itemTouchHelper = new ItemTouchHelper(simpleCallback);
itemTouchHelper.attachToRecyclerView(recyclerView);
}
ItemTouchHelper.SimpleCallback simpleCallback = new
ItemTouchHelper.SimpleCallback(ItemTouchHelper.UP | ItemTouchHelper.DOWN |
ItemTouchHelper.START | ItemTouchHelper.END, 0) {
@Override
public boolean onMove(@NonNull RecyclerView recyclerView, @NonNull
RecyclerView.ViewHolder viewHolder, @NonNull RecyclerView.ViewHolder
target) {
int fromPosition = viewHolder.getAdapterPosition();
int toPosition = target.getAdapterPosition();
Collections.swap(moviesList, fromPosition, toPosition);
recyclerView.getAdapter().notifyItemMoved(fromPosition,
toPosition);
return false;
}
@Override
public void onSwiped(@NonNull RecyclerView.ViewHolder viewHolder, int
direction) {
}
};
}
答案 0 :(得分:0)
当然,这是一个100行代码,位于单个Activity
中并导入,即使使用简单的动画也可以表示所有这些行为。
class MainActivity : AppCompatActivity() {
@Volatile
var state : State = State.INACTIVE
enum class State {
ACTIVE, INACTIVE, HANDLED
}
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
bind()
}
private fun bind() {
addQuestions()
addAnswers()
}
private fun getRandomColor(): Int {
return Color.argb(255, Random.nextInt(255),
Random.nextInt(255), Random.nextInt(255))
}
@SuppressLint("InflateParams")
private fun addQuestions() {
val inflater = getSystemService(
Context.LAYOUT_INFLATER_SERVICE
) as LayoutInflater
for (i in 1..8) {
val view = inflater.inflate(R.layout.item_question, null)
view.findViewById<View>(R.id.questionView)
.setOnDragListener(DragListener())
questionContainer.addView(view)
}
}
@SuppressLint("InflateParams")
private fun addAnswers() {
val inflater = getSystemService(
Context.LAYOUT_INFLATER_SERVICE
) as LayoutInflater
for (i in 1..8) {
val view = inflater.inflate(R.layout.item_answer, null)
(view as ViewGroup).getChildAt(0).setBackgroundColor(getRandomColor())
view.setOnTouchListener(DragItemTouchListener())
answerContainer.addView(view)
}
}
private inner class DragItemTouchListener : OnTouchListener {
val ITEM_INDEX_D = "Index-From"
override fun onTouch(view: View, motionEvent: MotionEvent): Boolean {
return if (motionEvent.action == MotionEvent.ACTION_DOWN) {
createDrag(view)
true
} else {
false
}
}
private fun createDrag(view : View) {
val parent = view.parent as ViewGroup
view.tag = Pair(ITEM_INDEX_D,
parent.indexOfChild(view))
view.startDragAndDrop(ClipData.newPlainText("", ""),
DragShadowBuilder(view), view, 0)
parent.removeView(view)
parent.setBackgroundColor(Color.WHITE)
}
}
private inner class DragListener : OnDragListener {
override fun onDrag(parent: View, event: DragEvent): Boolean {
val view = event.localState as View
when (event.action) {
DragEvent.ACTION_DRAG_STARTED -> {
state = State.ACTIVE
}
DragEvent.ACTION_DRAG_ENTERED -> {
}
DragEvent.ACTION_DRAG_EXITED -> {
}
DragEvent.ACTION_DROP -> {
state = State.HANDLED
animateDropEffect(parent, view)
return true
}
DragEvent.ACTION_DRAG_ENDED -> {
if (state == State.ACTIVE) {
state = State.INACTIVE
animateMoveBack(view,
(view.tag as Pair<*, *>).second as Int)
}
return true
}
else -> {
}
}
return true
}
private fun animateMoveBack(view: View, index : Int) {
answerContainer.addView(view, index)
}
private fun animateDropEffect(into: View, view: View) {
val parent = (into.parent as ViewGroup)
parent.addView(view)
val params = (view.layoutParams as FrameLayout.LayoutParams)
.apply {
gravity = Gravity.END
}
view.layoutParams = params
checkIsCorrect(parent)
}
private fun checkIsCorrect(parent : ViewGroup) {
val correct = Random.nextBoolean()
val colorFrom = Color.WHITE
val colorTo : Int = if (correct) 0x8000ff00.toInt() else 0x80ff0000.toInt()
ObjectAnimator.ofObject(
parent,
"backgroundColor",
ArgbEvaluator(),
colorFrom,
colorTo
)
.setDuration(1000)
.start()
}
}
}
所有使用的Xml。在xml下方的以下所有示例。
/* activity_main.xml */
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout
android:id="@+id/mainContainer"
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
tools:context=".MainActivity">
<ScrollView
android:layout_width="match_parent"
android:layout_height="500dp"
android:animateLayoutChanges="true">
<LinearLayout
android:id="@+id/questionContainer"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:animateLayoutChanges="true"
android:orientation="vertical">
</LinearLayout>
</ScrollView>
<HorizontalScrollView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:animateLayoutChanges="true">
<LinearLayout
android:id="@+id/answerContainer"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:animateLayoutChanges="true"
android:orientation="horizontal">
</LinearLayout>
</HorizontalScrollView>
</LinearLayout>
</FrameLayout>
/* item_question.xml */
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:animateLayoutChanges="true"
android:padding="5dp">
<View
android:layout_width="100dp"
android:layout_height="100dp"
android:layout_gravity="start"
android:background="@android:color/holo_blue_bright">
</View>
<View
android:id="@+id/questionView"
android:layout_width="100dp"
android:layout_height="100dp"
android:layout_gravity="end"
android:background="@android:color/holo_orange_light">
</View>
</FrameLayout>
/* item_answer.xml */
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="vertical"
android:padding="5dp"
android:tag="Test">
<LinearLayout
android:layout_width="100dp"
android:layout_height="100dp"
android:layout_gravity="center"
android:background="@android:color/darker_gray">
</LinearLayout>
</FrameLayout>