Android中的拖放+自定义绘图

Posted

技术标签:

【中文标题】Android中的拖放+自定义绘图【英文标题】:Drag and drop + custom drawing in Android 【发布时间】:2011-02-05 21:16:45 【问题描述】:

我正在做一些需要自定义拖放功能的事情,所以我一直在继承 View,对触摸事件进行大量数学运算,然后通过 onDraw 中的画布上的代码手动渲染所有内容。现在,我添加的功能越多,代码就越失控,我发现自己编写的代码比在 android 等高级环境中编写的代码要多得多。

这是如何完成的,还是我遗漏了什么?如果我没有在 UI 中做任何花哨的事情,框架会处理我的大部分交互。内置控件处理触摸和拖动,我的代码几乎仅限于业务逻辑和数据。有没有一种方法可以利用一些 UI 控件和动画之类的功能,同时在 onDraw 画布中手动执行一些操作?何时使用其中一种方法是否有公认的标准(如果这两种方法确实可以混合使用)?

【问题讨论】:

在我的游戏中,当处理几乎任何类型的动画和自定义触摸界面时,我当然必须编写大量代码、数学、检查等。也许有更简单的方法,但不得不做那种事情似乎并不罕见。 酷...感谢反馈。我在想我可以通过使用 ViewGroup 并将自定义绘制的视图与其他标准元素混合来做时髦的混合东西,但是当我已经有一点动力时,我真的不想花时间玩这些东西走很长的路。 【参考方案1】:

我在我的音乐播放器应用程序中使用拖放功能!我让用户能够将歌曲从播放列表移动到另一个播放列表。这对用户来说非常好和简单。当用户长按歌曲或选择菜单中的选项时,我会为我的视图启动拖动事件! 这是我的课:

package com.liviu.app.smpp.gui;

import android.content.Context;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.MotionEvent;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.RelativeLayout;
import android.widget.TextView;

import com.liviu.app.smpp.R;
import com.liviu.app.smpp.listeners.CollisionListener;

public class SongItemView extends RelativeLayout implements OnClickListener 
// data
private String TAG = "SongItemView";
private Context context;
private LayoutInflater lInflater;   
private String title;
private int id;
private int maxHeight = 410;
private int mCurX;
private int mCurY;

//listeners
private CollisionListener onCollisionListener = null;

// views
private View v;

public SongItemView(Context ctx, String title_, int id_) 
    super(ctx);

    context   = ctx;
    lInflater = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
    v         = lInflater.inflate(R.layout.song_item_view, null);
    title     = title_;
    id        = id_;

    ((TextView)v.findViewById(R.id.siv_title)).setText(title);      

    addView(v, new RelativeLayout.LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT));


@Override
public void onClick(View v) 
    Log.e(TAG, "clicked! " + ((TextView)v.findViewById(R.id.piv_title)).getText().toString());


public View getView()
    return v;


public String getPlsName() 
    return title;


public int getID() 
    return id;


public void setTitle(String title_)
    ((TextView)v.findViewById(R.id.siv_title)).setText(title_);
    title = title_;


public void setID(int id_) 
    id = id_;   


@Override
public boolean dispatchTouchEvent(MotionEvent event) 
    mCurX = (int) event.getRawX();
    mCurY = (int) event.getRawY();

    int action = event.getAction();         

    if (action == MotionEvent.ACTION_MOVE) 
           
        RelativeLayout.LayoutParams params = new RelativeLayout.LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);                     
        params.leftMargin = mCurX;
        params.topMargin  = mCurY;
        this.setLayoutParams(params);

        if(this.getTop() >= maxHeight)
        
            Log.e(TAG, "Collision!!!!");
            if(onCollisionListener != null)
                    onCollisionListener.onCollision(this);                  
            
                           
    

    return true;


public void setOnCollisionListener(CollisionListener listener)
    onCollisionListener = listener;


public void setMaxHeight(int height)
    maxHeight = height;


public int getmCurX() 
    return mCurX;


public int getmCurY() 
    return mCurY;


public int getMaxHeight() 
    return maxHeight;

我希望这会有所帮助。

谢谢!

【讨论】:

我喜欢这个主意。我将尝试通过在我的视图顶部创建一个RelativeLayout 来实现拖放,然后拦截longtouch 并移动。我想这也是你在这里所做的。灵感的好主意!

以上是关于Android中的拖放+自定义绘图的主要内容,如果未能解决你的问题,请参考以下文章

WinAppDriver中的拖放不起作用

nstableview 拖放与自定义单元格视图

Qt学习之路(54): 自定义拖放数据对象

自定义导航器中的拖拽定义

Android自定义视图绘图

JPanel 中的 Java 自定义拖放