PopUpWindow for a RecyclerView Item not positioned normally - android

Ok, I will try to describe the problem as best as I can.
I have a RecyclerView and a bunch of ViewHolder items.
Each ViewHolder has a button.
My goal is, to display a PopUpWindow right under the button that I click.
I set up the listeners, and I know 100% that I am touching the item that I intended to touch.
The problem is when I touch items that are way down the RecyclerView things get really weird.
Nothing is positioned within the screen boundaries, so when I call myPopUp.showAsDropDown(myButton) so if the item that I clicked on is the 1st or 2nd one let's say (where I have 2 ViewHolders occupying the screen at one time) I'm able to see the PopUpWindow normally. But, if I click on an item that isn't visible unless if I scroll down, the PopUpWindow is getting displayed but it's off the screen boundaries, which I kinda understand why but I don't know how to fix it, is this a bug?
Any help would be appreciated, I hope I was clear, If I wasn't I will expand, thanks!
UPDATE:
I Logged the coordinates of the View item when scrolling it into the screen in the middle, it is like 1200 y-value, where my screen is only like 1400.
So I guess my question can be rephrased into, "how can I make sure that view items in the recycler view give me accurate absolute coordinates based on where they are on the screen, instead of where they are in the recycler view?
Ok so after more testing, I see that when I click on the item, it gives correct absolute coordinates, then when after scrolling upwards where the 2nd item is now the 1st (visually) I click on it, and it gives a similar absolute y-value, which is good. But when I scroll to the 3rd item it gives me the original y-value of that item which is way higher than expected.

The view you pass for the popup will decide the popup location.
Now try with
myPopUp.showAsDropDown(myButton, x, y)
with x and y got from location calculation:
int[] originalPos = new int[2];
itemView.getLocationOnScreen(originalPos);
//or view.getLocationOnScreen(originalPos)
int x = originalPos[0];
int y = originalPos[1];

Related

RecyclerView LayoutManager - force to keep a view even if not visible

I am animating views between two RecyclerView. The first one is something like a list of folders showing the first item as cover, clicking it opens a new view showing the folders content animating the cover to the first item. Clicking back animates all visible views back to the folder where they came from (the cover being the top most view). This looks great as long as the opened folder shows the first item. If I scroll down the first item will be offscreen and the back animation does not look that good anymore because the cover view is not animated (I'm only animating all visible views currently).
What I think would work is following: the LayoutManager could position the first item at a position shortly offscreen and keeps it as a special view in it's pool so that u always can access the first view and when I animate back to the folder view I can animate the cover in addition to all other currently visible items ( the cover will be animated from top of the screen).
This means I need following:
the LayoutManager must handle the first item as a special one that is not recycled (I may need it any time for the back animation)
the first item must always be layed out (either at the default position in the list, if it is visible or offscreen directly above the screen), again because I may need it at any time for the back animation
Can someone help me where to start here? I think this is possible with extending the LayoutManager but I don't know where to start...
Have you tried the following?
recView.getRecycledViewPool().setMaxRecycledViews(TYPE_XXXX, 0);

How can I scroll item to middle of screen in scrollView when I press them

My project need to insert lots of data,I use scrollview to put them in one page.
Now I want it can scroll the item I press(primary Edittext) to the middle of screen.
I tried to use onFocusChangeListener()+scrollTo() with edittexts,but doesn't work very well.
Is there any better way to do it?
Have an onTouchListener for the scrollview.
When the user touches the screen, grab the x and y coordinates and then simply scroll to that point. So scrollview.scrollTo(x,y).
See here for more info

Position of GONE Views

I have a ScrollView->TableLayout->TableRow
Inside the TableLayout thare are some TableRows visible and some gone. Its because clicking a TableRow, some other rows below it will become VISIBLE.
Its everything ok now, except that the rows that I turned VISIBLE may not appear in the screen because they arent in the scrollview display area.
I wanna display them without the user scroll, so I need to get the row position to do the scroll.
The problem is, the Draw inst immediately, so I cant get the position. I tryed invalidate and postinvalidate but inst working.
What should I do?
EDIT: What I realy want is a way to update positions and sizes of my views.
I found the solution here (Android) Why won't invalidate() update my buttons immediately?
Do you know where the newly-visible cells are going to be drawn? If you have, say, the cell immediately above it (which would make sense if you're adding the rows with addView()), you can get the bottom position of the cells immediately above your newly-visible cells (with getChildAt() then calculating the vertical offset), and then use scrollTo() (or the sexier smoothScrollTo()) to scroll to that position - that should scroll so that the new row is at the top of the screen. Highlighting the new row somehow would also help the user see that this is the new content.
if you can calculate the rowHeight. or the height of each row. then you may be able to calculate the position where the row (view) may appear.
and you can call the
scrollView.scrollBy(x, y)
or
scrollView.scrollTo(x, y)
in the scroll view.

How can I scroll ListView continually with a constant velocity from code?

I have a ListView in which the user can drag&drop list elements to reorder the list (android 3.0). However, I have to handle the case when the list is long, and the user has to be able to scroll it during dragging an item. So I've put two scroll-areas onto the screen, one at the top and one at the bottom. When the user drags an item onto these, the ListView should start to scroll up/down with a constants speed, as long as the dragged item is in these areas.
How can I achieve this scrolling with ListView?
I've tried the smoothScroll...() methods but they need a specific position in the list to scroll to, or a specific distance to scroll by. The standard scrollBy...() methods don't work either, they scroll the ListView, but don't appear to invalidate is properly, so the appearing rows don't get rendered.
Any ideas?
You could try listView1.smoothScrollByOffset(int viewPosition). This way you could make the listview scroll up and down by an interval of 1+ views.
You could try smoothScrollToPositionFromTop(int position, int offset, int duration) with varying duration depending on the position where to scroll, like say
int duration = position*100;

Need help animating an Android ListView

I have a ListView in my Android application. The individual views in the list are a little bit smaller than the size of the screen.
I want the list to always show one item centered in the screen, with just a small sliver of the previous and next items showing above and below it.
When the user scrolls, I need to reposition the child view at position 0 or 1 (depending on which way they are scrolling). Currently I am doing this by calling "setSelectionFromTop" in my onScrollStateChanged method. This works, but the transition is immediate, not smooth. It is jarring and confusing in a lot of cases.
What's the best approach to fixing this? I want to animate the process of scrolling the list into the position I want, but I can't find any methods in ListView or its superclasses that let me directly control the scroll position of the entire list.
I think I could animate it using multiple calls to setSelectionFromTop(int position, int y) with progressive values of y, but I don't know how to determine the initial value of y. Is there some way to get that by interrogating the view object at the designated position?
Another challenge I have in front of me is that I want to animate the removal of an item from the list - by having it either disappear or slide away to the left, and then having the surrounding views move up and down to fill the space. Is there a straightforward and reliable way to do this with a ListView? Should I just give up on the ListView and write the whole thing as a custom view from scratch?
Thanks.
This definitely should be possible. Does smoothScrollToPosition() work?
Otherwise, you can try simulating the touches using TouchUtils.

Categories

Resources