package com.android.launcher; import com.android.launcher.DragController.DragListener; import android.content.Context; import android.content.res.TypedArray; import android.graphics.Rect; import android.graphics.drawable.Drawable; import android.util.AttributeSet; import android.view.GestureDetector; import android.view.HapticFeedbackConstants; import android.view.MotionEvent; import android.view.View; import android.view.GestureDetector.OnGestureListener; import android.widget.Toast; public class ActionButton extends CounterImageView implements DropTarget, DragListener { private Launcher mLauncher; private int mIdent=LauncherSettings.Favorites.CONTAINER_LAB; private ItemInfo mCurrentInfo; private Drawable bgResource; private Drawable bgEmpty; private Drawable mIconNormal; private int mIconSpecial_id; private Drawable mIconSpecial; private boolean specialMode=false; private boolean hiddenBg=false; private int specialAction=0; private GestureDetector mGestureDetector; private ABGestureListener mGestureListener; public boolean mInterceptClicks=false; private static final int ORIENTATION_HORIZONTAL = 1; private int mOrientation = ORIENTATION_HORIZONTAL; private SwipeListener mSwipeListener; public ActionButton(Context context) { super(context); // TODO Auto-generated constructor stub } public ActionButton(Context context, AttributeSet attrs) { this(context, attrs,0); // TODO Auto-generated constructor stub } public ActionButton(Context context, AttributeSet attrs, int defStyle) { super(context, attrs, defStyle); // TODO Auto-generated constructor stub setHapticFeedbackEnabled(true); TypedArray a=context.obtainStyledAttributes(attrs,R.styleable.ActionButton,defStyle,0); mIdent=a.getInt(R.styleable.ActionButton_ident, mIdent); mOrientation = a.getInt(R.styleable.ActionButton_direction, ORIENTATION_HORIZONTAL); //bgResource=a.getDrawable(R.styleable.ActionButton_background); bgEmpty=context.getResources().getDrawable(R.drawable.lab_rab_empty_bg); a.recycle(); mGestureListener = new ABGestureListener(); //mGestureDetector = new GestureDetector(mGestureListener); mGestureDetector = new GestureDetector(context, mGestureListener); } public boolean acceptDrop(DragSource source, int x, int y, int xOffset, int yOffset, Object dragInfo) { // TODO Auto-generated method stub return !specialMode; } public Rect estimateDropLocation(DragSource source, int x, int y, int xOffset, int yOffset, Object dragInfo, Rect recycle) { // TODO Auto-generated method stub return null; } public void onDragEnter(DragSource source, int x, int y, int xOffset, int yOffset, Object dragInfo) { // TODO Auto-generated method stub setPressed(true); } public void onDragExit(DragSource source, int x, int y, int xOffset, int yOffset, Object dragInfo) { // TODO Auto-generated method stub setPressed(false); } public void onDragOver(DragSource source, int x, int y, int xOffset, int yOffset, Object dragInfo) { // TODO Auto-generated method stub } public void onDrop(DragSource source, int x, int y, int xOffset, int yOffset, Object dragInfo) { boolean accept=true; ItemInfo info = (ItemInfo) dragInfo; switch (info.itemType) { case LauncherSettings.Favorites.ITEM_TYPE_APPLICATION: case LauncherSettings.Favorites.ITEM_TYPE_SHORTCUT: case LauncherSettings.Favorites.ITEM_TYPE_LIVE_FOLDER: case LauncherSettings.Favorites.ITEM_TYPE_USER_FOLDER: //we do accept those break; case LauncherSettings.Favorites.ITEM_TYPE_APPWIDGET: Toast t=Toast.makeText(getContext(), R.string.toast_widgets_not_supported, Toast.LENGTH_SHORT); t.show(); accept=false; break; default: Toast t2=Toast.makeText(getContext(), R.string.toast_unknown_item, Toast.LENGTH_SHORT); t2.show(); accept=false; break; } final LauncherModel model = Launcher.getModel(); //TODO:ADW check this carefully //We need to remove current item from database before adding the new one if (info instanceof LauncherAppWidgetInfo) { model.removeDesktopAppWidget((LauncherAppWidgetInfo) info); final LauncherAppWidgetInfo launcherAppWidgetInfo = (LauncherAppWidgetInfo) info; final LauncherAppWidgetHost appWidgetHost = mLauncher.getAppWidgetHost(); if (appWidgetHost != null) { appWidgetHost.deleteAppWidgetId(launcherAppWidgetInfo.appWidgetId); } } if(accept){ if(mCurrentInfo!=null){ model.removeDesktopItem(mCurrentInfo); LauncherModel.deleteItemFromDatabase(mLauncher, mCurrentInfo); } model.addDesktopItem(info); LauncherModel.addOrMoveItemInDatabase(mLauncher, info, mIdent, -1, -1, -1); UpdateLaunchInfo(info); }else{ LauncherModel.deleteItemFromDatabase(mLauncher, info); } } protected void UpdateLaunchInfo(ItemInfo info){ mCurrentInfo=info; //TODO:ADW extract icon and put it as the imageview src... Drawable myIcon=null; switch (info.itemType) { case LauncherSettings.Favorites.ITEM_TYPE_APPLICATION: case LauncherSettings.Favorites.ITEM_TYPE_SHORTCUT: if (info.container == NO_ID) { // Came from all apps -- make a copy info = new ApplicationInfo((ApplicationInfo) info); } setCounter(((ApplicationInfo)info).counter,((ApplicationInfo)info).counterColor); myIcon = mLauncher.createSmallActionButtonIcon(info); break; case LauncherSettings.Favorites.ITEM_TYPE_LIVE_FOLDER: case LauncherSettings.Favorites.ITEM_TYPE_USER_FOLDER: myIcon = mLauncher.createSmallActionButtonIcon(info); break; case LauncherSettings.Favorites.ITEM_TYPE_APPWIDGET: //Toast t=Toast.makeText(getContext(), "Widgets not supported... sorry :-)", Toast.LENGTH_SHORT); //t.show(); return; default: //Toast t2=Toast.makeText(getContext(), "Unknown item. We can't add unknown item types :-)", Toast.LENGTH_SHORT); //t2.show(); return; //throw new IllegalStateException("Unknown item type: " + info.itemType); } setIcon(myIcon); invalidate(); } public void onDragEnd() { // TODO Auto-generated method stub } public void onDragStart(View v, DragSource source, Object info, int dragAction) { // TODO Auto-generated method stub } void setLauncher(Launcher launcher) { mLauncher = launcher; } @Override public Object getTag() { // TODO Auto-generated method stub if(!specialMode){ return mCurrentInfo; }else{ return specialAction; } } public void updateIcon(){ if(mCurrentInfo!=null){ ItemInfo info=mCurrentInfo; Drawable myIcon=null; switch (info.itemType) { case LauncherSettings.Favorites.ITEM_TYPE_APPLICATION: case LauncherSettings.Favorites.ITEM_TYPE_SHORTCUT: if (info.container == NO_ID) { // Came from all apps -- make a copy info = new ApplicationInfo((ApplicationInfo) info); } myIcon = mLauncher.createSmallActionButtonIcon(info); break; case LauncherSettings.Favorites.ITEM_TYPE_LIVE_FOLDER: case LauncherSettings.Favorites.ITEM_TYPE_USER_FOLDER: myIcon = mLauncher.createSmallActionButtonIcon(info); break; case LauncherSettings.Favorites.ITEM_TYPE_APPWIDGET: //Toast t=Toast.makeText(getContext(), "Widgets not supported... sorry :-)", Toast.LENGTH_SHORT); //t.show(); return; default: //Toast t2=Toast.makeText(getContext(), "Unknown item. We can't add unknown item types :-)", Toast.LENGTH_SHORT); //t2.show(); return; //throw new IllegalStateException("Unknown item type: " + info.itemType); } setIcon(myIcon); invalidate(); }else{ Drawable myIcon = mLauncher.createSmallActionButtonIcon(null); setIcon(myIcon); invalidate(); } if(mIconSpecial_id!=0){ setSpecialIcon(mIconSpecial_id); } } /** * ADW: show/hide background * @param enable */ public void hideBg(boolean hide){ if(hide!=hiddenBg){ hiddenBg=hide; if(!hide) this.setBackgroundDrawable(bgResource); else{ this.setBackgroundDrawable(bgEmpty); } } } @Override public void setBackgroundDrawable(Drawable d) { // TODO Auto-generated method stub super.setBackgroundDrawable(d); if(d!=bgEmpty){ if(bgResource!=null)bgResource.setCallback(null); bgResource=d; } } private void setIcon(Drawable d){ if(mIconNormal!=null){ mIconNormal.setCallback(null); mIconNormal=null; } mIconNormal=d; if(!specialMode){ setImageDrawable(mIconNormal); } } public void setSpecialIcon(int res_id){ Drawable d=null; try{ d=getResources().getDrawable(res_id); if(mIconSpecial!=null){ mIconSpecial.setCallback(null); mIconSpecial=null; } mIconSpecial_id=res_id; mIconSpecial=mLauncher.createSmallActionButtonDrawable(d); if(specialMode){ setImageDrawable(mIconSpecial); } }catch (Exception e) { } } public void setSpecialMode(boolean special){ if(special!=specialMode){ specialMode=special; if(specialMode) setImageDrawable(mIconSpecial); else setImageDrawable(mIconNormal); } } public void setSpecialAction(int action){ specialAction=action; } @Override public boolean onTouchEvent(MotionEvent ev) { if (mGestureDetector.onTouchEvent(ev)) { return true; } if(!mInterceptClicks){ return super.onTouchEvent(ev); } return false; } class ABGestureListener implements OnGestureListener { public boolean onDown(MotionEvent e) { mInterceptClicks=false; return false; } public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) { float velocity=0; if(mOrientation!= ORIENTATION_HORIZONTAL){ if(velocityX<0 && Math.abs(velocityY)<Math.abs(velocityX)) velocity=Math.abs(velocityX); }else{ if(velocityY<0 && Math.abs(velocityY)>Math.abs(velocityX)) velocity=Math.abs(velocityY); } if(velocity>0){ dispatchSwipeEvent(); mInterceptClicks=true; return true; } return false; } public void onLongPress(MotionEvent e) { //not used } public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY) { //not used return false; } public void onShowPress(MotionEvent e) { //not used } public boolean onSingleTapUp(MotionEvent e) { //not used return false; } } public void setSwipeListener(SwipeListener listener) { mSwipeListener = listener; } /** * Dispatches a trigger event to listener. Ignored if a listener is not set. * @param whichHandle the handle that triggered the event. */ private void dispatchSwipeEvent() { if (mSwipeListener != null) { performHapticFeedback(HapticFeedbackConstants.LONG_PRESS, HapticFeedbackConstants.FLAG_IGNORE_VIEW_SETTING); mSwipeListener.onSwipe(); } } /** * Interface definition for a callback to be invoked when a tab is triggered * by moving it beyond a threshold. */ public interface SwipeListener { void onSwipe(); } }