I am trying to place a marker on a map overlay and then present a pop up when the user selects the drawable. The problem is the events seem to overlap.when i tap(ontouch MotionEvent.ACTION_UP call) on marker then some time other marker gone and i also want to do like when popup is visible then no one marker can drag by user. Does anyone have any suggestions on how to make these events mutually exclusive?
Here is the code for the map activity:
#Override
public boolean onTouchEvent(MotionEvent event, MapView mapView) {
final int action = event.getAction();
final int x = (int) event.getX();
final int y = (int) event.getY();
boolean result = false;
if (action == MotionEvent.ACTION_DOWN) {
for (OverlayItem item : items) {
Point p = new Point(0, 0);
map.getProjection().toPixels(item.getPoint(), p);
if (hitTest(item, marker, x - p.x, y - p.y)) {
result = true;
inDrag = item;
items.remove(inDrag);
populate();
xDragTouchOffset = 0;
yDragTouchOffset = 0;
setDragImagePosition(p.x, p.y);
dragImage.setVisibility(View.VISIBLE);
xDragTouchOffset = x - p.x;
yDragTouchOffset = y - p.y;
Log.e("touch"," out ACTION_DOWN");
// onTap(index);
break;
}
}
} else if (action == MotionEvent.ACTION_MOVE && inDrag != null) {
//
setDragImagePosition(x, y);
Log.e("touch"," out btn");
result = true;
flag = false;
} else if (action == MotionEvent.ACTION_UP && inDrag != null) {
if (mLastMotionEventAction == MotionEvent.ACTION_DOWN){
// SOME TAP ACTIONS ...
dragImage.setVisibility(View.GONE);
GeoPoint pt = map.getProjection().fromPixels(
x - xDragTouchOffset, y - yDragTouchOffset);
OverlayItem toDrop = new OverlayItem(pt, inDrag.getTitle(),
inDrag.getSnippet());
Log.e("touch"," out last" + pt.getLatitudeE6());
items.add(toDrop);
// onTap(pt, map);
// onTap();
populate();
inDrag = null;
result = true;
flag = false;
// if (result) {
//
// }
Log.e("pop up", "pop up");
return false;
} else {
return true;
}
// onTap(index);
}
mLastMotionEventAction = event.getAction();
return (result || super.onTouchEvent(event, mapView));
}
private void setDragImagePosition(int x, int y) {
RelativeLayout.LayoutParams lp = (RelativeLayout.LayoutParams) dragImage
.getLayoutParams();
lp.setMargins(x - xDragImageOffset - xDragTouchOffset, y
- yDragImageOffset - yDragTouchOffset, 0, 0);
dragImage.setLayoutParams(lp);
}
}
And i write onTap but this method is not working.no error getting.
i want to handle both method.
Finally i handled onTouchEvent and onTap overlapping with drag and pop-up with marker.
#Override
protected boolean onTap(final int index) {
if ( isPinch ){
return false;
}else{
// getMapView().setOnTouchListener(new OnTouchListener() {
// #Override
// public boolean onTouch(View arg0, MotionEvent arg1) {
// if (!items.isEmpty()) {
// if (view != null) {
// view.setVisibility(View.GONE);
// getMapView().invalidate();
// }
// }
// getMapView().invalidate();
// return true;
// }
// });
if (view != null) {
view.setVisibility(View.GONE);
getMapView().removeView(view);
getMapView().invalidate();
flag = false;
view = null;
}
view = getLayoutInflater().inflate(R.layout.balloon_overlay, null);
LinearLayout layout = (LinearLayout) view
.findViewById(R.id.balloon_main_layout);
layout.setLayoutParams(new LayoutParams(LayoutParams.WRAP_CONTENT,
LayoutParams.WRAP_CONTENT));
view.setLayoutParams(new LayoutParams(LayoutParams.WRAP_CONTENT,
LayoutParams.WRAP_CONTENT));
view.setBackgroundResource(R.drawable.balloon_overlay_bg_selector);
ImageView image = (ImageView) view
.findViewById(R.id.balloon_disclosure);
TextView text = (TextView) view
.findViewById(R.id.balloon_item_title);
text.setText(items.get(index).getTitle());
if (items.get(index).getTitle() != null
&& items.get(index).getTitle().equals("Me") == false) {
image.setImageResource(R.drawable.mekr);
}
Projection projection = getMapView().getProjection();
Point point = new Point();
projection.toPixels(items.get(index).getPoint(), point);
int x = (int) (view.getWidth() / 2f);
int y = -bitMap.getHeight() - 3;
MapView.LayoutParams lp = new MapView.LayoutParams(
ViewGroup.LayoutParams.WRAP_CONTENT,
ViewGroup.LayoutParams.WRAP_CONTENT, items.get(index)
.getPoint(), x, y,
MapView.LayoutParams.BOTTOM_CENTER);
getMapView().removeView(view);
getMapView().invalidate();
getMapView().addView(view, lp);
getMapView().invalidate();
view.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View view) {
if (!items.isEmpty()) {
if (view != null) {
view.setVisibility(View.GONE);
getMapView().invalidate();
}
}
getMapView().invalidate();
}
});
selectedIndex = index;
return true;
}
}
#Override
public boolean onTouchEvent(MotionEvent event, MapView mapView) {
final int action = event.getAction();
final int x = (int) event.getX();
final int y = (int) event.getY();
boolean result = false;
if (action == MotionEvent.ACTION_DOWN) {
for (OverlayItem item : items) {
Point p = new Point(0, 0);
map.getProjection().toPixels(item.getPoint(), p);
if (hitTest(item, marker, x - p.x, y - p.y)) {
result = true;
inDrag = item;
items.remove(inDrag);
populate();
xDragTouchOffset = 0;
yDragTouchOffset = 0;
setDragImagePosition(p.x, p.y);
dragImage.setVisibility(View.VISIBLE);
xDragTouchOffset = x - p.x;
yDragTouchOffset = y - p.y;
isPinch=false;
break;
}
}
} else if (action == MotionEvent.ACTION_MOVE && inDrag != null) {
if (view != null) {
if (view.getVisibility() != 0) {
Log.e("touch", " out move");
setDragImagePosition(x, y);
result = true;
isPinch=true;
}else{
setDragImagePosition(x, y);
isPinch=false;
}
}else{
setDragImagePosition(x, y);
result = true;
isPinch=true;
}
} else if (action == MotionEvent.ACTION_UP && inDrag != null) {
dragImage.setVisibility(View.GONE);
GeoPoint pt = map.getProjection().fromPixels(
x - xDragTouchOffset, y - yDragTouchOffset);
OverlayItem toDrop = new OverlayItem(pt, inDrag.getTitle(),
inDrag.getSnippet());
Log.e("touch", " out last" + pt.getLatitudeE6());
items.add(toDrop);
populate();
inDrag = null;
result = true;
isPinch = false;
}
return (isPinch || super.onTouchEvent(event,mapView));
}
private void setDragImagePosition(int x, int y) {
RelativeLayout.LayoutParams lp = (RelativeLayout.LayoutParams) dragImage
.getLayoutParams();
lp.setMargins(x - xDragImageOffset - xDragTouchOffset, y
- yDragImageOffset - yDragTouchOffset, 0, 0);
dragImage.setLayoutParams(lp);
}
}
Try out below code :
/**
* Class used to plot the start and end points on the map
*
*/
public class MapendPointsOverlay extends ItemizedOverlay<OverlayItem> {
private ArrayList<OverlayItem> m_overlays = new ArrayList<OverlayItem>();
private BalloonOverlayView m_balloonView;
private OverlayItem m_overlayitem;
private Context m_context;
private int m_viewOffset;
private MapController m_mapController;
private MapView m_mapView;
private int m_screenWidth;
private int m_screenHeight;
private Display m_screen;
private boolean m_fromroutepath = false;
public MapendPointsOverlay(Drawable p_drawable) {
super(p_drawable);
}
public MapendPointsOverlay(Drawable p_defaultMarker, Context p_context,
MapView p_mapview, boolean p_fromroutepath) {
super(boundCenterBottom(p_defaultMarker));
m_context = p_context;
m_mapView = p_mapview;
m_mapController = p_mapview.getController();
m_viewOffset = 35;
m_fromroutepath = p_fromroutepath;
m_screen = ((WindowManager) m_context .getSystemService(Context.WINDOW_SERVICE)).getDefaultDisplay();
m_screenWidth = m_screen.getWidth();
m_screenHeight = m_screen.getHeight();
}
/**
* Method that creates an OverlayItem from the list of OverlayItem at index
* given by <b>p_arg0</b>
*/
#Override
protected OverlayItem createItem(int p_arg0) {
return m_overlays.get(p_arg0);
}
#Override
public int size() {
return m_overlays.size();
}
#Override
protected boolean onTap(int p_index) {
boolean m_isRecycled;
GeoPoint m_point;
m_point = createItem(p_index).getPoint();
m_overlayitem = m_overlays.get(p_index);
if (m_balloonView == null) {
m_balloonView = new BalloonOverlayView(m_context, m_viewOffset);
m_isRecycled = false;
} else {
m_isRecycled = true;
}
m_balloonView.setVisibility(View.GONE);
m_balloonView.setData(m_overlayitem);
m_balloonView.setVisibility(View.VISIBLE);
MapView.LayoutParams m_params = new MapView.LayoutParams(
LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT, m_point,MapView.LayoutParams.BOTTOM_CENTER);
m_params.mode = MapView.LayoutParams.MODE_MAP;
List<Overlay> m_mapOverlays = m_mapView.getOverlays();
if (m_mapOverlays.size() > 1) {
hideOtherBalloons(m_mapOverlays);
}
if (m_isRecycled) {
m_balloonView.setLayoutParams(m_params);
} else {
m_mapView.addView(m_balloonView, m_params);
}
m_mapController.animateTo(m_point);
m_mapController.setCenter(m_point);
return true;
}
/**
* Sets the visibility of this overlay's balloon view to GONE.
*/
private void hideBalloon() {
if (m_balloonView != null) {
m_balloonView.setVisibility(View.GONE);
}
}
/**
* Hides the balloon view for any other BalloonItemizedOverlay instances
* that might be present on the MapView.
*
* #param p_overlays
* - list of overlays (including this) on the MapView.
*/
private void hideOtherBalloons(List<Overlay> p_overlays) {
for (Overlay m_overlay : p_overlays) {
if (m_overlay instanceof MapendPointsOverlay && m_overlay != this) {
((MapendPointsOverlay) m_overlay).hideBalloon();
}
}
}
/**
* Override this method to handle a "tap" on a balloon. By default, does
* nothing and returns false.
*
* #param p_index
* - The index of the item whose balloon is tapped.
* #return true if you handled the tap, otherwise false.
*/
protected boolean onBalloonTap(int p_index) {
return false;
}
}
BallonOverlay class that open the information window.
public class BalloonOverlayView extends FrameLayout
{
private LinearLayout m_layout;
private TextView m_title;
private TextView m_snippet;
/**
* Create a new BalloonOverlayView.
*
* #param p_context
* - The activity context.
* #param p_balloonBottomOffset
* - The bottom padding (in pixels) to be applied when rendering this view.
*/
public BalloonOverlayView(Context p_context, int p_balloonBottomOffset)
{
super(p_context);
// m_ctx = context;
setPadding(10, 0, 10, p_balloonBottomOffset);
m_layout = new LinearLayout(p_context);
m_layout.setVisibility(VISIBLE);
LayoutInflater m_inflater = (LayoutInflater) p_context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
View m_view = m_inflater.inflate(R.layout.balloonoverlay, m_layout);
m_title = (TextView) m_view.findViewById(R.id.balloon_item_title);
m_snippet = (TextView) m_view.findViewById(R.id.balloon_item_snippet);
m_snippet.setVisibility(View.GONE);
ImageView m_close = (ImageView) m_view.findViewById(R.id.close_img_button);
m_close.setOnClickListener(new OnClickListener(){
public void onClick(View v)
{
m_layout.setVisibility(GONE);
}
});
FrameLayout.LayoutParams m_params = new FrameLayout.LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
m_params.gravity = Gravity.NO_GRAVITY;
addView(m_layout, m_params);
}
}
Related
this is my code i m successfully zooming from center but i want to zoom in from the touch coordinates like instagram image zoom.I tried this code till now.Help me through it please.
ZoomImageActivity.java
public class ZoomImageActivity extends AppCompatActivity {
ImageView ivBG;
private ZoomImageHelper imageZoomHelper;
private View zoomableView = null;
View.OnTouchListener zoomTouchListener = new View.OnTouchListener() {
#Override
public boolean onTouch(View view, MotionEvent ev) {
switch (ev.getAction() & MotionEvent.ACTION_MASK) {
case MotionEvent.ACTION_MOVE:
if (ev.getPointerCount() == 2 && zoomableView == null)
zoomableView = view;
break;
}
return false;
}
};
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_zoom_image);
ivBG = (ImageView) findViewById(R.id.ivBG);
ivBG.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
}
});
ivBG.setOnTouchListener(zoomTouchListener);
imageZoomHelper = new ZoomImageHelper(this, tvParam);
imageZoomHelper.addOnZoomListener(new ZoomImageHelper.OnZoomListener() {
#Override
public void onImageZoomStarted(View view) {
}
#Override
public void onImageZoomEnded(View view) {
zoomableView = null;
}
});
}
#Override
public boolean dispatchTouchEvent(MotionEvent ev) {
return imageZoomHelper.onDispatchTouchEvent(ev, zoomableView) || super.dispatchTouchEvent(ev);
}}
ZoomImageHelper.java
public class ZoomImageHelper {
private View zoomableView = null;
private ViewGroup parentOfZoomableView;
private ViewGroup.LayoutParams zoomableViewLP;
private FrameLayout.LayoutParams zoomableViewFrameLP;
private Dialog dialog;
private View placeholderView;
private int viewIndex;
private View darkView;
private double originalDistance;
private int[] twoPointCenter;
private int[] originalXY;
private WeakReference<Activity> activityWeakReference;
private boolean isAnimatingDismiss = false;
private List<OnZoomListener> zoomListeners = new ArrayList<>();
public ZoomImageHelper(Activity activity) {
this.activityWeakReference = new WeakReference<>(activity);
}
public boolean onDispatchTouchEvent(MotionEvent ev, View view) {
Activity activity;
if ((activity = activityWeakReference.get()) == null)
return false;
if (ev.getPointerCount() == 2) {
if (zoomableView == null) {
if (view != null) {
zoomableView = view;
// get view's original location relative to the window
originalXY = new int[2];
view.getLocationInWindow(originalXY);
// this FrameLayout will be the zoomableView's temporary parent
FrameLayout frameLayout = new FrameLayout(view.getContext());
// this view is to gradually darken the backdrop as user zooms
darkView = new View(view.getContext());
darkView.setBackgroundColor(Color.BLACK);
darkView.setAlpha(0f);
// adding darkening backdrop to the frameLayout
frameLayout.addView(darkView, new FrameLayout.LayoutParams(
FrameLayout.LayoutParams.MATCH_PARENT,
FrameLayout.LayoutParams.MATCH_PARENT));
// the Dialog that will hold the FrameLayout
dialog = new Dialog(activity,
android.R.style.Theme_Translucent_NoTitleBar_Fullscreen);
dialog.addContentView(frameLayout,
new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT,
ViewGroup.LayoutParams.MATCH_PARENT));
dialog.show();
// get the parent of the zoomable view and get it's index and layout param
parentOfZoomableView = (ViewGroup) zoomableView.getParent();
viewIndex = parentOfZoomableView.indexOfChild(zoomableView);
this.zoomableViewLP = zoomableView.getLayoutParams();
// this is the new layout param for the zoomableView
zoomableViewFrameLP = new FrameLayout.LayoutParams(
view.getWidth(), view.getHeight());
zoomableViewFrameLP.leftMargin = originalXY[0];
zoomableViewFrameLP.topMargin = originalXY[1];
// this view will hold the zoomableView's position temporarily
placeholderView = new View(activity);
// setting placeholderView's background to zoomableView's drawingCache
// this avoids flickering when adding/removing views
zoomableView.setDrawingCacheEnabled(true);
BitmapDrawable placeholderDrawable = new BitmapDrawable(
activity.getResources(),
Bitmap.createBitmap(zoomableView.getDrawingCache()));
if (Build.VERSION.SDK_INT >= 16) {
placeholderView.setBackground(placeholderDrawable);
} else {
placeholderView.setBackgroundDrawable(placeholderDrawable);
}
// placeholderView takes the place of zoomableView temporarily
parentOfZoomableView.addView(placeholderView, zoomableViewLP);
// zoomableView has to be removed from parent view before being added to it's
// new parent
parentOfZoomableView.removeView(zoomableView);
frameLayout.addView(zoomableView, zoomableViewFrameLP);
// using a post to remove placeholder's drawing cache
zoomableView.post(new Runnable() {
#Override
public void run() {
if (dialog != null) {
if (Build.VERSION.SDK_INT >= 16) {
placeholderView.setBackground(null);
} else {
placeholderView.setBackgroundDrawable(null);
}
zoomableView.setDrawingCacheEnabled(false);
}
}
});
// Pointer variables to store the original touch positions
MotionEvent.PointerCoords pointerCoords1 = new MotionEvent.PointerCoords();
ev.getPointerCoords(0, pointerCoords1);
MotionEvent.PointerCoords pointerCoords2 = new MotionEvent.PointerCoords();
ev.getPointerCoords(1, pointerCoords2);
// storing distance between the two positions to be compared later on for
// zooming
originalDistance = (int) getDistance(pointerCoords1.x, pointerCoords2.x,
pointerCoords1.y, pointerCoords2.y);
// storing center point of the two pointers to move the view according to the
// touch position
twoPointCenter = new int[]{
(int) ((pointerCoords2.x + pointerCoords1.x) / 2),
(int) ((pointerCoords2.y + pointerCoords1.y) / 2)
};
sendZoomEventToListeners(zoomableView, true);
return true;
}
} else {
MotionEvent.PointerCoords pointerCoords1 = new MotionEvent.PointerCoords();
ev.getPointerCoords(0, pointerCoords1);
MotionEvent.PointerCoords pointerCoords2 = new MotionEvent.PointerCoords();
ev.getPointerCoords(1, pointerCoords2);
int[] newCenter = new int[]{
(int) ((pointerCoords2.x + pointerCoords1.x) / 2),
(int) ((pointerCoords2.y + pointerCoords1.y) / 2)
};
int currentDistance = (int) getDistance(pointerCoords1.x, pointerCoords2.x,
pointerCoords1.y, pointerCoords2.y);
double pctIncrease = (currentDistance - originalDistance) / originalDistance;
zoomableView.setScaleX((float) (1 + pctIncrease));
zoomableView.setScaleY((float) (1 + pctIncrease));
updateZoomableViewMargins(newCenter[0] - twoPointCenter[0] + originalXY[0],
newCenter[1] - twoPointCenter[1] + originalXY[1]);
darkView.setAlpha((float) (pctIncrease / 8));
return true;
}
} else {
if (zoomableView != null && !isAnimatingDismiss) {
isAnimatingDismiss = true;
ValueAnimator valueAnimator = ValueAnimator.ofFloat(0f, 1f);
valueAnimator.setDuration(activity.getResources()
.getInteger(android.R.integer.config_shortAnimTime));
valueAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
float scaleYStart = zoomableView.getScaleY();
float scaleXStart = zoomableView.getScaleX();
int leftMarginStart = zoomableViewFrameLP.leftMargin;
int topMarginStart = zoomableViewFrameLP.topMargin;
float alphaStart = darkView.getAlpha();
float scaleYEnd = 1f;
float scaleXEnd = 1f;
int leftMarginEnd = originalXY[0];
int topMarginEnd = originalXY[1];
float alphaEnd = 0f;
#Override
public void onAnimationUpdate(ValueAnimator valueAnimator) {
float animatedFraction = valueAnimator.getAnimatedFraction();
if (animatedFraction < 1) {
zoomableView.setScaleX(((scaleXEnd - scaleXStart) * animatedFraction) +
scaleXStart);
zoomableView.setScaleY(((scaleYEnd - scaleYStart) * animatedFraction) +
scaleYStart);
updateZoomableViewMargins(
((leftMarginEnd - leftMarginStart) * animatedFraction) +
leftMarginStart,
((topMarginEnd - topMarginStart) * animatedFraction) +
topMarginStart);
darkView.setAlpha(((alphaEnd - alphaStart) * animatedFraction) +
alphaStart);
} else {
dismissDialogAndViews();
}
}
});
valueAnimator.start();
return true;
}
}
return false;
}
void updateZoomableViewMargins(float left, float top) {
if (zoomableView != null && zoomableViewFrameLP != null) {
zoomableViewFrameLP.leftMargin = (int) left;
zoomableViewFrameLP.topMargin = (int) top;
zoomableView.setLayoutParams(zoomableViewFrameLP);
}
}
/**
* Dismiss dialog and set views to null for garbage collection
*/
private void dismissDialogAndViews() {
sendZoomEventToListeners(zoomableView, false);
if (zoomableView != null) {
zoomableView.setVisibility(View.VISIBLE);
zoomableView.setDrawingCacheEnabled(true);
BitmapDrawable placeholderDrawable = new BitmapDrawable(
zoomableView.getResources(),
Bitmap.createBitmap(zoomableView.getDrawingCache()));
if (Build.VERSION.SDK_INT >= 16) {
placeholderView.setBackground(placeholderDrawable);
} else {
placeholderView.setBackgroundDrawable(placeholderDrawable);
}
ViewGroup parent = (ViewGroup) zoomableView.getParent();
parent.removeView(zoomableView);
this.parentOfZoomableView.addView(zoomableView, viewIndex, zoomableViewLP);
this.parentOfZoomableView.removeView(placeholderView);
zoomableView.setDrawingCacheEnabled(false);
zoomableView.post(new Runnable() {
#Override
public void run() {
dismissDialog();
}
});
zoomableView = null;
} else {
dismissDialog();
}
isAnimatingDismiss = false;
}
public void addOnZoomListener(OnZoomListener onZoomListener) {
zoomListeners.add(onZoomListener);
}
public void removeOnZoomListener(OnZoomListener onZoomListener) {
zoomListeners.remove(onZoomListener);
}
private void sendZoomEventToListeners(View zoomableView, boolean zoom) {
for (OnZoomListener onZoomListener : zoomListeners) {
if (zoom)
onZoomListener.onImageZoomStarted(zoomableView);
else
onZoomListener.onImageZoomEnded(zoomableView);
}
}
private void dismissDialog() {
if (dialog != null) {
dialog.dismiss();
dialog = null;
}
darkView = null;
resetOriginalViewAfterZoom();
}
private void resetOriginalViewAfterZoom() {
zoomableView.invalidate();
zoomableView = null;
}
/**
* Get distance between two points
*
* #param x1
* #param x2
* #param y1
* #param y2
* #return distance
*/
private double getDistance(double x1, double x2, double y1, double y2) {
return Math.sqrt(Math.pow(x2 - x1, 2) + Math.pow(y2 - y1, 2));
}
public interface OnZoomListener {
void onImageZoomStarted(View view);
void onImageZoomEnded(View view);
}}
I need the image to zoom and pan from its touch coordinates not from center.. Thanks in advance.
I am creating a floor map with n number of dynamic buttons with incremental value and added to a custom relative layout. Now i need to create onclicklistner for each buttons added to a view. How to get the id or some unique value to identify which button is clicked. Can somebody please help me on this i am breaking my head for the past 10 days. Thanks in advance.
This is my Custom Relative layout :
public class InteractiveView extends RelativeLayout implements OnClickListener{
Matrix matrix = new Matrix();
private float mPositionX = 0;
private float mPositionY = 0;
private float mScale = 0.1f;
private Context context;
private boolean canvasFlag = true;
public InteractiveView(Context context) {
super(context);
this.context = context;
this.setWillNotDraw(false);
// this.setOnTouchListener(mTouchListener);
this.setOnClickListener(this);
}
public void setPosition(float lPositionX, float lPositionY){
mPositionX = lPositionX;
mPositionY = lPositionY;
}
public void setMovingPosition(float lPositionX, float lPositionY){
mPositionX += lPositionX;
mPositionY += lPositionY;
}
public void setScale(float lScale){
mScale = lScale;
}
protected void dispatchDraw(Canvas canvas) {
canvas.save();
// canvas.setMatrix(matrix);
Log.e("Canvas Height ",canvas.getWidth()+" "+canvas.getHeight());
Log.e("Canvas Height ",getWidth() /14 +" "+getHeight()/12 );
Log.e("Canvas Density "," "+canvas.getDensity() );
canvas.translate(mPositionX*mScale, mPositionY*mScale);
canvas.translate(getWidth() / 14,getHeight() / 12);
if (mScale < 0.10)
mScale = 0.1f;
canvas.scale(mScale, mScale);
Log.e("Scale : ",mScale+" ");
super.dispatchDraw(canvas);
canvas.restore();
}
// touch events
private final int NONE = 0;
private final int DRAG = 1;
private final int ZOOM = 2;
private final int CLICK = 3;
// pinch to zoom
private float mOldDist;
private float mNewDist;
private float mScaleFactor = 0.01f;
// position
private float mPreviousX;
private float mPreviousY;
int mode = NONE;
#SuppressWarnings("deprecation")
public OnTouchListener mTouchListener = new OnTouchListener(){
public boolean onTouch(View v, MotionEvent e) {
/*Button button = (Button)v;
Log.e("Button Text : "," "+button.getText().toString());
*/
float x = e.getX();
float y = e.getY();
switch (e.getAction()) {
case MotionEvent.ACTION_DOWN: // one touch: drag
mode = CLICK;
break;
case MotionEvent.ACTION_POINTER_2_DOWN: // two touches: zoom
mOldDist = spacing(e);
mode = ZOOM; // zoom
break;
case MotionEvent.ACTION_UP: // no mode
mode = NONE;
break;
case MotionEvent.ACTION_POINTER_2_UP: // no mode
mode = NONE;
break;
case MotionEvent.ACTION_MOVE: // rotation
if (e.getPointerCount() > 1 && mode == ZOOM) {
/*mNewDist = spacing(e) - mOldDist;
mScale += mNewDist*mScaleFactor;
invalidate();
mOldDist = spacing(e); */
} else if (mode == CLICK || mode == DRAG) {
float dx = (x - mPreviousX)/mScale;
float dy = (y - mPreviousY)/mScale;
setMovingPosition(dx, dy);
invalidate();
mode = DRAG;
}
break;
}
mPreviousX = x;
mPreviousY = y;
return true;
}
};
// finds spacing
private float spacing(MotionEvent event) {
float x = event.getX(0) - event.getX(1);
float y = event.getY(0) - event.getY(1);
return FloatMath.sqrt(x * x + y * y)/4;
}
This is my fragment class where i create floor map :
public class FloorMapFragment extends Fragment implements OnClickListener {
ViewGroup root;
Button exhibitor;
ZoomControls zoom;
int id = 0;
float dx=0,dy=0,x=0,y=0;
InteractiveView mInteractiveView;
int startX, startY;
boolean isClicked = false;
int unit = 100;
int incremental = 100;
int new_X;
int i;
int new_Width = new_X + incremental;
int new_Y;
int new_Hight = new_Y + incremental;
int leftMargin, topMargin;
int orange = Color.parseColor("#C0680F");
int maroon = Color.parseColor("#5F0C0C");
int pink = Color.parseColor("#F45C91");
int moov = Color.parseColor("#6E4689");
int gray = Color.parseColor("#777777");
int red = Color.parseColor("#E31E26");
int blue = Color.parseColor("#3A53A4");
int green = Color.parseColor("#70BD59");
int cyan = Color.parseColor("#70CDDD");
RelativeLayout r;
// View mainView = null;
// Remember some things for zooming
PointF start = new PointF();
PointF mid = new PointF();
float oldDist = 1f;
PointF oldDistPoint = new PointF();
public static String TAG = "ZOOM";
int mScreenWidth = 0;
int mScreenHeight= 0;
static final int NONE = 0;
static final int DRAG = 1;
static final int ZOOM = 2;
int mode = NONE;
enum Direction {
LEFT, RIGHT, UP, DOWN
};
FloorListner listner;
#SuppressWarnings("deprecation")
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
root = (ViewGroup) inflater.inflate(R.layout.floor_main, null);
// mainView = (RelativeLayout)root.findViewById(R.id.zoom_layout);
r = (RelativeLayout) root.findViewById(R.id.my_relative_layout);
zoom = (ZoomControls)root. findViewById(R.id.zoomControls1);
mScreenWidth = r.getWidth();
/*MainActivity.activity.getResources()
.getDisplayMetrics().widthPixels;*/
mScreenHeight = r.getHeight();
/*MainActivity.activity.getResources()
.getDisplayMetrics().heightPixels; */
RelativeLayout.LayoutParams layoutParams = new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.FILL_PARENT,
RelativeLayout.LayoutParams.FILL_PARENT);
layoutParams.height = 75;
layoutParams.width = 57;
// layoutParams.bottomMargin = 100;
// layoutParams.setMargins(0, 0, 0, 100);
// layoutParams.setMargins(-220, 0, 0, 0);
/*ImageView lImageView = new ImageView(MainActivity.activity);
lImageView.setLayoutParams(new RelativeLayout.LayoutParams(-1,-1));
lImageView.setImageResource(R.drawable.transparentimage);;*/
mInteractiveView = new InteractiveView(MainActivity.activity);
// mInteractiveView.setOnClickListener(this);
// mInteractiveView.setOnTouchListener(mTouchListener);
// mInteractiveView.setLayoutParams(new RelativeLayout.LayoutParams(-5,-5 ));
// mInteractiveView.setLayoutParams(layoutParams);
// mInteractiveView.setPosition(-mScreenWidth/2, -mScreenHeight/2);
zoom.setOnZoomInClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
float x = r.getScaleX();
float y = r.getScaleY();
Log.e("Zoon In Listener : ", "X Scale : "+ x );
Log.e("Zoon In Listener : ", "Y Scale : "+ y );
Log.e("Zoon In Width : ", "X Scale : "+ r.getWidth() );
Log.e("Zoon In Height : ", "Y Scale : "+ r.getHeight() );
if (x <= 6.0 && y <= 6.0){
r.setScaleX((float) (x + 0.5));
r.setScaleY((float) (y + 0.5));
}
}
});
zoom.setOnZoomOutClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
float x = r.getScaleX();
float y = r.getScaleY();
Log.e("Zoon Out Listener : ", "X Scale : "+ x );
Log.e("Zoon Out Listener : ", "Y Scale : "+ y );
if (x > 1.0 && y > 1.0){
r.setScaleX((float) (x - 0.5));
r.setScaleY((float) (y - 0.5));
}
}
});
ProgressDialog d = new ProgressDialog(getActivity());
d.setMessage("Loading Map");
d.show();
draw();
d.dismiss();
/*
mInteractiveView.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
}
});*/
/*for( i=0; i<((ViewGroup)mInteractiveView).getChildCount(); ++i) {
View nextChild = ((ViewGroup)mInteractiveView).getChildAt(i);
try {
final Button b = (Button) nextChild;
Log.e("Button Text : ", " : "+b.getText().toString());
b.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
int index = ((ViewGroup)b.getParent()).indexOfChild(b);
Log.e("Button get Id : ", ""+v.getTag().toString());
}
});
} catch (Exception e) {
}
}*/
//
// mInteractiveView.addView(lImageView);
// r.setLayoutParams(layoutParams);
r.addView(mInteractiveView);
/* ExhibitorDAO dao = new ExhibitorDAO(getActivity());
workAround(dao, "K19");*/
/* Fragment fragment = new NewsFragment();
FragmentTransaction trans = ;
trans.addToBackStack(null);
trans.replace(R.id.main, fragment);
trans.commit();*/
// r.setOnTouchListener(MyOnTouchListener);
// r.setLayoutParams(layoutParams);
Log.e("Width And Height : ", "Width : "+r.getLayoutParams().width+ " : Height :"+r.getLayoutParams().height);
return root;
}
private OnTouchListener mTouchListener = new OnTouchListener(){
#Override
public boolean onTouch(View v, MotionEvent event) {
switch (event.getAction() & MotionEvent.ACTION_MASK) {
case MotionEvent.ACTION_DOWN:
isClicked = true;
x = event.getX();
y = event.getY();
dx = x-r.getX();
dy = y-r.getY();
break;
case MotionEvent.ACTION_UP:
if (isClicked){
isClicked = false;
/*Button b = (Button) v;
ExhibitorDAO dao = new ExhibitorDAO(getActivity());
workAround(dao,b.getText().toString());*/
}
break;
case MotionEvent.ACTION_POINTER_UP:
isClicked = false;
break;
case MotionEvent.ACTION_POINTER_DOWN:
isClicked = false;
break;
case MotionEvent.ACTION_MOVE:
r.setX(event.getX()-dx);
r.setY(event.getY()-dy);
isClicked = false;
break;
default:
break;
}
return false;
}
};
private void decreaseXBy(int i) {
new_X = new_X - (2 * i);
}
private void reset() {
new_X = 0;
new_Y += incremental;
;
}
private void drawingH(Direction direction, float width) {
if (direction == direction.RIGHT) {// means go to right direction{
new_X += (incremental * width);
} else if (direction == direction.LEFT) { // means go to left
new_X -= (incremental * width);
}
}
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
Button b = (Button) v;
ExhibitorDAO dao = new ExhibitorDAO(getActivity());
try{
Exhibitor exhibitor = new Exhibitor();
Log.e("Button Text : ", " : "+b.getText());
if (!b.getText().equals("")) {
Logger.log("floor:");
exhibitor = dao.getExhibitorByBooth(b.getText().toString());
ExhibitorApplication ex = new ExhibitorApplication();
ex.exhibitor = exhibitor;
if (exhibitor != null){
listner.Onfloorclick();
ex.fav_exhibitor = 4 ;
Logger.log("floor:"+ex.exhibitor.Exhibitor_FileNumber);
}
else
{
Logger.log("floor:"+ex.exhibitor.Exhibitor_FileNumber);
}
}
{
Logger.log("floor:no data");
}
}
catch(Exception ex)
{
Toast.makeText(getActivity(), "No Information "+ex.getMessage(), Toast.LENGTH_SHORT).show();
}
}
public Button drawExhibitor(float width, int height, int color,
String label, String fileNumber, Direction d) {
exhibitor = new Button(getActivity());
// exhibitor.setOnClickListener(this);
// exhibitor.setOnTouchListener(MyOnTouchListener);
if (color == Color.BLUE)
exhibitor.setBackgroundColor(Color.parseColor("#56A5EC"));
if (color == Color.WHITE)
exhibitor.setAlpha(0);
else
exhibitor.setBackgroundColor(color);
// exhibitor.setId(id);
// id++;
exhibitor.setText(label);
exhibitor.setTextSize(8);
// exhibitor.setId(foo);
exhibitor.setTag(label);
exhibitor.setTypeface(Typeface.DEFAULT_BOLD);
exhibitor.setGravity(Gravity.CENTER);
exhibitor.setTextColor(Color.WHITE);
/*exhibitor.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
Log.e("Button get Id : ", ""+exhibitor.getId());
}
});*/
exhibitor.setOnTouchListener(mTouchListener);
leftMargin = new_X;
topMargin = new_Y;
drawingH(d, width);
InteractiveView.LayoutParams params = new InteractiveView.LayoutParams(
(int) (width * incremental), height * incremental);
params.leftMargin = leftMargin;
params.topMargin = topMargin;
mInteractiveView.addView(exhibitor, params);
params = null;
if (color != Color.WHITE) {
drawingHSpace();
}
return exhibitor;
}
#Override
public void onAttach(Activity activity) {
super.onAttach(activity);
if (activity instanceof FloorListner) {
listner = (FloorListner) activity;
} else {
throw new ClassCastException(activity.toString()
+ " must implemenet MyListFragment.OnItemSelectedListener");
}
}
private void drawingHSpace() {
new_X += 2;
}
private void drawingHSpace(float t) {
new_X = (int) (new_X + (2 * t));
}
private void drawingVSpace() {
new_Y += 2;
}
private void removeDrawingVSpace() {
new_Y -= 2;
}
private void decreaseXBy(float i) {
new_X = (int) (new_X - (2 * i));
}
private void drawLabel(float width, int height, int color, int drawable, Direction d) {
// TODO Auto-generated method stub
TextView image = new TextView(getActivity());
//image.setText(label);
image.setBackgroundResource(drawable);
image.setGravity(Gravity.CENTER);
image.setTextSize(20);
image.setTypeface(Typeface.DEFAULT_BOLD);
//image.setTextColor(color);
// image.setOnTouchListener(MyOnTouchListener);
leftMargin = new_X;
topMargin = new_Y;
drawingH(d,width);
InteractiveView.LayoutParams params = new InteractiveView.LayoutParams(
(int)(width * incremental), height * incremental);
params.leftMargin = leftMargin;
params.topMargin = topMargin;
mInteractiveView.addView(image, params);
}
private void drawLabel(float width, int height, int color, String label, Direction d) {
// TODO Auto-generated method stub
TextView image = new TextView(getActivity());
image.setText(label);
image.setGravity(Gravity.CENTER);
image.setTextSize(20);
image.setTypeface(Typeface.DEFAULT_BOLD);
image.setTextColor(color);
// image.setOnTouchListener(mTouchListener);
leftMargin = new_X;
topMargin = new_Y;
drawingH(d,width);
InteractiveView.LayoutParams params = new InteractiveView.LayoutParams(
(int)(width * incremental), height * incremental);
params.leftMargin = leftMargin;
params.topMargin = topMargin;
mInteractiveView.addView(image, params);
}
private void draw() {
drawExhibitor(28.5F, 3, Color.WHITE, "", "", Direction.RIGHT);
drawLabel(2, 3, blue, R.drawable.al_mamzar, Direction.RIGHT);
reset();
reset();
drawExhibitor(16.5F, 1, Color.WHITE, "", "", Direction.RIGHT);
drawLabel(2, 1, blue, R.drawable.business_center, Direction.RIGHT);
drawExhibitor(4.65F, 1, Color.WHITE, "", "", Direction.RIGHT);
drawLabel(1, 1, blue, R.drawable.bath_f, Direction.RIGHT);
drawExhibitor(14F, 1, Color.WHITE, "", "", Direction.RIGHT);
drawLabel(1, 1, blue, R.drawable.bath_m, Direction.RIGHT);
//reset();
reset();
drawingVSpace();
drawingVSpace();
}
}
Finally i am adding the Interactive View to a relative layout.
As you will find it in the documentation that each view can have an id (using setId (int id) or from xml android:id ) or tag(using setTag (int key)) associated with it and later on you can get that id or tag via getId() or getTag().
Now before you actually retrieve any id for a view at first you have to set an id for that specific view either via programmatically or via xml.
If you don't specify any id for a view and you are trying get that view's id you will get NO_ID.
As per documentation: getId () returns this view's identifier.A positive integer used to identify the view or NO_ID if the view has no ID.
Now to address your problem, before you add a button to your viewgroup assign a unique id to that button.
To illustrate more here is an example:
public class MainActivity extends Activity {
private LinearLayout mRootLayout;
private OnClickListener mOnClickListener = new OnClickListener() {
#Override
public void onClick(View arg0) {
// TODO Auto-generated method stub
Log.e("mButton "," onClick");
Toast.makeText(MainActivity.this, " "+arg0.getId(), Toast.LENGTH_LONG).show();
}
};
#Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mRootLayout = (LinearLayout)findViewById(R.id.mRootLayout);
for(int i = 0;i<10;i++){
Button mButton = new Button(this);
mButton.setText("Button "+i);
mButton.setId(i);
if(i<9){
mButton.setOnClickListener(mOnClickListener);
}
mRootLayout.addView(mButton);
}
Button testFindButton = (Button)mRootLayout.findViewById(9);
testFindButton.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
Log.e("testFindButton "," onClick");
Toast.makeText(MainActivity.this, " testFindButton "+v.getId(), Toast.LENGTH_LONG).show();
}
});
}
}
You can use the setTag method for each button, to set an id. Then in the onClick method, retrieve that value, and execute the code related to that button.
Some code (not tested):
private OnClickListener listener = new OnClickListener()
{
#Override
public void onClick(View v)
{
int id = (Integer)v.getTag();
switch (id)
{
case 1: break;
....
}
}
});
for (int i=0 ; i<N ; i++)
{
yourbutton.setTag(Integer.valueOf(i));
yourbutton.setOnClickListener(listener);
}
I try to make an app with multitouching and I use this code:
Multitouchng code
It works, but I've got problem, because in my app I've got HorizontalScrollView (HSV) and when I press buttons from begining of HSV I've got buttons Id (View.getId()) in "downTouchedViewsIndex", but when I scroll my HSV and press any button I have only layout's Id - nothing about buttons.
My touch code:
package com.lacrima.pianoo;
public class MainActivity extends Activity implements SeekBar.OnSeekBarChangeListener, OnTouchListener {
static private String TAG = "MainActivity";
public View parent;
private final ArrayList[] recentTouchedViewsIndex = new ArrayList[10];
private final ArrayList[] downTouchedViewsIndex = new ArrayList[10];
private final ArrayList<View> moveOutsideEnabledViews = new ArrayList<View>();
private List<Integer> list = new ArrayList<Integer>();
private final int mTouchSlop = 24;
AssetFileDescriptor des; // deskryptor do opisu wczytywanego pliku muzycznego (miejsce gdzie jesta zapisany dlugość i inne takie)
MediaPlayer[] mp = new MediaPlayer[36];// = new MediaPlayer();
//Pierwsza oktawa
Button button1, button2, button3, button4, button5, button6, button7;
Button button1_5, button2_5, button4_5, button5_5, button6_5;
//Druga oktawa
Button button8, button9, button10, button11, button12, button13, button14;
Button button8_5, button9_5, button11_5, button12_5, button13_5;
//Trzecia oktawa
Button button15, button16, button17, button18, button19, button20, button21;
Button button15_5, button16_5, button18_5, button19_5, button20_5;
SamplePlayer sound;
Integer[] soundIDs = new Integer[36];
private boolean[] whitePlays = new boolean[21];
private boolean[] blackPlays = new boolean[15];
private View[] whiteViews = new View[21];
private View[] blackViews = new View[15];
private int lastButton;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
requestWindowFeature(Window.FEATURE_NO_TITLE);
getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN, WindowManager.LayoutParams.FLAG_FULLSCREEN);
setContentView(R.layout.activity_main);
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE); //Ustawienie ekranu horuzontalnie na sztywno
this.setVolumeControlStream(AudioManager.STREAM_MUSIC);
parent = findViewById(android.R.id.content).getRootView();
parent.setOnTouchListener(this);
SeekBar seek = (SeekBar) findViewById(R.id.seekBar);
final LockedHorizontalScrollView hsv = (LockedHorizontalScrollView)findViewById(R.id.hsv);
seek.setMax(948);
seek.setProgress(474);
seek.setOnSeekBarChangeListener(this);
hsv.post(new Runnable() {
#Override
public void run() {
hsv.scrollTo(474, 0);
}
});
sound = new SamplePlayer(this);
falsePlays();
buttonListeners();
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.activity_main, menu);
return true;
}
#Override
public void onProgressChanged(SeekBar seekBar, int progress, boolean fromTouch) {
LockedHorizontalScrollView hsv = (LockedHorizontalScrollView)findViewById(R.id.hsv);
hsv.scrollTo(progress, 0);
}
#Override
public void onStartTrackingTouch(SeekBar seekBar) {
//uruchamiane w momencie kliknięcia na suwak
Log.d(TAG, "Tracking on");
}
#Override
public void onStopTrackingTouch(SeekBar seekBar) {
//uruchamiane w momencie odkliknięcia suwaka
Log.d(TAG, "Tracking off");
}
#Override
protected void onDestroy() {
sound.release();
super.onDestroy();
}
#Override
public boolean onTouch(View v, MotionEvent event) {
// index of the pointer which starts this Event
final int actionPointerIndex = event.getActionIndex();
// resolve the action as a basic type (up, down or move)
int actionResolved = event.getAction() & MotionEvent.ACTION_MASK;
if (actionResolved < 7 && actionResolved > 4) {
actionResolved = actionResolved - 5;
}
if (actionResolved == MotionEvent.ACTION_DOWN || actionResolved == MotionEvent.ACTION_UP
|| actionResolved == MotionEvent.ACTION_CANCEL) {
dealEvent(actionPointerIndex, event, v, actionResolved);
}
return true;
}
private void dealEvent(final int actionPointerIndex, final MotionEvent event, final View eventView,
final int actionResolved) {
int rawX, rawY;
final int location[] = { 0, 0 };
eventView.getLocationOnScreen(location);
// Log.v("tag", location + "");
rawX = (int) event.getX(actionPointerIndex) + location[0];
rawY = (int) event.getY(actionPointerIndex) + location[1];
final int actionPointerID = event.getPointerId(actionPointerIndex);
ArrayList<View> hoverViews = getTouchedViews(rawX, rawY);
if (actionResolved == MotionEvent.ACTION_DOWN) {
downTouchedViewsIndex[actionPointerID] = (ArrayList<View>) hoverViews.clone();
lastButton = hoverViews.get(k-1).getId();
}
if(actionResolved == MotionEvent.ACTION_UP){
int k = hoverViews.size();
Log.d("klop", "Odklijniecie: " + hoverViews.get(k-1).getId());
lastButton = eventView.getId();
}
// deletes all views which where not clicked on ActionDown
if (downTouchedViewsIndex[actionPointerID] != null) {
final ArrayList<View> tempViews = (ArrayList<View>) hoverViews.clone();
tempViews.removeAll(downTouchedViewsIndex[actionPointerID]);
hoverViews.removeAll(tempViews);
}
if (recentTouchedViewsIndex[actionPointerID] != null) {
final ArrayList<View> recentTouchedViews = recentTouchedViewsIndex[actionPointerID];
final ArrayList<View> shouldTouchViews = (ArrayList<View>) hoverViews.clone();
if (!shouldTouchViews.containsAll(recentTouchedViews)) {
shouldTouchViews.removeAll(recentTouchedViews);
shouldTouchViews.addAll(recentTouchedViews);
final ArrayList<View> outsideTouchedViews = (ArrayList<View>) shouldTouchViews.clone();
outsideTouchedViews.removeAll(hoverViews);
}
recentTouchedViewsIndex[actionPointerID] = hoverViews;
hoverViews = shouldTouchViews;
} else {
recentTouchedViewsIndex[actionPointerID] = hoverViews;
}
if (actionResolved == MotionEvent.ACTION_UP) {
recentTouchedViewsIndex[actionPointerID] = null;
downTouchedViewsIndex[actionPointerID] = null;
}
for (final View view : hoverViews) {
int x, y;
view.getLocationOnScreen(location);
x = rawX - location[0];
y = rawY - location[1];
// View does not recognize that the Pointer is
// outside if the Pointer is not far away (>mTouchSlop)
if (recentTouchedViewsIndex[actionPointerID] != null) {
if (pointInView(x, y, mTouchSlop, view.getWidth(), view.getHeight())) {
if (!recentTouchedViewsIndex[actionPointerID].contains(view)) {
recentTouchedViewsIndex[actionPointerID].add(view);
}
} else if (moveOutsideEnabledViews.contains(view)) {
Log.v("tag", "outside but gets event");
recentTouchedViewsIndex[actionPointerID].add(view);
}
}
final MotionEvent me = MotionEvent.obtain(event.getDownTime(), event.getEventTime(), actionResolved, x, y,
event.getPressure(actionPointerIndex), event.getPressure(actionPointerIndex), event.getMetaState(),
event.getXPrecision(), event.getYPrecision(), event.getDeviceId(), event.getEdgeFlags());
me.setLocation(x, y);
if (!me.equals(event)) {
// deals the Event
view.onTouchEvent(me);
}
// debug
if (actionResolved == MotionEvent.ACTION_MOVE) {
Log.v("tag", "#" + actionPointerIndex + " Rawx:" + rawX + " rawy:" + rawY + " x:" + x + " y:" + y + " "
+ view.toString());
}
}
}
private ArrayList<View> getTouchedViews(final int x, final int y) {
final ArrayList<View> touchedViews = new ArrayList<View>();
final ArrayList<View> possibleViews = new ArrayList<View>();
if (parent instanceof ViewGroup) {
possibleViews.add(parent);
for (int i = 0; i < possibleViews.size(); i++) {
final View view = possibleViews.get(i);
final int location[] = { 0, 0 };
view.getLocationOnScreen(location);
if (((view.getHeight() + location[1] >= y) & (view.getWidth() + location[0] >= x) & (view.getLeft() <= x) & (view
.getTop() <= y)) || view instanceof FrameLayout) {
touchedViews.add(view);
possibleViews.addAll(getChildViews(view));
}
}
}
return touchedViews;
}
private ArrayList<View> getChildViews(final View view) {
final ArrayList<View> views = new ArrayList<View>();
if (view instanceof ViewGroup) {
final ViewGroup v = ((ViewGroup) view);
if (v.getChildCount() > 0) {
for (int i = 0; i < v.getChildCount(); i++) {
views.add(v.getChildAt(i));
}
}
}
return views;
}
private boolean pointInView(final float localX, final float localY, final float slop, final float width,
final float height) {
return localX >= -slop && localY >= -slop && localX < ((width) + slop) && localY < ((height) + slop);
}
public void addMoveOutsideEnabledViews(final View view) {
moveOutsideEnabledViews.add(view);
}
And xml file:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:background="#0A0A0A"
android:orientation="vertical" >
<SeekBar
android:id="#+id/seekBar"
android:layout_width="fill_parent"
android:layout_height="53dp" />
<com.lacrima.pianoo.LockedHorizontalScrollView
android:id="#+id/hsv"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:scrollbars="none" >
<RelativeLayout
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:orientation="horizontal" >
<Button...
</RelativeLayout>
</com.lacrima.pianoo.LockedHorizontalScrollView>
</LinearLayout>
My code is quite long so I puttet it on dropbox (whole project) and you can see what happend
Project
I think if you move the scrollbar you lose the focus of the first clicked button. two reasons:
- the Scrollview overrides the onTouchEvent and return true. --> the touch is consumed
- you lose focus of the first button. Try to add the Buttons with the addMoveOutsideEnabledViews Methode and see what happens.
I resolved my problem.
You don't need looking for button under touch. You have to take X and Y of your touch position and add your values from scrollView. Then you have to check, there are any button and start method:
rawX = (int) event.getX(actionPointerIndex) + location[0];
rawY = (int) event.getY(actionPointerIndex) + location[1];
scrollX = seek.getProgress() + rawX;
if (actionResolved == MotionEvent.ACTION_DOWN) {
findButton(scrollX, rawY, true);
}
if(actionResolved == MotionEvent.ACTION_UP || actionResolved == MotionEvent.ACTION_CANCEL) {
findButton(scrollX, rawY, false);
}
I want to make my dialog visible when i touch everywhere on the display.
I have an Activity, a view and a Renderer class. I wrote my code in the View class:
public boolean onTouchEvent(final MotionEvent event) {
queueEvent(new Runnable() {....}}
I posted my code. (Only activity and View)
public class MapEditorActivity extends Activity {
private GLSurfaceView mGLSurfaceView;
Region dialogRegion;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
requestWindowFeature(Window.FEATURE_NO_TITLE);
getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
WindowManager.LayoutParams.FLAG_FULLSCREEN);
this.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE);
// Create our Preview view and set it as the content of our
// Activity
mGLSurfaceView = new MapEditorView(this);
setContentView(mGLSurfaceView);
}
#Override
protected void onPause() {
super.onPause();
mGLSurfaceView.onPause();
}
#Override
protected void onResume() {
super.onResume();
mGLSurfaceView.onResume();
}
}
And my View class:
public class MapEditorView extends GLSurfaceView {
private static final String LOG_TAG = "de.rwth.arlab.colofields.ui.MapEditorView";
MapEditorRenderer editMapRenderer;
// we have a maximum of 5 pointer
private int[] coordsX = new int[5];
private int[] coordsY = new int[5];
// we have to save first touch for motion
private int[] coordsXFirst = new int[5];
private int[] coordsYFirst = new int[5];
// offsets for view
private float offX;
private float offY;
private float offZ;
Context context;
boolean zooming;
public MapEditorView(Context context) {
super(context);
editMapRenderer = new MapEditorRenderer(context);
setRenderer(editMapRenderer);
// initialize as not present
Arrays.fill(coordsX, Integer.MIN_VALUE);
Arrays.fill(coordsY, Integer.MIN_VALUE);
zooming = false;
}
public boolean onTouchEvent(final MotionEvent event) {
queueEvent(new Runnable() {
// TODO: Speak about this thing, this functions need API8
#SuppressLint("NewApi")
public void run() {
switch (event.getAction() & MotionEvent.ACTION_MASK) {
case MotionEvent.ACTION_DOWN:
offX = editMapRenderer.getxView();
offY = editMapRenderer.getyView();
coordsXFirst[0] = (int) event.getX(0);
coordsYFirst[0] = (int) event.getY(0);
startDialog(null);
break;
case MotionEvent.ACTION_POINTER_DOWN:
offZ = editMapRenderer.getzView();
coordsXFirst[0] = (int) event.getX(0);
coordsYFirst[0] = (int) event.getY(0);
coordsXFirst[1] = (int) event.getX(1);
coordsYFirst[1] = (int) event.getY(1);
zooming=true;
break;
case MotionEvent.ACTION_UP:
zooming=false;
break;
default:
// track all touches
for (int i = 0; i < event.getPointerCount(); i++) {
int id = event.getPointerId(i);
// update all other pointer positions
coordsX[id] = (int) event.getX(i);
coordsY[id] = (int) event.getY(i);
}
// When only one finger
if (event.getPointerCount() == 1 && !zooming)
editMapRenderer.setPosition(offX
+ (coordsX[0] - coordsXFirst[0])*editMapRenderer.getzView()*-1 / 1000.0f, offY
+ (coordsYFirst[0] - coordsY[0])*editMapRenderer.getzView()*-1 / 1000.0f);
// When two fingers
float distanceOld = (float) FloatMath
.sqrt((coordsXFirst[1] - coordsXFirst[0])
* (coordsXFirst[1] - coordsXFirst[0])
+ (coordsYFirst[1] - coordsYFirst[0])
* (coordsYFirst[1] - coordsYFirst[0]));
float distanceNew = (float) FloatMath
.sqrt((coordsX[1] - coordsX[0])
* (coordsX[1] - coordsX[0])
+ (coordsY[1] - coordsY[0])
* (coordsY[1] - coordsY[0]));
float distanceMax = (float) FloatMath
.sqrt(getWidth()
* getWidth()
+ getHeight()
* getHeight());
if (event.getPointerCount() == 2) {
editMapRenderer.setZoom(offZ + (distanceNew
- distanceOld)/(distanceMax/10));
}
break;
}
}
public Dialog startDialog(Bundle savedInstanceState) {
final CharSequence[] items = new String[] { "#F5F6F6", "#FFC0CB", "#FF0000",
"#C00000","#62492F","#DB3C00", "#98E01C" };
AlertDialog.Builder builder = new AlertDialog.Builder(this);
builder.setTitle("Pick a color");
builder.setItems(items, new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int item) {
Toast.makeText((Context) getApplicationWindowToken(), items[item], Toast.LENGTH_SHORT).show();
}
});
AlertDialog alert = builder.create();
}
});
return true;
}
MapEditorRenderer mRenderer;
public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater inflater =((Activity)context).getMenuInflater();
inflater.inflate(R.layout.menu_save, menu);
return true;
}
}
My problem is the method startDialog().
It does not work. I get an error:
"The constructor AlertDialog.Builder(new Runnable(){}) is undefined"
How can i solve it?
Ok i post again my code :
>
public class MapEditorActivity extends Activity {
private GLSurfaceView mGLSurfaceView;
Region dialogRegion;
MapEditorRenderer editMapRenderer;
// we have a maximum of 5 pointer
private int[] coordsX = new int[5];
private int[] coordsY = new int[5];
// we have to save first touch for motion
private int[] coordsXFirst = new int[5];
private int[] coordsYFirst = new int[5];
// offsets for view
private float offX;
private float offY;
private float offZ;
Context context;
boolean zooming;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
requestWindowFeature(Window.FEATURE_NO_TITLE);
getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
WindowManager.LayoutParams.FLAG_FULLSCREEN);
this.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE);
// Create our Preview view and set it as the content of our
// Activity
mGLSurfaceView = new MapEditorView(this);
setContentView(mGLSurfaceView);
mGLSurfaceView.setOnTouchListener(MapEditorActivity.this);
}
#Override
protected void onPause() {
super.onPause();
mGLSurfaceView.onPause();
}
#Override
protected void onResume() {
super.onResume();
mGLSurfaceView.onResume();
}
public boolean onTouchEvent(final MotionEvent event) {
queueEvent(new Runnable() {
// TODO: Speak about this thing, this functions need API8
#SuppressLint("NewApi")
public void run() {
switch (event.getAction() & MotionEvent.ACTION_MASK) {
case MotionEvent.ACTION_DOWN:
offX = editMapRenderer.getxView();
offY = editMapRenderer.getyView();
coordsXFirst[0] = (int) event.getX(0);
coordsYFirst[0] = (int) event.getY(0);
startDialog(null);
break;
case MotionEvent.ACTION_POINTER_DOWN:
offZ = editMapRenderer.getzView();
coordsXFirst[0] = (int) event.getX(0);
coordsYFirst[0] = (int) event.getY(0);
coordsXFirst[1] = (int) event.getX(1);
coordsYFirst[1] = (int) event.getY(1);
zooming=true;
break;
case MotionEvent.ACTION_UP:
zooming=false;
break;
default:
// track all touches
for (int i = 0; i < event.getPointerCount(); i++) {
int id = event.getPointerId(i);
// update all other pointer positions
coordsX[id] = (int) event.getX(i);
coordsY[id] = (int) event.getY(i);
}
// When only one finger
if (event.getPointerCount() == 1 && !zooming)
editMapRenderer.setPosition(offX
+ (coordsX[0] - coordsXFirst[0])*editMapRenderer.getzView()*-1 / 1000.0f, offY
+ (coordsYFirst[0] - coordsY[0])*editMapRenderer.getzView()*-1 / 1000.0f);
// When two fingers
float distanceOld = (float) FloatMath
.sqrt((coordsXFirst[1] - coordsXFirst[0])
* (coordsXFirst[1] - coordsXFirst[0])
+ (coordsYFirst[1] - coordsYFirst[0])
* (coordsYFirst[1] - coordsYFirst[0]));
float distanceNew = (float) FloatMath
.sqrt((coordsX[1] - coordsX[0])
* (coordsX[1] - coordsX[0])
+ (coordsY[1] - coordsY[0])
* (coordsY[1] - coordsY[0]));
float distanceMax = (float) FloatMath
.sqrt(getWidth()
* getWidth()
+ getHeight()
* getHeight());
if (event.getPointerCount() == 2) {
editMapRenderer.setZoom(offZ + (distanceNew
- distanceOld)/(distanceMax/10));
}
break;
}
}
private int getHeight() {
// TODO Auto-generated method stub
return 0;
}
private int getWidth() {
// TODO Auto-generated method stub
return 0;
}
public Dialog startDialog(Bundle savedInstanceState) {
final CharSequence[] items = new String[] { "#F5F6F6", "#FFC0CB", "#FF0000",
"#C00000","#62492F","#DB3C00", "#98E01C" };
AlertDialog.Builder builder = new AlertDialog.Builder(MapEditorActivity.this);
builder.setTitle("Pick a color");
builder.setItems(items, new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int item) {
Toast.makeText((Context) getApplication(), items[item], Toast.LENGTH_SHORT).show();
}
});
AlertDialog alert = builder.create();
return alert;
}
});
return true;
}
private void queueEvent(Runnable runnable) {
// TODO Auto-generated method stub
}
MapEditorRenderer mRenderer;
public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater inflater =((Activity)context).getMenuInflater();
inflater.inflate(R.layout.menu_save, menu);
return true;
}
}
Replace
AlertDialog.Builder builder = new AlertDialog.Builder(this);
with
AlertDialog.Builder builder = new AlertDialog.Builder(getBaseContext());
and your problem will be solved.
Replace
AlertDialog.Builder builder = new AlertDialog.Builder(this);
with
AlertDialog.Builder builder = new AlertDialog.Builder(MapEditorView.this.getContext());
Write below code line
builder.show();
instead of
AlertDialog alert = builder.create();
it will solve your problem.
Ok guys, i have changed my code. This is the last version.but i have stimm the same problem.
public class MapEditorActivity extends Activity implements OnTouchListener{
private GLSurfaceView mGLSurfaceView;
MapEditorRenderer editMapRenderer;
// we have a maximum of 5 pointer
private int[] coordsX = new int[5];
private int[] coordsY = new int[5];
// we have to save first touch for motion
private int[] coordsXFirst = new int[5];
private int[] coordsYFirst = new int[5];
// offsets for view
private float offX;
private float offY;
private float offZ;
Context context;
boolean zooming;
Region dialogRegion;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
requestWindowFeature(Window.FEATURE_NO_TITLE);
getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
WindowManager.LayoutParams.FLAG_FULLSCREEN);
this.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE);
// Create our Preview view and set it as the content of our
// Activity
mGLSurfaceView = new MapEditorView(this);
setContentView(mGLSurfaceView);
mGLSurfaceView.setOnTouchListener(MapEditorActivity.this);
}
private void showDialog(){
AlertDialog.Builder dialogBuilder = new AlertDialog.Builder(this);
final String[] color = { "#F5F6F6", "#FFC0CB", "#FF0000",
"#C00000","#62492F","#DB3C00", "#98E01C" };
dialogBuilder.setTitle("pick one Color");
dialogBuilder.setItems(color, new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int which) {
Toast.makeText(getApplicationContext(),color[which], Toast.LENGTH_SHORT).show();
}
});
AlertDialog alertDialog = dialogBuilder.create();
alertDialog.show();
}
#Override
protected void onPause() {
super.onPause();
mGLSurfaceView.onPause();
}
#Override
protected void onResume() {
super.onResume();
mGLSurfaceView.onResume();
}
public boolean onTouch(View v, MotionEvent event) {
switch (event.getAction() & MotionEvent.ACTION_MASK) {
case MotionEvent.ACTION_DOWN:
offX = editMapRenderer.getxView();
offY = editMapRenderer.getyView();
coordsXFirst[0] = (int) event.getX(0);
coordsYFirst[0] = (int) event.getY(0);
showDialog();
break;
case MotionEvent.ACTION_POINTER_DOWN:
offZ = editMapRenderer.getzView();
coordsXFirst[0] = (int) event.getX(0);
coordsYFirst[0] = (int) event.getY(0);
coordsXFirst[1] = (int) event.getX(1);
coordsYFirst[1] = (int) event.getY(1);
zooming=true;
break;
case MotionEvent.ACTION_UP:
zooming=false;
break;
default:
// track all touches
for (int i = 0; i < event.getPointerCount(); i++) {
int id = event.getPointerId(i);
// update all other pointer positions
coordsX[id] = (int) event.getX(i);
coordsY[id] = (int) event.getY(i);
}
// When only one finger
if (event.getPointerCount() == 1 && !zooming)
editMapRenderer.setPosition(offX
+ (coordsX[0] - coordsXFirst[0])*editMapRenderer.getzView()*-1 / 1000.0f, offY
+ (coordsYFirst[0] - coordsY[0])*editMapRenderer.getzView()*-1 / 1000.0f);
// When two fingers
float distanceOld = (float) FloatMath
.sqrt((coordsXFirst[1] - coordsXFirst[0])
* (coordsXFirst[1] - coordsXFirst[0])
+ (coordsYFirst[1] - coordsYFirst[0])
* (coordsYFirst[1] - coordsYFirst[0]));
float distanceNew = (float) FloatMath
.sqrt((coordsX[1] - coordsX[0])
* (coordsX[1] - coordsX[0])
+ (coordsY[1] - coordsY[0])
* (coordsY[1] - coordsY[0]));
float distanceMax = (float) FloatMath
.sqrt(getWidth()
* getWidth()
+ getHeight()
* getHeight());
if (event.getPointerCount() == 2) {
editMapRenderer.setZoom(offZ + (distanceNew
- distanceOld)/(distanceMax/10));
}
break;
}
return false;
}
private int getHeight() {
// TODO Auto-generated method stub
return 0;
}
private int getWidth() {
// TODO Auto-generated method stub
return 0;
}
}
When I am trying to fling example this error faced. with java Null pointer exception.
My java code
public class LearnCount extends Activity {
private FlingGallery mGallery;
public boolean onTouchEvent(MotionEvent event) {
return mGallery.onGalleryTouchEvent(event);
}
private String[] teststr = {
"test1","test2","test3","test4","test5"
};
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
setContentView(R.layout.main);
LinearLayout productHolder = (LinearLayout) findViewById(R.id.linearLayoutOfCount);
mGallery = new FlingGallery(this);
mGallery.setAdapter(new ArrayAdapter<String>(getApplicationContext(),
android.R.layout.simple_list_item_1, teststr) {
public View getView(int position, View convertView, ViewGroup parent) {
System.out.println(mGallery.getCurrentPosition() + " position");
if (convertView != null
&& convertView instanceof GalleryViewItem) {
GalleryViewItem galleryView = (GalleryViewItem) convertView;
//galleryView.pImage.setImageResource(mImageIds[position]);
galleryView.b.setText(teststr[position]);
return galleryView;
}
GalleryViewItem gvi = new GalleryViewItem(getApplicationContext(), position);
gvi.b.setText(teststr[position]);
return gvi;
}
});
productHolder.addView(mGallery);
}
public class GalleryViewItem extends TableLayout {
private TextView b;
public GalleryViewItem(Context context, int position) {
super(context);
LayoutInflater inflater = (LayoutInflater) getSystemService(Context.LAYOUT_INFLATER_SERVICE);
View v = inflater.inflate(R.layout.test, null);
b = (TextView) v.findViewById(R.id.test);
this.addView(v);
}
}
public class FlingGallery extends FrameLayout {
// Constants
private final int swipe_min_distance = 120;
private final int swipe_max_off_path = 250;
private final int swipe_threshold_veloicty = 400;
// Properties
private int mViewPaddingWidth = 0;
private int mAnimationDuration = 250;
private float mSnapBorderRatio = 0.5f;
private boolean mIsGalleryCircular = false;
// Members
private int mGalleryWidth = 0;
private boolean mIsTouched = false;
private boolean mIsDragging = false;
private float mCurrentOffset = 0.0f;
private long mScrollTimestamp = 0;
private int mFlingDirection = 0;
public int mCurrentPosition = 0;
private int mCurrentViewNumber = 0;
private Context mContext;
private Adapter mAdapter;
private FlingGalleryView[] mViews;
private FlingGalleryAnimation mAnimation;
private GestureDetector mGestureDetector;
private Interpolator mDecelerateInterpolater;
public FlingGallery(Context context) {
super(context);
mContext = context;
mAdapter = null;
mViews = new FlingGalleryView[3];
mViews[0] = new FlingGalleryView(0, this);
mViews[1] = new FlingGalleryView(1, this);
mViews[2] = new FlingGalleryView(2, this);
mAnimation = new FlingGalleryAnimation();
mGestureDetector = new GestureDetector(new FlingGestureDetector());
mDecelerateInterpolater = AnimationUtils.loadInterpolator(mContext,
android.R.anim.decelerate_interpolator);
}
public void setPaddingWidth(int viewPaddingWidth) {
mViewPaddingWidth = viewPaddingWidth;
}
public void setAnimationDuration(int animationDuration) {
mAnimationDuration = animationDuration;
}
public void setSnapBorderRatio(float snapBorderRatio) {
mSnapBorderRatio = snapBorderRatio;
}
public int getCurrentPosition() {
return mCurrentPosition;
}
public void setIsGalleryCircular(boolean isGalleryCircular) {
if (mIsGalleryCircular != isGalleryCircular) {
mIsGalleryCircular = isGalleryCircular;
if (mCurrentPosition == getFirstPosition()) {
// We need to reload the view immediately to the left to
// change it to circular view or blank
mViews[getPrevViewNumber(mCurrentViewNumber)]
.recycleView(getPrevPosition(mCurrentPosition));
}
if (mCurrentPosition == getLastPosition()) {
// We need to reload the view immediately to the right to
// change it to circular view or blank
mViews[getNextViewNumber(mCurrentViewNumber)]
.recycleView(getNextPosition(mCurrentPosition));
}
}
}
public int getGalleryCount() {
return (mAdapter == null) ? 0 : mAdapter.getCount();
}
public int getFirstPosition() {
return 0;
}
public int getLastPosition() {
return (getGalleryCount() == 0) ? 0 : getGalleryCount() - 1;
}
private int getPrevPosition(int relativePosition) {
int prevPosition = relativePosition - 1;
if (prevPosition < getFirstPosition()) {
prevPosition = getFirstPosition() - 1;
if (mIsGalleryCircular == true) {
prevPosition = getLastPosition();
}
}
return prevPosition;
}
private int getNextPosition(int relativePosition) {
int nextPosition = relativePosition + 1;
if (nextPosition > getLastPosition()) {
nextPosition = getLastPosition() + 1;
if (mIsGalleryCircular == true) {
nextPosition = getFirstPosition();
}
}
return nextPosition;
}
private int getPrevViewNumber(int relativeViewNumber) {
return (relativeViewNumber == 0) ? 2 : relativeViewNumber - 1;
}
private int getNextViewNumber(int relativeViewNumber) {
return (relativeViewNumber == 2) ? 0 : relativeViewNumber + 1;
}
protected void onLayout(boolean changed, int left, int top, int right,
int bottom) {
super.onLayout(changed, left, top, right, bottom);
// Calculate our view width
mGalleryWidth = right - left;
if (changed == true) {
// Position views at correct starting offsets
mViews[0].setOffset(0, 0, mCurrentViewNumber);
mViews[1].setOffset(0, 0, mCurrentViewNumber);
mViews[2].setOffset(0, 0, mCurrentViewNumber);
}
}
public void setAdapter(Adapter adapter) {
mAdapter = adapter;
mCurrentPosition = 0;
mCurrentViewNumber = 0;
// Load the initial views from adapter
mViews[0].recycleView(mCurrentPosition);
mViews[1].recycleView(getNextPosition(mCurrentPosition));
mViews[2].recycleView(getPrevPosition(mCurrentPosition));
// Position views at correct starting offsets
mViews[0].setOffset(0, 0, mCurrentViewNumber);
mViews[1].setOffset(0, 0, mCurrentViewNumber);
mViews[2].setOffset(0, 0, mCurrentViewNumber);
}
private int getViewOffset(int viewNumber, int relativeViewNumber) {
// Determine width including configured padding width
int offsetWidth = mGalleryWidth + mViewPaddingWidth;
// Position the previous view one measured width to left
if (viewNumber == getPrevViewNumber(relativeViewNumber)) {
return offsetWidth;
}
// Position the next view one measured width to the right
if (viewNumber == getNextViewNumber(relativeViewNumber)) {
return offsetWidth * -1;
}
return 0;
}
void movePrevious() {
// Slide to previous view
mFlingDirection = 1;
processGesture();
}
void moveNext() {
// Slide to next view
mFlingDirection = -1;
processGesture();
}
public boolean onKeyDown(int keyCode, KeyEvent event) {
switch (keyCode) {
case KeyEvent.KEYCODE_DPAD_LEFT:
movePrevious();
return true;
case KeyEvent.KEYCODE_DPAD_RIGHT:
moveNext();
return true;
case KeyEvent.KEYCODE_DPAD_CENTER:
case KeyEvent.KEYCODE_ENTER:
}
return super.onKeyDown(keyCode, event);
}
public boolean onGalleryTouchEvent(MotionEvent event) {
boolean consumed = mGestureDetector.onTouchEvent(event);
if (event.getAction() == MotionEvent.ACTION_UP) {
if (mIsTouched || mIsDragging) {
processScrollSnap();
processGesture();
}
}
return consumed;
}
void processGesture() {
int newViewNumber = mCurrentViewNumber;
int reloadViewNumber = 0;
int reloadPosition = 0;
mIsTouched = false;
mIsDragging = false;
if (mFlingDirection > 0) {
if (mCurrentPosition > getFirstPosition()
|| mIsGalleryCircular == true) {
// Determine previous view and outgoing view to recycle
newViewNumber = getPrevViewNumber(mCurrentViewNumber);
mCurrentPosition = getPrevPosition(mCurrentPosition);
reloadViewNumber = getNextViewNumber(mCurrentViewNumber);
reloadPosition = getPrevPosition(mCurrentPosition);
}
}
if (mFlingDirection < 0) {
if (mCurrentPosition < getLastPosition()
|| mIsGalleryCircular == true) {
// Determine the next view and outgoing view to recycle
newViewNumber = getNextViewNumber(mCurrentViewNumber);
mCurrentPosition = getNextPosition(mCurrentPosition);
reloadViewNumber = getPrevViewNumber(mCurrentViewNumber);
reloadPosition = getNextPosition(mCurrentPosition);
}
}
if (newViewNumber != mCurrentViewNumber) {
mCurrentViewNumber = newViewNumber;
// Reload outgoing view from adapter in new position
mViews[reloadViewNumber].recycleView(reloadPosition);
}
// Ensure input focus on the current view
mViews[mCurrentViewNumber].requestFocus();
// Run the slide animations for view transitions
mAnimation.prepareAnimation(mCurrentViewNumber);
this.startAnimation(mAnimation);
// Reset fling state
mFlingDirection = 0;
//checkNextBackButton(mCurrentPosition);
System.out.println("positionFiling" + mCurrentPosition);
}
void processScrollSnap() {
// Snap to next view if scrolled passed snap position
float rollEdgeWidth = mGalleryWidth * mSnapBorderRatio;
int rollOffset = mGalleryWidth - (int) rollEdgeWidth;
int currentOffset = mViews[mCurrentViewNumber].getCurrentOffset();
if (currentOffset <= rollOffset * -1) {
// Snap to previous view
mFlingDirection = 1;
}
if (currentOffset >= rollOffset) {
// Snap to next view
mFlingDirection = -1;
}
}
public class FlingGalleryView {
private int mViewNumber;
private FrameLayout mParentLayout;
private FrameLayout mInvalidLayout = null;
private LinearLayout mInternalLayout = null;
private View mExternalView = null;
public FlingGalleryView(int viewNumber, FrameLayout parentLayout) {
mViewNumber = viewNumber;
mParentLayout = parentLayout;
// Invalid layout is used when outside gallery
mInvalidLayout = new FrameLayout(mContext);
mInvalidLayout.setLayoutParams(new LinearLayout.LayoutParams(
LayoutParams.FILL_PARENT, LayoutParams.FILL_PARENT));
// Internal layout is permanent for duration
mInternalLayout = new LinearLayout(mContext);
mInternalLayout.setLayoutParams(new LinearLayout.LayoutParams(
LayoutParams.FILL_PARENT, LayoutParams.FILL_PARENT));
mParentLayout.addView(mInternalLayout);
}
public void recycleView(int newPosition) {
if (mExternalView != null) {
mInternalLayout.removeView(mExternalView);
}
if (mAdapter != null) {
if (newPosition >= getFirstPosition()
&& newPosition <= getLastPosition()) {
mExternalView = mAdapter.getView(newPosition,
mExternalView, mInternalLayout);
} else {
mExternalView = mInvalidLayout;
}
}
if (mExternalView != null) {
mInternalLayout.addView(mExternalView,
new LinearLayout.LayoutParams(
LayoutParams.FILL_PARENT,
LayoutParams.FILL_PARENT));
}
}
public void setOffset(int xOffset, int yOffset,
int relativeViewNumber) {
// Scroll the target view relative to its own position relative
// to currently displayed view
mInternalLayout.scrollTo(getViewOffset(mViewNumber,
relativeViewNumber)
+ xOffset, yOffset);
}
public int getCurrentOffset() {
// Return the current scroll position
return mInternalLayout.getScrollX();
}
public void requestFocus() {
mInternalLayout.requestFocus();
}
}
public class FlingGalleryAnimation extends Animation {
private boolean mIsAnimationInProgres;
private int mRelativeViewNumber;
private int mInitialOffset;
private int mTargetOffset;
private int mTargetDistance;
public FlingGalleryAnimation() {
mIsAnimationInProgres = false;
mRelativeViewNumber = 0;
mInitialOffset = 0;
mTargetOffset = 0;
mTargetDistance = 0;
}
public void prepareAnimation(int relativeViewNumber) {
// If we are animating relative to a new view
if (mRelativeViewNumber != relativeViewNumber) {
if (mIsAnimationInProgres == true) {
// We only have three views so if requested again to
// animate in same direction we must snap
int newDirection = (relativeViewNumber == getPrevViewNumber(mRelativeViewNumber)) ? 1
: -1;
int animDirection = (mTargetDistance < 0) ? 1 : -1;
// If animation in same direction
if (animDirection == newDirection) {
// Ran out of time to animate so snap to the target
// offset
mViews[0].setOffset(mTargetOffset, 0,
mRelativeViewNumber);
mViews[1].setOffset(mTargetOffset, 0,
mRelativeViewNumber);
mViews[2].setOffset(mTargetOffset, 0,
mRelativeViewNumber);
}
}
// Set relative view number for animation
mRelativeViewNumber = relativeViewNumber;
}
// Note: In this implementation the targetOffset will always be
// zero
// as we are centering the view; but we include the calculations
// of
// targetOffset and targetDistance for use in future
// implementations
mInitialOffset = mViews[mRelativeViewNumber].getCurrentOffset();
mTargetOffset = getViewOffset(mRelativeViewNumber,
mRelativeViewNumber);
mTargetDistance = mTargetOffset - mInitialOffset;
// Configure base animation properties
this.setDuration(mAnimationDuration);
this.setInterpolator(mDecelerateInterpolater);
// Start/continued animation
mIsAnimationInProgres = true;
}
protected void applyTransformation(float interpolatedTime,
Transformation transformation) {
// Ensure interpolatedTime does not over-shoot then calculate
// new offset
interpolatedTime = (interpolatedTime > 1.0f) ? 1.0f
: interpolatedTime;
int offset = mInitialOffset
+ (int) (mTargetDistance * interpolatedTime);
for (int viewNumber = 0; viewNumber < 3; viewNumber++) {
// Only need to animate the visible views as the other view
// will always be off-screen
if ((mTargetDistance > 0 && viewNumber != getNextViewNumber(mRelativeViewNumber))
|| (mTargetDistance < 0 && viewNumber != getPrevViewNumber(mRelativeViewNumber))) {
mViews[viewNumber].setOffset(offset, 0,
mRelativeViewNumber);
}
}
}
public boolean getTransformation(long currentTime,
Transformation outTransformation) {
if (super.getTransformation(currentTime, outTransformation) == false) {
// Perform final adjustment to offsets to cleanup animation
mViews[0].setOffset(mTargetOffset, 0, mRelativeViewNumber);
mViews[1].setOffset(mTargetOffset, 0, mRelativeViewNumber);
mViews[2].setOffset(mTargetOffset, 0, mRelativeViewNumber);
// Reached the animation target
mIsAnimationInProgres = false;
return false;
}
// Cancel if the screen touched
if (mIsTouched || mIsDragging) {
// Note that at this point we still consider ourselves to be
// animating
// because we have not yet reached the target offset; its
// just that the
// user has temporarily interrupted the animation with a
// touch gesture
return false;
}
return true;
}
}
private class FlingGestureDetector extends GestureDetector.SimpleOnGestureListener {
public boolean onDown(MotionEvent e) {
// Stop animation
mIsTouched = true;
// Reset fling state
mFlingDirection = 0;
return true;
}
public boolean onScroll(MotionEvent e1, MotionEvent e2,
float distanceX, float distanceY) {
if (e2.getAction() == MotionEvent.ACTION_MOVE) {
if (mIsDragging == false) {
// Stop animation
mIsTouched = true;
// Reconfigure scroll
mIsDragging = true;
mFlingDirection = 0;
mScrollTimestamp = System.currentTimeMillis();
mCurrentOffset = mViews[mCurrentViewNumber]
.getCurrentOffset();
}
float maxVelocity = mGalleryWidth
/ (mAnimationDuration / 1000.0f);
long timestampDelta = System.currentTimeMillis()
- mScrollTimestamp;
float maxScrollDelta = maxVelocity
* (timestampDelta / 1000.0f);
float currentScrollDelta = e1.getX() - e2.getX();
if (currentScrollDelta < maxScrollDelta * -1)
currentScrollDelta = maxScrollDelta * -1;
if (currentScrollDelta > maxScrollDelta)
currentScrollDelta = maxScrollDelta;
int scrollOffset = Math.round(mCurrentOffset
+ currentScrollDelta);
// We can't scroll more than the width of our own frame
// layout
if (scrollOffset >= mGalleryWidth)
scrollOffset = mGalleryWidth;
if (scrollOffset <= mGalleryWidth * -1)
scrollOffset = mGalleryWidth * -1;
mViews[0].setOffset(scrollOffset, 0, mCurrentViewNumber);
mViews[1].setOffset(scrollOffset, 0, mCurrentViewNumber);
mViews[2].setOffset(scrollOffset, 0, mCurrentViewNumber);
}
return false;
}
public boolean onFling(MotionEvent e1, MotionEvent e2,
float velocityX, float velocityY) {
if (Math.abs(e1.getY() - e2.getY()) <= swipe_max_off_path) {
if (e2.getX() - e1.getX() > swipe_min_distance
&& Math.abs(velocityX) > swipe_threshold_veloicty) {
movePrevious();
}
if (e1.getX() - e2.getX() > swipe_min_distance
&& Math.abs(velocityX) > swipe_threshold_veloicty) {
moveNext();
}
}
return false;
}
public void onLongPress(MotionEvent e) {
// Finalise scrolling
mFlingDirection = 0;
processGesture();
}
public void onShowPress(MotionEvent e) {
}
public boolean onSingleTapUp(MotionEvent e) {
// Reset fling state
mFlingDirection = 0;
return false;
}
}
}
}
My log cat error message is:
I am the beginner for android, something wrong my code?
LinearLayout productHolder = (LinearLayout) findViewById(R.id.linearLayoutOfCount);
Is returning null. Make sure you are referencing the correct id.