StatePanelTrack.java revision fb6a8e166f0a46d2a994a408b1679e3a67fdcb52
1fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard/*
2fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard * Copyright (C) 2013 The Android Open Source Project
3fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard *
4fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard * Licensed under the Apache License, Version 2.0 (the "License");
5fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard * you may not use this file except in compliance with the License.
6fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard * You may obtain a copy of the License at
7fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard *
8fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard *      http://www.apache.org/licenses/LICENSE-2.0
9fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard *
10fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard * Unless required by applicable law or agreed to in writing, software
11fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard * distributed under the License is distributed on an "AS IS" BASIS,
12fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard * See the License for the specific language governing permissions and
14fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard * limitations under the License.
15fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard */
16fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
17fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroardpackage com.android.gallery3d.filtershow.state;
18fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
19fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroardimport android.animation.LayoutTransition;
20fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroardimport android.content.Context;
21fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroardimport android.graphics.Point;
22fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroardimport android.graphics.Rect;
23fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroardimport android.util.AttributeSet;
24fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroardimport android.view.GestureDetector;
25fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroardimport android.view.MotionEvent;
26fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroardimport android.view.View;
27fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroardimport android.widget.Adapter;
28fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroardimport android.widget.LinearLayout;
29fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroardimport com.android.gallery3d.filtershow.FilterShowActivity;
30fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroardimport com.android.gallery3d.filtershow.filters.FilterRepresentation;
31fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
32fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroardpublic class StatePanelTrack extends LinearLayout implements PanelTrack {
33fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
34fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    private static final String LOGTAG = "StatePanelTrack";
35fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    private Point mTouchPoint;
36fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    private StateView mCurrentView;
37fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    private StateView mCurrentSelectedView;
38fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    private boolean mExited = false;
39fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    private boolean mStartedDrag = false;
40fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    private StateAdapter mAdapter;
41fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    private DragListener mDragListener = new DragListener(this);
42fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    GestureDetector mGestureDetector;
43fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    private int mContainerWidth = 668; // TODO: get this from XML
44fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    private int mContainerHeight = 200;
45fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
46fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    public StatePanelTrack(Context context, AttributeSet attrs) {
47fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        super(context, attrs);
48fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        GestureDetector.SimpleOnGestureListener simpleOnGestureListener
49fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                = new GestureDetector.SimpleOnGestureListener(){
50fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            @Override
51fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            public void onLongPress(MotionEvent e) {
52fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                longPress(e);
53fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            }
54fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            @Override
55fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            public boolean onDoubleTap(MotionEvent e) {
56fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                addDuplicate(e);
57fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                return true;
58fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            }
59fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        };
60fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        mGestureDetector = new GestureDetector(context, simpleOnGestureListener);
61fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    }
62fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
63fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    private void addDuplicate(MotionEvent e) {
64fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        if (mCurrentSelectedView == null) {
65fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            return;
66fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
67fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        int pos = findChild(mCurrentSelectedView);
68fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        if (pos != -1) {
69fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            mAdapter.insert(new State(mCurrentSelectedView.getState()), pos);
70fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            fillContent(true);
71fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
72fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    }
73fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
74fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    private void longPress(MotionEvent e) {
75fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        View view = findChildAt((int) e.getX(), (int) e.getY());
76fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        if (view == null) {
77fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            return;
78fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
79fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        if (view instanceof StateView) {
80fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            StateView stateView = (StateView) view;
81fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            stateView.setDuplicateButton(true);
82fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
83fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    }
84fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
85fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    public void setAdapter(StateAdapter adapter) {
86fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        mAdapter = adapter;
87fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        mAdapter.setListener(this);
88fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        mAdapter.setOrientation(getOrientation());
89fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        fillContent(false);
90fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        requestLayout();
91fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    }
92fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
93fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    public StateView findChildWithState(State state) {
94fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        for (int i = 0; i < getChildCount(); i++) {
95fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            StateView view = (StateView) getChildAt(i);
96fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            if (view.getState() == state) {
97fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                return view;
98fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            }
99fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
100fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        return null;
101fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    }
102fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
103fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    @Override
104fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec){
105fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        int w = MeasureSpec.getSize(widthMeasureSpec);
106fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        if (w > 0) {
107fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            mContainerWidth = w;
108fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
109fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
110fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        fillContent(false);
111fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    }
112fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
113fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    public void fillContent(boolean animate) {
114fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        if (!animate) {
115fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            this.setLayoutTransition(null);
116fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
117fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        int n = mAdapter.getCount();
118fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        int w = mContainerWidth;
119fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        int h = mContainerHeight;
120fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        for (int i = 0; i < getChildCount(); i++) {
121fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            StateView child = (StateView) getChildAt(i);
122fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            child.resetPosition();
123fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            if (!mAdapter.contains(child.getState())) {
124fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                removeView(child);
125fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            }
126fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
127fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        LayoutParams params;
128fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        params = new LayoutParams(w, h);
129fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        LayoutParams paramsEnds;
130fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        paramsEnds = new LayoutParams(w, h/2);
131fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        for (int i = 0; i < n; i++) {
132fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            State s = mAdapter.getItem(i);
133fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            if (findChildWithState(s) == null) {
134fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                View view = mAdapter.getView(i, null, this);
135fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                addView(view, i, params);
136fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            }
137fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
138fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        for (int i = 0; i < n; i++) {
139fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            State state = mAdapter.getItem(i);
140fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            StateView view = (StateView) getChildAt(i);
141fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            view.setState(state);
142fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            if (i == 0) {
143fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                view.setType(StateView.BEGIN);
144fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            } else if (i == n - 1) {
145fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                view.setType(StateView.END);
146fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            }
147fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            view.resetPosition();
148fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            if (i == 0 || (i == n -1)) {
149fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                if (view.getWidth() != w || view.getHeight() != h/2) {
150fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                    view.setLayoutParams(paramsEnds);
151fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                    requestLayout();
152fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                }
153fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            } else {
154fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                if (view.getWidth() != w || view.getHeight() != h) {
155fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                    view.setLayoutParams(params);
156fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                    requestLayout();
157fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                }
158fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            }
159fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
160fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
161fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        if (!animate) {
162fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            this.setLayoutTransition(new LayoutTransition());
163fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
164fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    }
165fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
166fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    public void onTouch(MotionEvent event, StateView view) {
167fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        if (!view.isDraggable()) {
168fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            return;
169fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
170fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        mCurrentView = view;
171fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        if (mCurrentSelectedView == mCurrentView) {
172fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            return;
173fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
174fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        if (mCurrentSelectedView != null) {
175fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            mCurrentSelectedView.setSelected(false);
176fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
177fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        // We changed the current view -- let's reset the
178fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        // gesture detector.
179fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        MotionEvent cancelEvent = MotionEvent.obtain(event);
180fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        cancelEvent.setAction(MotionEvent.ACTION_CANCEL);
181fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        mGestureDetector.onTouchEvent(cancelEvent);
182fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        mCurrentSelectedView = mCurrentView;
183fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        mCurrentSelectedView.setSelected(true);
184fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        // We have to send the event to the gesture detector
185fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        mGestureDetector.onTouchEvent(event);
186fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        FilterShowActivity activity = (FilterShowActivity) getContext();
187fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        activity.getPanelController().showComponentWithRepresentation(
188fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                mCurrentSelectedView.getState().getFilterRepresentation());
189fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    }
190fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
191fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    @Override
192fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    public boolean onInterceptTouchEvent(MotionEvent event) {
193fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        if (mCurrentView != null) {
194fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            return true;
195fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
196fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        return false;
197fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    }
198fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
199fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    @Override
200fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    public boolean onTouchEvent(MotionEvent event) {
201fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        if (mCurrentView == null) {
202fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            return false;
203fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
204fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        mGestureDetector.onTouchEvent(event);
205fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        if (mTouchPoint == null) {
206fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            mTouchPoint = new Point();
207fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            mTouchPoint.x = (int) event.getX();
208fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            mTouchPoint.y = (int) event.getY();
209fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
210fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        if (event.getActionMasked() == MotionEvent.ACTION_MOVE) {
211fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            float translation = event.getY() - mTouchPoint.y;
212fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            float alpha = 1.0f - (Math.abs(translation) / mCurrentView.getHeight());
213fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            if (getOrientation() == LinearLayout.VERTICAL) {
214fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                translation = event.getX() - mTouchPoint.x;
215fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                alpha = 1.0f - (Math.abs(translation) / mCurrentView.getWidth());
216fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                mCurrentView.setTranslationX(translation);
217fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            } else {
218fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                mCurrentView.setTranslationY(translation);
219fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            }
220fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            mCurrentView.setBackgroundAlpha(alpha);
221fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            if (alpha < 0.7) {
222fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                setOnDragListener(mDragListener);
223fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                DragShadowBuilder shadowBuilder = new DragShadowBuilder(mCurrentView);
224fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                mCurrentView.startDrag(null, shadowBuilder, mCurrentView, 0);
225fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                mStartedDrag = true;
226fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            }
227fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
228fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        if (event.getActionMasked() == MotionEvent.ACTION_UP
229fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                || (!mStartedDrag && event.getActionMasked() == MotionEvent.ACTION_CANCEL)) {
230fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            checkEndState();
231fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
232fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        return true;
233fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    }
234fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
235fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    public void checkEndState() {
236fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        mTouchPoint = null;
237fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        if (mExited || mCurrentView.getAlpha() < 0.2) {
238fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            int origin = findChild(mCurrentView);
239fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            if (origin != -1) {
240fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                State current = mAdapter.getItem(origin);
241fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                mAdapter.remove(current);
242fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                fillContent(true);
243fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            }
244fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        } else {
245fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            mCurrentView.setBackgroundAlpha(1.0f);
246fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            mCurrentView.setTranslationX(0);
247fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            mCurrentView.setTranslationY(0);
248fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
249fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        mCurrentView = null;
250fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        mExited = false;
251fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        mStartedDrag = false;
252fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    }
253fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
254fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    public View findChildAt(int x, int y) {
255fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        Rect frame = new Rect();
256fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        int scrolledXInt = getScrollX() + x;
257fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        int scrolledYInt = getScrollY() + y;
258fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        for (int i = 0; i < getChildCount(); i++) {
259fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            View child = getChildAt(i);
260fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            child.getHitRect(frame);
261fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            if (frame.contains(scrolledXInt, scrolledYInt)) {
262fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                return child;
263fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            }
264fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
265fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        return null;
266fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    }
267fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
268fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    public int findChild(View view) {
269fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        for (int i = 0; i < getChildCount(); i++) {
270fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            View child = getChildAt(i);
271fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            if (child == view) {
272fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard                return i;
273fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard            }
274fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        }
275fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        return -1;
276fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    }
277fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
278fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    public StateView getCurrentView() {
279fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        return mCurrentView;
280fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    }
281fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
282fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    public void setCurrentView(View currentView) {
283fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        mCurrentView = (StateView) currentView;
284fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    }
285fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
286fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    public void setExited(boolean value) {
287fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        mExited = value;
288fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    }
289fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
290fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    public Point getTouchPoint() {
291fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        return mTouchPoint;
292fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    }
293fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard
294fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    public Adapter getAdapter() {
295fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard        return mAdapter;
296fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard    }
297fb6a8e166f0a46d2a994a408b1679e3a67fdcb52nicolasroard}
298