In one of my Activities I have a ListView that displays a list of locations. For each list item I want a little arrow icon that points in the direction of the corresponding location. I implemented this icon by extending ImageView. This custom View has a listener that reacts to changes of the device's orientation by rotating the icon image accordingly. I register the listener in the onAttachedToWindow() method and unregister it in onDetachedFromWindow(). This kind of works but the problem is that onDetachedFromWindow() sometimes gets called only a long time after the containing Activity has paused. Also, the whole layout overall seems a little hacky. So my question is: Is there a proper way to unregister the listeners or would you implement this in a completely different way to begin with?
I think you're having difficulty because your design is hacky like you acknowledge. I think what you should probably do is have your Activity listen for the device orientation and use onPause/onResume to handle the registering for orientation changes. Then have a custom cursor that is updated by the Activity when it changes. The custom cursor then can call notifyDataSetChanged to tell the ListView to update. Then in the getView call you can pass in the data necessary for your arrow to display correctly. This way the only arrows that will be updated are those that are visible. You'll only have one place where you are receiving orientation data and later you can handle the onScrollStateChanged and stop updating the arrows when the user is scrolling if it impacts the scroll animations too much.
Related
I would like to start by saying if you can think of a better title for this problem, feel free to change it since I have no clue how to explain this in a short way.
So here is my problem:
For the application I am trying to make I have these schedules, one schedule for today, and one for upcoming days. Both of these are a listview inside a fragment.
(I used those fragments to create tabs to seperate the two.)
Each game (let's call them games because calling them activities would be confusing) on the schedule has a status, and here is where the annoying part comes. I have been asked to check if any game has been started, and if so I need to disable the buttons to start any other game than the one that is already ongoing.
EDIT: The main problem is that I cannot use findViewById on the listview item because apparently it is a null object reference
I made a little "paint"ing to give you more of a graphical representation.
So long story short, I need a way to check the status inside of every listview item inside of the listview inside of the fragment inside the activity to use said status to disable every button except for the one of the ongoing game.
Little side note: If no games have been started yet, all buttons are enabled.
I hope this made sense.
If you want some code to go with this, feel free to ask but be warned, I am making this inside a testing app so a lot of useless testing data and sloppy code.
EDIT:
This is where I am stuck in a more clear example:
The start buttons are enabled but should be disabled.
Scrolling further down the list, there is a started 'game' and right below it, a game with the same status as in the previous picture where the button is disabled as it should be.
This is because the "isStartable" boolean in my code goes to false after the game with status "start" has passed and the following items are disabled.
When I scroll back up, it is how it should be, the items are all disabled but I need them to be like this when the listview gets filled. Any way to refresh the data in this listview and taking the "isStartable" boolean with it?
This is what it looks like after I scroll back up.
create a model class for your listview data items. Set a boolean variable in model class like isGameStarted. Set that variable as per your result.Then in your listview adapter, put a condition as below
if(isGameStarted){
holder.startButton.setEnable(true);
else
holder.startButton.setEnable(false);
I'm using Recyclerview to show a list. I want to delete some items like IOS. In my listview template I have added a button to delete item which is invisible by default. In my activity I have another button attached at bottom (Not part of listview) and on tap of this button I want to make all delete buttons of listview visible.
My Question is how can I get reference to all delete buttons of listview in activity and is it the right way to do this?
Thanks
Assuming you have ViewHolders set up, you already have references to all the buttons in your list. All you have to do is to make them visible for every item in the list with a simple loop.
In case you haven't implemented ViewHolders I suggest you check out the documentation and take a look at some simple tutorials on how to use them.
On a side note. If I understood correctly you're making a bottom tab for your app and since you referenced iOS I gotta say this; Remember that Android and iOS are two unique operating systems with their own ways of handling things. Check out Googles pure Android documentation.
In your question title you say RecyclerView, but in your text you say ListView. The solution is similar either way, but it's best to be perfectly clear what you're doing.
In either case, there are at least two different solutions.
First, you could use a boolean flag to determine if all the the item buttons should be showing or not. You check this flag at the time the item view is inflated or created and toggle the button accordingly. If the boolean flag is ever changed, the easiest thing to do is tell the RecyclerView/ListView that the underlying data has changed and to redraw all the views. Call notifyDatasetChanged on the adapter.
The other thing you can do at the time the item buttons should change is iterate all the visible item views, find the button, and change its visibility. With RecyclerView, you can do this, and with ListView you can do this.
I would like to know some codes on how to restore the Color of ListView after orientation changed. From landscape to potrait and vice versa. Thank you.
I m not sure i understood what you want to achive but if i get it right you have a ListView and you want to color every item with different color.
There are several way of doing this, one and the simplest is to handle the configuration change by yourself by defing the Activity with this:
android:configChanges="keyboardHidden|orientation|keyboard|smallestScreenSize|screenSize"
your Activity won't be recreated on all this events and it will just resize your view without loosing the state. Be carefull this has lots of down sides depending on what you are doing in your Activity/Fragment.
An other solution is to keep track of the state of every ListView item by yourself, so, for instance make an int array and save there the color of all your list view elements and use it to color the view in your adatper getView() call.
In my application, I save data in my sqlite db a variable number of notes composed of: (IDNote,title,body, date of creation, owner of note, icon_name). When i save and query the DB, my data are all ok, so my question is, Is possible to implement GestureDetection for moving and restore a single icon that correspond at a single note ? Because a found an example but all the icons are moved, but i want to move only one icon at time simulating all the gesture of the icons of Desktop computer.
Thanks in advance.
Marco
Set an OnTouchListener on the view that holds your icon. This listener is called when an ACTION_DOWN event on the view is caught.
Here register it somewhere as the 'currently dragged object'. Make sure onTouch() returns false, so the event is propagated further to your views parent.
This parent is responsible for checking whether a view has been registered as the 'currently dragged object'. Also, it has to call your Gesturedetector, which in onScroll will do the actual scrolling and moving.
This is just an idea, tell how it went!
I am using a ListActivity to display an iconified list (using a custom implementation of BaseAdapter). It does not reload data properly. When I change the contents of the adapter and notify the list, it appears that the old data draws on top of the new data, until a scroll event happens. The old rows draw on top of the new rows, but the old rows disappear when I start scrolling.
However if I set the ListActivity style to Theme.Dialog, it refreshes fine. (presumably because when in dialog, the activity resizes each time the list contents changes, which forces a redraw of the whole view hiearchy?)
Any ideas how to make this work in my fullscreen activity?
Thanks.
Did you try to call invalidate() on your listView?
Here are some function you could try:
invalidate()
requestLayout()
forceLayout()
You could even do that, when your thing is iconified( I don't exactly what you mean by that). You could set the adapter of the view to null or an empty adapter. Something empty just enough to not make your activity crash. Then when you want to display your ListView just set the adapter back to it.
That could be linked to drawing cache but it would be good if you could give us some more information.
Oddly enough, if I set a background color, everything refreshes properly. Without the background color, I get the refresh issues I described in the original post.