带滑动删除的Dummynote

介绍:首先这个应用是结合了我之前做的Dummynote,那个note的删除主要靠的是长按后的ContextMenu

	public void onCreateContextMenu(ContextMenu menu, View v, ContextMenuInfo menuInfo) {
		menu.add(0, MENU_DELETE, 0, "删除记事");
		menu.setHeaderTitle("要如何处理这笔记录?");
		super.onCreateContextMenu(menu, v, menuInfo);
	}

这样做不算差。但是如果可以实现滑动删除的话,效果会更好。于是我借鉴了这篇文章http://blog.csdn.net/xiaanming/article/details/18311877

文章很详细,注释也很多。他一步步告诉你滑动删除具体是怎么实现的。

难点:

问题一、当用户要删除某一行时,我只能得到该行的行号,但不知道该行在数据库中的_id值是多少?

我因此使用了带 limit 和 offest 的语句

db.delete(DATABASE_TABLE,ROWID+"="+rowId,null);

改成了

db.execSQL("delete from tids where _id in(select _id from tids limit 1 offset "+rowId+");"); //是从数据库中的第rowId+1条数据开始查询一条数据,即第rouId+1条

知识:

取前十行

select user_id from udb_user  limit 10; 

跳过前10行,再取前15行

select user_id from udb_user  limit 10,15; 

跳过前15行,再取前10行

select user_id from udb_user  limit 10 offest 15; 

不多说,代码奉上。

Healthyids

package demo.xpf.healthytids;

import android.content.Intent;
import android.os.Bundle;
import android.app.Activity;
import android.content.Intent;
import android.database.Cursor;
import android.support.v4.widget.SimpleCursorAdapter;
import android.text.StaticLayout;
import android.util.Log;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.widget.AdapterView;
import android.widget.Toast;
import android.widget.AdapterView.OnItemClickListener;
import demo.xpf.healthytids.SwipeDismissListView.OnDismissCallback;

public class Healthytids extends Activity {
	private static final String TAG = "tids";
	private SwipeDismissListView swipeDismissListView;
	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.main);
		//getListView().setEmptyView(findViewById(R.id.empty));//设置列表为空时的显示内容为 empty文本框
		setAdapter();
		init();
	}

	private TidsDbAdapter mDbHelper ;
	private Cursor mTidCursor;

	private void setAdapter(){
		mDbHelper = new TidsDbAdapter(this);
		mDbHelper.open();
		fillData();
	}
	//fillData()刷新数据
	private void fillData(){
		mTidCursor = mDbHelper.getall();
		Log.d(TAG, "filldata  "+mTidCursor);
		startManagingCursor(mTidCursor);

		String[] from = new String[]{TidsDbAdapter.NOTE};
		int[] to = new int[]{android.R.id.text1};//android.R.id.text1是Android 框架里面的TextView的一个标识符

		//Now create a simple cursor adapter
		SimpleCursorAdapter adapter =
				new SimpleCursorAdapter(this, android.R.layout.simple_list_item_1, mTidCursor, from, to);
		swipeDismissListView = (SwipeDismissListView) findViewById(R.id.swipeDismissListView);
		swipeDismissListView.setAdapter(adapter);
	}

	private void init() {
		swipeDismissListView.setOnDismissCallback(new OnDismissCallback() {

			@Override
			public void onDismiss(int dismissPosition) {
				//adapter.remove(adapter.getItem(dismissPosition));
				boolean T=mDbHelper.delete(dismissPosition);
				Log.d(TAG, "delete"+dismissPosition+"    "+T);
				fillData();
			}
		});

		swipeDismissListView.setOnItemClickListener(new OnItemClickListener() {
			private static final int ACTIVITY_EDIT = 0x1001;
			public void onItemClick(AdapterView<?> parent, View view,int position, long id) {
				Intent intent = new Intent(Healthytids.this, NoteEdit.class);
				intent.putExtra(TidsDbAdapter.ROWID, id);//id就是_id值,不是当前的列表项值。代表绑定到这个“ListView”项目的“row ID”
			    startActivityForResult(intent, ACTIVITY_EDIT);
			}
		});

	}
	//Add an entity
		protected static final int MENU_INSERT = Menu.FIRST;
		@Override
		public boolean onCreateOptionsMenu(Menu menu) {
			// Inflate the menu; this adds items to the action bar if it is present.
			 super.onCreateOptionsMenu(menu);
			 menu.add(0, MENU_INSERT, 0, "新增记事");
			 return super.onCreateOptionsMenu(menu);
		}
		public boolean onOptionsItemSelected(MenuItem item){
			switch(item.getItemId()){
			case MENU_INSERT:
				String noteName = "New Note ";
				mDbHelper.create(noteName);
				fillData();
				return true;
			}
			return super.onOptionsItemSelected(item);
		}

}

SwipeDismissListView

package demo.xpf.healthytids;

import static com.nineoldandroids.view.ViewHelper.setAlpha;
import static com.nineoldandroids.view.ViewHelper.setTranslationX;
import android.content.Context;
import android.util.AttributeSet;
import android.view.MotionEvent;
import android.view.VelocityTracker;
import android.view.View;
import android.view.ViewConfiguration;
import android.view.ViewGroup;
import android.widget.AdapterView;
import android.widget.ListView;

import com.nineoldandroids.animation.Animator;
import com.nineoldandroids.animation.AnimatorListenerAdapter;
import com.nineoldandroids.animation.ValueAnimator;
import com.nineoldandroids.view.ViewHelper;
import com.nineoldandroids.view.ViewPropertyAnimator;
/**
 * @blog http://blog.csdn.net/xiaanming
 *
 * @author xiaanming
 *
 */
@SuppressWarnings("unused")
public class SwipeDismissListView extends ListView  {
	/**
	 * 认为是用户滑动的最小距离
	 */
	private int mSlop;
	/**
	 * 滑动的最小速度
	 */
	private int mMinFlingVelocity;
	/**
	 * 滑动的最大速度
	 */
	private int mMaxFlingVelocity;
	/**
	 * 执行动画的时间
	 */
	protected long mAnimationTime = 150;
	/**
	 * 用来标记用户是否正在滑动中
	 */
	private boolean mSwiping;
	/**
	 * 滑动速度检测类
	 */
	private VelocityTracker mVelocityTracker;
	/**
	 * 手指按下的position
	 */
	private int mDownPosition;
	/**
	 * 按下的item对应的View
	 */
	private View mDownView;
	private float mDownX;
	private float mDownY;
	/**
	 * item的宽度
	 */
	private int mViewWidth;
	/**
	 * 当ListView的Item滑出界面回调的接口
	 */
	private OnDismissCallback onDismissCallback;

	/**
	 * 设置动画时间
	 *
	 * @param mAnimationTime
	 */
	public void setmAnimationTime(long mAnimationTime) {
		this.mAnimationTime = mAnimationTime;
	}

	/**
	 * 设置删除回调接口
	 *
	 * @param onDismissCallback
	 */
	public void setOnDismissCallback(OnDismissCallback onDismissCallback) {
		this.onDismissCallback = onDismissCallback;
	}

	public SwipeDismissListView(Context context) {
		this(context, null);
	}

	public SwipeDismissListView(Context context, AttributeSet attrs) {
		this(context, attrs, 0);
	}

	public SwipeDismissListView(Context context, AttributeSet attrs,
			int defStyle) {
		super(context, attrs, defStyle);

		ViewConfiguration vc = ViewConfiguration.get(context);
		mSlop = vc.getScaledTouchSlop();
		mMinFlingVelocity = vc.getScaledMinimumFlingVelocity() * 8; //获取滑动的最小速度
		mMaxFlingVelocity = vc.getScaledMaximumFlingVelocity();  //获取滑动的最大速度
	}

	@Override
	public boolean onTouchEvent(MotionEvent ev) {
		switch (ev.getAction()) {
		case MotionEvent.ACTION_DOWN:
			handleActionDown(ev);
			break;
		case MotionEvent.ACTION_MOVE:
			return handleActionMove(ev);
		case MotionEvent.ACTION_UP:
			handleActionUp(ev);
			break;
		}
		return super.onTouchEvent(ev);
	}

	/**
	 * 按下事件处理
	 *
	 * @param ev
	 * @return
	 */
	private void handleActionDown(MotionEvent ev) {
		mDownX = ev.getX();
		mDownY = ev.getY();

		mDownPosition = pointToPosition((int) mDownX, (int) mDownY);

		if (mDownPosition == AdapterView.INVALID_POSITION) {
			return;
		}

		mDownView = getChildAt(mDownPosition - getFirstVisiblePosition());

		if (mDownView != null) {
			mViewWidth = mDownView.getWidth();
		}

		//加入速度检测
		mVelocityTracker = VelocityTracker.obtain();
		mVelocityTracker.addMovement(ev);
	}

	/**
	 * 处理手指滑动的方法
	 *
	 * @param ev
	 * @return
	 */
	private boolean handleActionMove(MotionEvent ev) {
		if (mVelocityTracker == null || mDownView == null) {
			return super.onTouchEvent(ev);
		}

		// 获取X方向滑动的距离
		float deltaX = ev.getX() - mDownX;
		float deltaY = ev.getY() - mDownY;

		// X方向滑动的距离大于mSlop并且Y方向滑动的距离小于mSlop,表示可以滑动
		if (Math.abs(deltaX) > mSlop && Math.abs(deltaY) < mSlop) {
			mSwiping = true;

			//当手指滑动item,取消item的点击事件,不然我们滑动Item也伴随着item点击事件的发生
			MotionEvent cancelEvent = MotionEvent.obtain(ev);
            cancelEvent.setAction(MotionEvent.ACTION_CANCEL |
                       (ev.getActionIndex()<< MotionEvent.ACTION_POINTER_INDEX_SHIFT));
            onTouchEvent(cancelEvent);
		}

		if (mSwiping) {
			// 跟谁手指移动item
			ViewHelper.setTranslationX(mDownView, deltaX);
			// 透明度渐变
			ViewHelper.setAlpha(mDownView, Math.max(0f, Math.min(1f, 1f - 2f * Math.abs(deltaX)/ mViewWidth)));

			// 手指滑动的时候,返回true,表示SwipeDismissListView自己处理onTouchEvent,其他的就交给父类来处理
			return true;
		}

		return super.onTouchEvent(ev);

	}

	/**
	 * 手指抬起的事件处理
	 * @param ev
	 */
	private void handleActionUp(MotionEvent ev) {
		if (mVelocityTracker == null || mDownView == null|| !mSwiping) {
			return;
		}

		float deltaX = ev.getX() - mDownX;

		//通过滑动的距离计算出X,Y方向的速度
		mVelocityTracker.computeCurrentVelocity(1000);
		float velocityX = Math.abs(mVelocityTracker.getXVelocity());
		float velocityY = Math.abs(mVelocityTracker.getYVelocity());

		boolean dismiss = false; //item是否要滑出屏幕
		boolean dismissRight = false;//是否往右边删除

		//当拖动item的距离大于item的一半,item滑出屏幕
		if (Math.abs(deltaX) > mViewWidth / 2) {
			dismiss = true;
			dismissRight = deltaX > 0;

			//手指在屏幕滑动的速度在某个范围内,也使得item滑出屏幕
		} else if (mMinFlingVelocity <= velocityX
				&& velocityX <= mMaxFlingVelocity && velocityY < velocityX) {
			dismiss = true;
			dismissRight = mVelocityTracker.getXVelocity() > 0;
		}

		if (dismiss) {
			ViewPropertyAnimator.animate(mDownView)
					.translationX(dismissRight ? mViewWidth : -mViewWidth)//X轴方向的移动距离
					.alpha(0)
					.setDuration(mAnimationTime)
					.setListener(new AnimatorListenerAdapter() {
						@Override
						public void onAnimationEnd(Animator animation) {
							//Item滑出界面之后执行删除
							performDismiss(mDownView, mDownPosition);
						}
					});
		} else {
			//将item滑动至开始位置
			ViewPropertyAnimator.animate(mDownView)
			.translationX(0)
			.alpha(1)
			.setDuration(mAnimationTime).setListener(null);
		}

		//移除速度检测
		if(mVelocityTracker != null){
			mVelocityTracker.recycle();
			mVelocityTracker = null;
		}

		mSwiping = false;
	}

	/**
	 * 在此方法中执行item删除之后,其他的item向上或者向下滚动的动画,并且将position回调到方法onDismiss()中
	 * @param dismissView
	 * @param dismissPosition
	 */
	private void performDismiss(final View dismissView, final int dismissPosition) {
		final ViewGroup.LayoutParams lp = dismissView.getLayoutParams();//获取item的布局参数
		final int originalHeight = dismissView.getHeight();//item的高度

		ValueAnimator animator = ValueAnimator.ofInt(originalHeight, 0).setDuration(mAnimationTime);
		animator.start();

		animator.addListener(new AnimatorListenerAdapter() {
			@Override
			public void onAnimationEnd(Animator animation) {
				if (onDismissCallback != null) {
					onDismissCallback.onDismiss(dismissPosition);
				}

				//这段代码很重要,因为我们并没有将item从ListView中移除,而是将item的高度设置为0
				//所以我们在动画执行完毕之后将item设置回来
				ViewHelper.setAlpha(dismissView, 1f);
				ViewHelper.setTranslationX(dismissView, 0);
				ViewGroup.LayoutParams lp = dismissView.getLayoutParams();
				lp.height = originalHeight;
				dismissView.setLayoutParams(lp);

			}
		});

		animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
			@Override
			public void onAnimationUpdate(ValueAnimator valueAnimator) {
				//这段代码的效果是ListView删除某item之后,其他的item向上滑动的效果
				lp.height = (Integer) valueAnimator.getAnimatedValue();
				dismissView.setLayoutParams(lp);
			}
		});

	}

	/**
	 * 删除的回调接口
	 *
	 * @author xiaanming
	 *
	 */
	public interface OnDismissCallback {
		public void onDismiss(int dismissPosition);
	}

}

TidsDbAdapter

package demo.xpf.healthytids;

import java.util.Date;

import android.content.ContentValues;
import android.content.Context;
import android.database.SQLException;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import android.database.*;
import android.util.Log;
public class TidsDbAdapter {
	private static final String TAG = "tids";

	private static final String DATABASE_NAME = "tids.db";
	private static final int DATABASE_VERSION = 1 ;
	private static final String DATABASE_TABLE = "tids";
	private static final String DATABASE_CREATE =
			"create table tids("
			+"_id INTEGER PRIMARY KEY,"
			+"note TEXT NOT NULL,"
			+"created INTEGER"
			+");";

	private static class DatabaseHelper extends SQLiteOpenHelper{
		public DatabaseHelper(Context context) {
			super(context, DATABASE_NAME,null,DATABASE_VERSION);
			// TODO Auto-generated constructor stub
		}

		@Override//创建数据表
		public void onCreate(SQLiteDatabase db) {
			// TODO Auto-generated method stub
			try {
				db.execSQL(DATABASE_CREATE);
				Log.d(TAG, "onCreate !");
			} catch (Exception e) {
				Log.d(TAG, e.toString());
			}
		}

		@Override//更新数据表
		public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {

			try {
				// TODO Auto-generated method stub
				db.execSQL("DROP TABLE IF EXISTS "+DATABASE_TABLE);
				onCreate(db);
				Log.d(TAG, "inUpgrade!");
			} catch (Exception e) {
				Log.d(TAG, "onUpgrade failure!");
			}
		}
}

	private Context mCtx = null;	 //抽象界面
	private DatabaseHelper dbHelper; //数据库工具类
	private SQLiteDatabase db;		 //数据库类
	/** COnstructor**/
	public TidsDbAdapter(Context ctx){
		this.mCtx=ctx;
	}

	public TidsDbAdapter open () throws SQLException{
		dbHelper = new DatabaseHelper(mCtx);
		db = dbHelper.getWritableDatabase();//数据库不存在就创造一个,若存在就根据版本库来决定是否更新数据库

		return this;
	}

	public void close(){
		dbHelper.close();
	}

	public static final String  ROWID = "_id";
	public static final String  NOTE = "note";
	public static final String  CREATED = "created";

	//query single entry
		public Cursor get(long rowId)throws SQLException {
			Cursor mCursor = db.query(DATABASE_TABLE,//Which table to select
						new String[]{ROWID,NOTE,CREATED},//Which columns to return
						ROWID+"="+rowId,   //Where clause
						null,   //Where arguments
						null,   //Group By clause
						null,   //Having clause
						null    //Order-by clause
						);
			if(mCursor!=null){
				mCursor.moveToFirst();//指针移到一开始
			}
			return mCursor;
		}

	//query single entry
	public Cursor getall() {
		return db.query(DATABASE_TABLE,//Which table to select
					new String[]{ROWID,NOTE,CREATED},//Which columns to return
					null,   //Where clause
					null,   //Where arguments
					null,   //Group By clause
					null,   //Having clause
					null    //Order-by clause
					);
	}

	//add an entity
	public long create(String Note){
		Date now = new Date();
		ContentValues args = new ContentValues();
		args.put(NOTE, Note);
		args.put(CREATED, now.getDate());

		return db.insert(DATABASE_TABLE, null, args);
	}

	//remove an entity
	public boolean delete(long rowId){
		Log.d(TAG, "delete func"+rowId);
		 db.execSQL("delete from tids where _id in(select _id from tids  limit 1 offset "+rowId+");");
		 //是从数据库中的第rowId+1条数据开始查询一条数据,即第rouId+1条。
		return true;
		 //return db.delete(DATABASE_TABLE,ROWID+"="+rowId,null)>0;//delete失败返回0
	}

	//update an entity
	public boolean update(long rowId,String note){
		ContentValues args = new ContentValues();
		args.put(NOTE, note);

		return db.update(DATABASE_TABLE, args, ROWID+"="+rowId, null)>0;
	}
}
NoteEdit
package demo.xpf.healthytids;

import android.app.Activity;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import demo.xpf.healthytids.TidsDbAdapter;

public class NoteEdit extends Activity{
	private static final String TAG = "tids";
	private TidsDbAdapter mDbHelper;
	private SQLiteDatabase db;
	@Override
	protected void onCreate(Bundle SavedInstanceState){
		super.onCreate(SavedInstanceState);
		mDbHelper = new TidsDbAdapter(this);
		mDbHelper.open();
		setContentView(R.layout.note_edit);
		Log.d(TAG, "edit");
		findViews();
		showViews(SavedInstanceState);
	}

	private EditText field_note;
	private Button   button_confirm;
	private void findViews() {
		// TODO Auto-generated method stub
		field_note = (EditText) findViewById(R.id.note);
		button_confirm = (Button) findViewById(R.id.confirm);
	}

	private Long mRowId;
	private void showViews(Bundle savedInstanceState) {
		mRowId = savedInstanceState != null?
				savedInstanceState.getLong(TidsDbAdapter.ROWID) : null;
		/*saveInstanceState 这个“bundle”数据容器中,取出Activity上一次处于“stop”状态是,键值为“_id”(NotesDbAdapter.ROWID)的内容值。如果这个ACtivity是
		全新打开的或是之前的行程已经被回收了,那么“mRouId”的值被设为“null”*/

		if (mRowId == null) {
			Bundle extras = getIntent().getExtras();
			mRowId = extras != null ? extras.getLong(TidsDbAdapter.ROWID) : null;
			Log.d(TAG, "position  "+mRowId);
		/*
			Cursor mCursor = db.query("tids",new String[]{"_id"}, null, null, null, null, null, mRowId+"1");
			while (mCursor!=null) {
		          mRowId = mCursor.getLong(0); //获取第一列的值,第一列的索引从0开始
		          Log.d(TAG, "id  "+mRowId);
		} */
		}

		populateFields();//根据RowId查询记录,并显示在EditText中

		button_confirm.setOnClickListener(new View.OnClickListener(){

			@Override
			public void onClick(View v) {
				mDbHelper.update(mRowId, field_note.getText().toString());
				setResult(RESULT_OK);
				finish();
			}
		});
	}

	private void populateFields() {
		if (mRowId != null){
			Cursor note = mDbHelper.get(mRowId);
			startManagingCursor(note);

			field_note.setText(note.getString(note.getColumnIndexOrThrow(TidsDbAdapter.NOTE)));
		}

	}

}

时间: 2024-10-12 08:09:31

带滑动删除的Dummynote的相关文章

【转】Android 使用Scroller实现绚丽的ListView左右滑动删除Item效果

原文网址:http://blog.csdn.net/xiaanming/article/details/17539199 我在上一篇文章中Android 带你从源码的角度解析Scroller的滚动实现原理从源码的角度介绍了Scroller的滚动实现原理,相信大家对Scroller的使用有一定的了解,这篇文章就给大家带来使用Scroller的小例子,来帮助大家更加熟悉的掌握Scroller的使用,掌握好了Scroller的使用我们就能实现很多滑动的效果.例如侧滑菜单,launcher,ListVi

本文出自xiaanming的博客(http://blog.csdn.net/xiaanming/article/details/18311877)Android 使用NineOldAndroids实现绚丽的ListView左右滑动删除Item效果

今天还是给大家带来自定义控件的编写,自定义一个ListView的左右滑动删除Item的效果,这个效果之前已经实现过了,有兴趣的可以看下Android 使用Scroller实现绚丽的ListView左右滑动删除Item效果,之前使用的是滑动类Scroller来实现的,但是看了下通知栏的左右滑动删除效果,确实很棒,当我们滑动Item超过一半的时候,item的透明度就变成了0,我们就知道抬起手指的时候item就被删除了,当item的透明度不为0的时候,我们抬起手指Item会回到起始位置,这样我们就知道

Android 使用NineOldAndroids实现绚丽的ListView左右滑动删除Item效果

今天还是给大家带来自定义控件的编写,自定义一个ListView的左右滑动删除Item的效果,这个效果之前已经实现过了,有兴趣的可以看下Android 使用Scroller实现绚丽的ListView左右滑动删除Item效果, 之前使用的是滑动类Scroller来实现的,但是看了下通知栏的左右滑动删除效果,确实很棒,当我们滑动Item超过一半的时候,item的透明度就变 成了0,我们就知道抬起手指的时候item就被删除了,当item的透明度不为0的时候,我们抬起手指Item会回到起始位置,这样我们就

Android Demo 下拉刷新+加载更多+滑动删除

小伙伴们在逛淘宝或者是各种app上,都可以看到这样的功能,下拉刷新和加载更多以及滑动删除,刷新,指刷洗之后使之变新,比喻突破旧的而创造出新的,比如在手机上浏览新闻的时候,使用下拉刷新的功能,我们可以第一时间掌握最新消息,加载更多是什么nie,简单来说就是在网页上逛淘宝的时候,我们可以点击下一页来满足我们更多的需求,但是在手机端就不一样了,没有上下页,怎么办nie,方法总比困难多,细心的小伙伴可能会发现,在手机端中,有加载更多来满足我们的要求,其实加载更多也是分页的一种体现.小伙伴在使用手机版QQ

[转]Android 使用Scroller实现绚丽的ListView左右滑动删除Item效果

我在上一篇文章中Android 带你从源码的角度解析Scroller的滚动实现原理从源码的角度介绍了Scroller的滚动实现原理,相信大家对Scroller的使用有一定的了解,这篇文章就给大家带来使用Scroller的小例子,来帮助大家更加熟悉的掌握Scroller的使用,掌握好了Scroller的使用我们就能实现很多滑动的效果.例如侧滑菜单,launcher,ListView的下拉刷新等等效果,我今天实现的是ListView的item的左右滑动删除item的效果,现在很多朋友看到这个效果应该

Notification(Notification的通知栏常驻、各种样式、点击无效、禁止滑动删除、兼容低版本)

Notification(Notification的通知栏常驻.Notification的各种样式.Notification点击无效.Notification禁止滑动删除) Android的Notification是android系统中很重要的一个机制, 产品人员常常利用通知栏的方式,跟用户进行弱沟通.拥有推送通知的app要比没有此类功能的app活跃率要高很多.另外类似于墨迹天气,清理大师等app,也会将通知栏常驻,利用自定义的布局,方便用户及时快捷的查看所需的信息和使用快捷的功能.所以Noti

ios8 tableView设置滑动删除时 显示多个按钮

** *  tableView:editActionsForRowAtIndexPath:     //设置滑动删除时显示多个按钮 *  UITableViewRowAction                        //通过此类创建按钮 *  1. 我们在使用一些应用的时候,在滑动一些联系人的某一行的时候,会出现删除.置顶.更多等等的按钮,在iOS8之前,我们都需要自己去实现.但是,到了iOS8,系统已经写好了,只需要一个代理方法和一个类就搞定了 *  2. iOS8的协议多了一个方法

ios8 tableView设置滑动删除时显示多个按钮

镔哥,研究很久最后才发现iOS8 TableView出新功能,然后就记下来,供大家参考,为大伙所用. 看我博客都知道,我一向都是喜欢代码注释结合,提供demo给大伙参考,写得不好,不要见怪哦. ** *  tableView:editActionsForRowAtIndexPath:     // 设置滑动删除时显示多个按钮 *  UITableViewRowAction                        // 通过此类创建按钮 *  1. 我们在使用一些应用的时候,在滑动一些联系人

UITableView 自带编辑删除 自定义按钮

一:UITableView 自带编辑删除 1:实现两个方法即可 #pragma mark   tableView自带的编辑功能 -(void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath{ //方法实现后,默认实现手势滑动删除的方法 if (editingStyle!