I didn't describe the question in a good way, so I edit the question to be clear.
I am so confused about this: I wrote a RelativeLayout with a DragViewGroup and a gridview, and I noticed that every time when I used notifyDatasetChanged() method would cause the DragViewGroup do the redrawing thing.And the DragViewGroup extends from LinearLayout which uses ViewDragHelper, so I could not maintain the position already scrolled to.
Here is my xml file:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<com.xxxx.DragViewGroup
android:id="#+id/dragview"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="#3f83f7"
android:orientation="vertical">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="665dp"
android:orientation="vertical">
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="310dp"
android:id="#+id/mainview"
>
...
</RelativeLayout>
<include
android:layout_width="match_parent"
android:layout_height="355dp"
android:layout_marginBottom="62dp"
layout="#layout/fake_panel" />
</LinearLayout>
</com.xxxx.DragViewGroup>
<RelativeLayout
android:layout_width="match_parent"
android:id="#+id/layout"
android:layout_alignParentBottom="true"
android:layout_height="210dp"
android:background="#ffffff"
android:clickable="true"
>
<HorizontalScrollView
android:id="#+id/btn_scroll_view"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:overScrollMode="never"
android:layout_alignParentBottom="true"
android:layout_marginBottom="26dp"
android:scrollbars="none">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent">
<GridView
android:id="#+id/list"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_margin="10dp"
android:listSelector="#color/transparent"
android:horizontalSpacing="6dp"
android:scrollbars="none" />
</LinearLayout>
</HorizontalScrollView>
<com.xxxx.UniversalSeekBar
....
android:layout_marginTop="18dp"/>
</RelativeLayout>
</RelativeLayout>
DragViewGroup code:
public class DragViewGroup extends LinearLayout {
private ViewDragHelper viewDragHelper;
private View mainView;
private int mainHeight;
public DragViewGroup(Context context) {
super(context);
initView();
}
public DragViewGroup(Context context, AttributeSet attrs) {
super(context, attrs);
initView();
}
public DragViewGroup(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
initView();
}
#Override
protected void onFinishInflate() {
super.onFinishInflate();
mainView = getChildAt(0);
}
#Override
protected void onSizeChanged(int w, int h, int oldw, int oldh) {
super.onSizeChanged(w, h, oldw, oldh);
mainHeight = mainView.findViewById(R.id.mainview).getMeasuredHeight();
}
#Override
public boolean onInterceptTouchEvent(MotionEvent ev) {
return viewDragHelper.shouldInterceptTouchEvent(ev);
}
#Override
public boolean onTouchEvent(MotionEvent event) {
viewDragHelper.processTouchEvent(event);
return true;
}
#Override
public void computeScroll() {
if (viewDragHelper.continueSettling(true)) {
ViewCompat.postInvalidateOnAnimation(this);
}
}
private void initView() {
viewDragHelper = ViewDragHelper.create(this, callback);
}
private ViewDragHelper.Callback callback = new ViewDragHelper.Callback() {
#Override
public boolean tryCaptureView(View child, int pointerId) {
return mainView == child;
}
#Override
public int clampViewPositionHorizontal(View child, int left, int dx) {
return 0;
}
#Override
public int clampViewPositionVertical(View child, int top, int dy) {
return top;
}
#Override
public void onViewReleased(View releasedChild, float xvel, float yvel) {
super.onViewReleased(releasedChild, xvel, yvel);
if (mainView.getTop() > -500) {
viewDragHelper.smoothSlideViewTo(mainView, 0, 0);
ViewCompat.postInvalidateOnAnimation(DragViewGroup.this);
} else {
viewDragHelper.smoothSlideViewTo(mainView, 0, -mainHeight);
ViewCompat.postInvalidateOnAnimation(DragViewGroup.this);
}
}
};
}
Once I use the notifyDatasetChanged() method to update the gridview, my DragViewGroup will slide to the original position itself although it has been dragged before. Apparently the method draw the whole layout instead of only drawing gridview itself.
I need to maintain the dragged position of DragViewGroup, I have tried that override onDraw method in DragViewGroup like this:
#Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
// set isDragged label in onViewReleased()
if (isDragged) {
viewDragHelper.smoothSlideViewTo(main, 0, -mainHeight);
}
}
It works, but there is a visible sliding process which I don't want.
Hope someone could help me.Thanks very much.
Store ScrollValue at the time of the scrolling the view, and just use setSelectionMethod on your gridview
gridview.setOnScrollListener(new OnScrollListener() {
#Override
public void onScrollStateChanged(AbsListView view, int scrollState) {
// TODO Auto-generated method stub
int count = gridview.getCount();
if (scrollState == SCROLL_STATE_IDLE) {
if (gridview.getLastVisiblePosition() >= count
- 1) {
scrollPos = <positionOfList>;
}
}
}
});
Here enter your last position insted of "positionOfList"
And just after calling notifydatasetChanged() call gridview.setSelection(scrollPos)
Hope this will help you!
Just use bellow code in class that you update display:
int index = myList.getFirstVisiblePosition();
View v = myList.getChildAt(0);
int top = (v == null) ? 0 : v.getTop();
myList.setAdapter(adapter);
adapter.notifyDataSetChanged();
myList.setSelectionFromTop(index, top);
Related
I want to achieve parallax scrolling in android without using external library.Is there anyway to achieve this same as in google play store.
Thanks
To implement that in a RecyclerView:
public class MyScrollListener extends RecyclerView.OnScrollListener {
private int totalScrollDistance = 0;
private View parallax;
#Override
public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
totalScrollDistance += dy;
if (parallax == null) {
parallax = recyclerView.getChildAt(0);
}
parallax.setTranslationY(totalScrollDistance/2);
}
}
Setup:
mRecyclerView.setOnScrollListener(new MyScrollListener());
To implement that in a ScrollView, you have to implement a OnScrollListener:
public class MyScrollView extends ScrollView {
private int lastScrollY;
private OnScrollListener listener;
public void setOnScrollListener(OnScrollListener listener) {
this.listener = listener;
}
private Handler handler = new Handler() {
#Override
public void handleMessage(Message msg) {
int scrollY = getScrollY();
if (lastScrollY != scrollY) {
lastScrollY = scrollY;
// update when lastScrollY != scrollY and keep sending message till lastScrollY == scrollY
handler.sendMessageDelayed(handler.obtainMessage(), 5);
}
if (listener != null) {
listener.onScroll(scrollY);
}
}
};
public MyScrollView(Context context) {
super(context);
}
public MyScrollView(Context context, AttributeSet attrs) {
super(context, attrs);
}
public MyScrollView(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
}
public MyScrollView(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) {
super(context, attrs, defStyleAttr, defStyleRes);
}
#Override
public boolean onTouchEvent(MotionEvent ev) {
lastScrollY = getScrollY();
if (listener != null) {
listener.onScroll(lastScrollY);
}
if (ev.getAction() == MotionEvent.ACTION_UP) {
//might still scrolling after touching, use a handler to handle it
handler.sendMessageDelayed(handler.obtainMessage(), 5);
}
return super.onTouchEvent(ev);
}
public interface OnScrollListener {
void onScroll(int dy);
}
}
Then do what we did in OnScrollListener of RecyclerView:
scrollView = (MyScrollView) findViewById(R.id.my_scrollview);
final View parallax = ((ViewGoup) scrollView.getChildAt(0)).getChildAt(0);
scrollView.setOnScrollListener(new MyScrollView.OnScrollListener() {
#Override
public void onScroll(int dy) {
parallax.setTranslationY(dy/2);
}
});
For me the following method worked out .
In your android layout mention the below code:`
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:fitsSystemWindows="true">
<android.support.design.widget.CoordinatorLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:fitsSystemWindows="true"
>
<android.support.design.widget.AppBarLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:fitsSystemWindows="true"
android:background="#color/white"
>
<android.support.design.widget.CollapsingToolbarLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:layout_scrollFlags="scroll|exitUntilCollapsed"
>
//place the widgets that you want to collapse .....(here i have used an
ImageView)
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
<ImageView
android:layout_width="match_parent"
android:layout_height="200dp"
android:id="#+id/imgViewFirst"
android:src="#drawable/firstImage"
android:scaleType="fitXY"/>
</LinearLayout>
</android.support.design.widget.CollapsingToolbarLayout>
//place the widgets that you want to pin after scrolling up.....
<LinearLayout
android:layout_width="match_parent"
android:layout_height="50dp"
android:background="#color/lightGrey"/>
</android.support.design.widget.AppBarLayout>
//place the widgets you want to show after you scrolled upwards...(here i have
used an ImageView)
<android.support.v4.widget.NestedScrollView
android:layout_width="match_parent"
android:layout_height="match_parent"
app:layout_behavior="#string/appbar_scrolling_view_behavior">
<ImageView
android:layout_width="match_parent"
android:layout_height="200dp"
android:id="#+id/imgViewSecond"
android:src="#drawable/secondImage"
android:scaleType="fitXY"/>
</android.support.v4.widget.NestedScrollView>
</android.support.design.widget.CoordinatorLayout>
</LinearLayout>`
I want to create a custom view which should be added in another custom view.
The second view will be a container, so it should be able to contain the first view as its child.
For creating this views I am extending ViewGroup & LinearLayout classes.
Child view class is NodeView
public class NodeView extends LinearLayout
{
private final static String TAG = "NodeView";
private ImageView ivTop;
private ImageView ivBottom;
private Context myContext;
public NodeView(Context context, AttributeSet attrs)
{
super(context, attrs);
this.myContext = context;
setOrientation(LinearLayout.VERTICAL);
setGravity(Gravity.CENTER);
LayoutInflater inflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
inflater.inflate(R.layout.view_test_multi, this, true);
ivTop = (ImageView) getChildAt(0);
ivBottom = (ImageView) getChildAt(2);
ivTop.setOnClickListener(new OnClickListener()
{
#Override
public void onClick(View v)
{
Toast.makeText(myContext, "Top Clicked", Toast.LENGTH_SHORT).show();
}
});
ivBottom.setOnClickListener(new OnClickListener()
{
#Override
public void onClick(View v)
{
Toast.makeText(myContext, "Bottom Clicked", Toast.LENGTH_SHORT).show();
}
});
}
#Override
protected void onDraw(Canvas canvas)
{
super.onDraw(canvas);
}
public NodeView(Context context)
{
this(context, null);
}
}
& the container class is TreeViewGroup
public class TreeViewGroup extends ViewGroup
{
private static final String TAG = "CustomTreeNodeView";
NodeView nodeView;
public TreeViewGroup(Context context, AttributeSet attrs, int defStyleAttr)
{
super(context, attrs, defStyleAttr);
nodeView = new NodeView(getContext());
addView(nodeView);
}
public TreeViewGroup(Context context, AttributeSet attrs)
{
this(context, attrs, 0);
}
public TreeViewGroup(Context context)
{
this(context, null, 0);
}
#Override
protected void onDraw(Canvas canvas)
{
super.onDraw(canvas);
}
#Override
protected void onLayout(boolean changed, int l, int t, int r, int b)
{
}
}
& xml layout for node view is view_test_multi.xml
<?xml version="1.0" encoding="utf-8"?>
<merge xmlns:android="http://schemas.android.com/apk/res/android" >
<ImageView
android:layout_width="15dp"
android:layout_height="15dp"
android:layout_centerVertical="true"
android:src="#drawable/point_grey" />
<ImageView
android:layout_width="35dp"
android:layout_height="35dp"
android:layout_centerVertical="true"
android:src="#drawable/point_red" />
<ImageView
android:layout_width="15dp"
android:layout_height="15dp"
android:layout_centerVertical="true"
android:src="#drawable/point_grey" />
</merge>
My activity's layout is activity_main.xml
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
xmlns:custom="http://schemas.android.com/apk/res/com.ab1209.testcustom"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="#dimen/activity_vertical_margin"
android:paddingLeft="#dimen/activity_horizontal_margin"
android:paddingRight="#dimen/activity_horizontal_margin"
android:paddingTop="#dimen/activity_vertical_margin"
tools:context=".MainActivity" >
<com.ab1209.testcustom.view.TreeViewGroup
android:id="#+id/activity_main_custom_tree_node_view"
android:layout_width="match_parent"
android:layout_height="match_parent" />
</RelativeLayout>
MainActivity class is
**public class MainActivity extends Activity
{
TreeViewGroup treeNodeView;
#Override
protected void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
treeNodeView = (TreeViewGroup) findViewById(R.id.activity_main_custom_tree_node_view);
}
}**
When I run the app I don't see the NodeView added in main View. Am I doing the right thing if not please tell me how can I make it working?
To create a custom ViewGroup, the only method you need to override is
onLayout. The onLayout is triggered after the ViewGroup itself has
finished laying itself out inside its own container ViewGroup and is
now responsible for laying out its children. It should call the layout
method on all of its children to now position and size them (the left
and top parameters will determine the child view’s x and y and the
right and bottom will determine its width (right – left) and height
(top-bottom).
So your TreeViewGroup code will look like :
#Override
protected void onLayout(boolean changed, int l, int t, int r, int b) {
int count = getChildCount();
for (int i = 0; i < count; i++) {
View child = getChildAt(i);
if (child.getVisibility() != GONE) {
ViewGroup.LayoutParams lp = (ViewGroup.LayoutParams) child
.getLayoutParams();
int childLeft = 0;
int childTop = 0;
child.layout(childLeft, childTop,
childLeft + child.getMeasuredWidth(),
childTop + child.getMeasuredHeight());
}
}
}
#Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
measureChildren(widthMeasureSpec, heightMeasureSpec);
int measuredWidth = 200; // Calculate the height
int measuredHeight = 200; // Calculate the width
setMeasuredDimension(measuredWidth, measuredHeight);
}
Refer this link http://arpitonline.com/2012/07/01/creating-custom-layouts-for-android/
I have created a scrollview and an imageview is placed within it. I'd like on scroll for it to resize in the same fashion it is done in the image below but so far I've had little success.
In my attempts the image is resized on scroll but, there is space left over after the resize. How would you modify the below:
Image:
My Code so far:
activity_main.xml
<ImageView
android:layout_gravity="center"
android:adjustViewBounds="true"
android:layout_width="601dp"
android:layout_height="250dp"
android:paddingTop="0dp"
android:paddingLeft="0dp"
android:paddingRight="0dp"
android:scaleType="fitXY"
android:id="#+id/contactPic"
android:src="#drawable/stock"
android:clickable="true"/>
MainActivity:
#Override
public void onScrollChanged(ObservableScrollView scrollView, int x, int y, int oldx, int oldy) {
final ImageView contactPicture = (ImageView) findViewById(R.id.contactPic);
final RelativeLayout contactLayout = (RelativeLayout) findViewById(R.id.ContactRLayout);
if (scrollView == contactScrollView) {
View view = (View) scrollView.getChildAt(scrollView.getChildCount() - 1);
int distanceFromPageEnd = (view.getBottom() - (scrollView.getHeight() + scrollView.getScrollY()));
Log.e("onScrollChanged", "distance from bottom = " + String.valueOf(distanceFromPageEnd));
if (distanceFromPageEnd >= 1408)
{
contactPicture.getLayoutParams().height = (distanceFromPageEnd - 1408);
contactPicture.requestLayout();
}
}
ScrollViewListener:
public interface ScrollViewListener {
void onScrollChanged(ObservableScrollView scrollView, int x, int y, int oldx, int oldy);
}
ObservableScrollView:
public class ObservableScrollView extends ScrollView {
private ScrollViewListener scrollViewListener = null;
public ObservableScrollView(Context context) {
super(context);
}
public ObservableScrollView(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
}
public ObservableScrollView(Context context, AttributeSet attrs) {
super(context, attrs);
}
public void setScrollViewListener(ScrollViewListener scrollViewListener) {
this.scrollViewListener = scrollViewListener;
}
public void onOverScrolled(int scrollX, int scrollY, boolean clampedX, boolean clampedY) {
super.onOverScrolled(scrollX, scrollY, clampedX, clampedY);
}
#Override
protected void onScrollChanged(int x, int y, int oldx, int oldy) {
super.onScrollChanged(x, y, oldx, oldy);
if(scrollViewListener != null) {
scrollViewListener.onScrollChanged(this, x, y, oldx, oldy);
}
}
}
There is simple example below that shows how to achieve parallax effect.
First, put your ImageView and other views into FrameLayout:
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/scrollView"
android:layout_width="match_parent"
android:layout_height="match_parent">
<FrameLayout
android:id="#+id/flWrapper"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<ImageView
android:id="#+id/contactPic"
android:layout_width="match_parent"
android:layout_height="#dimen/contact_photo_height"
android:scaleType="centerCrop"
android:src="#drawable/stock" />
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="#dimen/contact_photo_height">
<!-- Other Views -->
</LinearLayout>
</FrameLayout>
</ScrollView>
LinearLayout's top margin is equal to the ImageViews's height (#dimen/contact_photo_height in our example).
Then we should listen scroll position of the ScrollView and change the position of ImageView:
#Override
protected void onCreate(Bundle savedInstanceState) {
<...>
mScrollView = (ScrollView) findViewById(R.id.scrollView);
mPhotoIV = (ImageView) findViewById(R.id.contactPic);
mWrapperFL = (FrameLayout) findViewById(R.id.flWrapper);
mScrollView.getViewTreeObserver().addOnScrollChangedListener(new ScrollPositionObserver());
<...>
}
private class ScrollPositionObserver implements ViewTreeObserver.OnScrollChangedListener {
private int mImageViewHeight;
public ScrollPositionObserver() {
mImageViewHeight = getResources().getDimensionPixelSize(R.dimen.contact_photo_height);
}
#Override
public void onScrollChanged() {
int scrollY = Math.min(Math.max(mScrollView.getScrollY(), 0), mImageViewHeight);
// changing position of ImageView
mPhotoIV.setTranslationY(scrollY / 2);
// alpha you could set to ActionBar background
float alpha = scrollY / (float) mImageViewHeight;
}
}
padding does not work as expected in custom ViewGroup
Hi:
My layout have the following structure:
RelativeLayout(with padding)
MainView(ViewGroup)
And the activety_main.xml:
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#ffffff"
android:paddingBottom="16dp"
android:paddingLeft="16dp"
android:paddingRight="16dp"
android:paddingTop="16dp"
tools:context=".MainActivity" >
<com.example.testandroid.MainView
android:layout_width="match_parent"
android:layout_height="match_parent" />
</RelativeLayout>
MainView:
public class MainView extends ViewGroup {
public MainView(Context context, AttributeSet as) {
super(context);
addView(new MyView(context, null));
}
#Override
protected void dispatchDraw(Canvas canvas) {
canvas.drawColor(Color.GREEN);
super.dispatchDraw(canvas);
}
#Override
protected void onLayout(boolean changed, int l, int t, int r, int b) {
for (int i = 0, len = getChildCount(); i < len; i++) {
View v = getChildAt(i);
v.layout(l,t,r,b);
}
}
}
MyView:
public class MyView extends SurfaceView implements Callback {
public MyView(Context contex, AttributeSet as) {
super(contex, as);
getHolder().addCallback(this);
}
#Override
public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
refresh();
}
private void refresh() {
SurfaceHolder holder = getHolder();
synchronized (holder) {
Canvas canvas = holder.lockCanvas();
if (canvas != null) {
try {
Paint p = new Paint();
p.setColor(Color.RED);
canvas.drawCircle(10, 10, 10, p);
} finally {
holder.unlockCanvasAndPost(canvas);
}
}
}
}
#Override
public void surfaceCreated(SurfaceHolder holder) {
refresh();
}
#Override
public void surfaceDestroyed(SurfaceHolder holder) {
}
}
Now, this is what I got now:
As you can see, the viewgroup I created MainView has a background of green.
And MainView add a MyView dynamically whose background is black here.
Now, the problem is that what the MyView have a padding relative to MainView? Because I want it take all the space of MainView, that's to say, the greed should be invisible.
Why?
But
When you layout your children, it needs to be relative to your position.
To fill yourself you would do child.layout(0, 0, getWidth(), getHeight());.
Try doing this ...
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_margin="16dp"
tools:context=".MainActivity" >
<com.example.testandroid.MainView
android:layout_width="match_parent"
android:layout_height="600dp"
/>
</RelativeLayout>
I am using Horizontal Scroll View, dynamically i will add items in to that. if no. of items are more than displaying items on the screen i want to show image(arrow) at the edges ( like scroll view shows fading edges). How can i do it.
just look at below image, i want create like that.
this is the xml code
<HorizontalScrollView
android:layout_width="wrap_content"
android:scrollbars="none"
android:id="#+id/app_category"
android:layout_below="#+id/top_layout"
android:background="#drawable/minitopbar"
android:layout_height="30dp">
<LinearLayout
android:orientation="horizontal"
android:id="#+id/app_category_scroll_layout"
android:layout_width="wrap_content"
android:layout_height="fill_parent"/>
</HorizontalScrollView>
A. You have to create your own class, that extends HorizontalScrollView:
public class ExtendedHorizontalScrollView extends HorizontalScrollView {
private IScrollStateListener scrollStateListener;
public HorizontalScrollViewForMenu(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
}
public HorizontalScrollViewForMenu(Context context, AttributeSet attrs) {
super(context, attrs);
}
public HorizontalScrollViewForMenu(Context context) {
super(context);
}
#Override
protected void onLayout(boolean changed, int l, int t, int r, int b) {
super.onLayout(changed, l, t, r, b);
prepare();
}
private void prepare() {
if (scrollStateListener != null) {
View content = this.getChildAt(0);
if (content.getLeft() >= 0)
scrollStateListener.onScrollMostLeft();
if (content.getLeft() < 0)
scrollStateListener.onScrollFromMostLeft();
if (content.getRight() <= getWidth())
scrollStateListener.onScrollMostRight();
if (content.getLeft() > getWidth())
scrollStateListener.onScrollFromMostRight();
}
}
#Override
protected void onScrollChanged(int l, int t, int oldl, int oldt) {
super.onScrollChanged(l, t, oldl, oldt);
if (scrollStateListener != null) {
if (l == 0)
scrollStateListener.onScrollMostLeft();
else if (oldl == 0)
scrollStateListener.onScrollFromMostLeft();
int mostRightL = this.getChildAt(0).getWidth() - getWidth();
if (l >= mostRightL)
scrollStateListener.onScrollMostRight();
if (oldl >= mostRightL && l < mostRightL)
scrollStateListener.onScrollFromMostRight();
}
}
public void setScrollStateListener(IScrollStateListener listener) {
scrollStateListener = listener;
}
public interface IScrollStateListener {
void onScrollMostLeft();
void onScrollFromMostLeft();
void onScrollMostRight();
void onScrollFromMostRight();
}
}
B. Use it defining of layout:
<LinearLayout
.....>
<ImageView
android:id="#+id/navigation_left"
..... />
<your.custom.view.package.ExtendedHorizontalScrollView
android:id="#+id/scroller"
android:layout_width="0px"
android:layout_weight="1"
android:fadingEdge="none"
....>
<LinearLayout
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="match_parent" />
</your.custom.view.package.ExtendedHorizontalScrollView>
<ImageView
android:id="#+id/navigation_right"
..... />
</LinearLayout>
C. Add logic for disabling arrows when you can't scroll any more.
((ExtendedHorizontalScrollView)findViewById(R.id.scroller)).setScrollStateListener(new IScrollStateListener() {
public void onScrollMostRight() {
((View) scroller.getParent()).findViewById(R.id.navigation_right).setVisibility(View.INVISIBLE);
}
public void onScrollMostLeft() {
((View) scroller.getParent()).findViewById(R.id.navigation_left).setVisibility(View.INVISIBLE);
}
public void onScrollFromMostLeft() {
((View) scroller.getParent()).findViewById(R.id.navigation_left).setVisibility(View.VISIBLE);
}
public void onScrollFromMostRight() {
((View) scroller.getParent()).findViewById(R.id.navigation_right).setVisibility(View.VISIBLE);
}
});
An easy alternative is to make a scrollview without fading edges and then add the image with arrow below or on top of the scrollview.
Your xml something similar:
<FrameLayout
android:layout_width="fill_parent"
android:layout_height="fill_parent">
<ListView
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:layout_alignParentTop="true"
android:fadingEdge="none"
/>
<RelativeLayout
android:layout_width="fill_parent"
android:layout_height="fill_parent">
<View
android:layout_height="6dp"
android:layout_width="fill_parent"
android:layout_alignParentBottom="true"
android:background="#drawable/background_effect"/>
</RelativeLayout>
</FrameLayout>