Only update visible table view cells? - iphone

I'm trying to load a table view with cells that contain images downloaded off the internet. I'd like to only perform the download operation on cells that are currently visible instead of downloading every image as the user scrolls down quickly.
I found the indexPathsForVisibleRows method and that should fit my needs nicely but I need a way to figure out when the table view is no longer scrolling. My idea is to use the indexPathsForVisibleRows when the table view isn't scrolling so that all of the images currently on screen are loaded without unnecessarily loading images.
Are there any methods that I can override or notifications to subscribe to that will alert me when the table view is no longer scrolling?
Thanks!

Take a look at the methods listed here:
http://developer.apple.com/library/ios/#DOCUMENTATION/UIKit/Reference/UIScrollViewDelegate_Protocol/Reference/UIScrollViewDelegate.html
If your view controller is the delegate of the UITableView, these will also be fired for it, as the UITableView is a subclass of UIScrollView.
Particularly, pay attention to: scrollViewDidEndDecelerating. This is the one I used to do pretty much what you're asking.

Related

Newbie TableView challenges

I am building an app that requires a tableview control so that users can select multiple rows and act upon them in some way. I find it easy to load my data and display it using the UITableViewController but it seems when I do it this way I am unable to place any other controls on the page, such as a toolbar to give the user some actions to perform on the selected rows. I can place a toolbar control on the form in the storyboard, but it doesn't render in the emulator.
Using a UIViewController and placing a TableView on it seems to come with its own set of confusing challenges (that will make total sense once I conquer them).
Is there any advice for a smooth way of getting a table view with toolbar controls? Thanks!
don't use a TableViewController. Use a Standard ViewController, then add a UITableView to it, and adjust the size. This way you will be able to do whatever else you want on that view without limiting yourself to the tableView only functionality.
When you do this make sure you add the datasource and delegate to the connected table. Then add cellForRowAtIndex, number of sections, number of rows, and whatever other delegate methods you need for your table.
Good luck
Is there any advice for a smooth way of getting a table view with toolbar controls?
Yes there are few ways to accomplish this, one way would be adding a footerview to your tableviewcontroller check these
http://developer.apple.com/
UIButtons on tableFooterView not responding to events
Easier way to add this is using storyboard.
Just drag and drop a view in to your tableviewcontroller, then you can adjust the views size and put anything from objects menu to inside of the view.
Now the problem with that is view will not be stable position at the bottom of the page like a tabbar. Lets say you have only 1 row in your tableview, footer view will go up just below that 1 row, lets say you have hundreds of items in your tableview toolbar will be at the bottom of the rows.
The other solutions for your problem would be either create a custom view and adding it to current view or window (this is little bit adbance),but if you want this just google it.
Or just as you said, create a viewcontroller and put a uitableview inside. Dont forget to add <UITableViewDelegate,UITableViewDataSource> to your .h file and then you can call UItableview delegate methods.\
Good Luck.

Calling reload data while scrolling on UIScrollView

I am implementing a UIScrollView which behaves mostly like a UITableView, a bit more advanced with that.. but most of the API used are the same signature.. cellForRowAtIndexPath.. etc. First before people start storming why not just use a UITableView, let me just say that I can't. The reasons are fairly complex, but that is a decision been made.
The issue is now I am implementing infinite scrolling, basically when I scroll down and I am at 65% of the full contentHeight I am doing an async request to the backend to fetch more data and adding it to the data source and then calling reloadData. The issue is that if I am calling reloadData while the user is scrolling, it doesn't provide a very smooth scrolling experience. So what is the best way to tackle this? Also I noticed that reloadData basically refreshes the entire table view (in this case my scroll view). In my table view cell I am animating a UIImage to fade in. So when reloadData is called, the image that is already presented is being faded in again, which is kind of annoying.
How do I avoid such things?
Any tips and tricks?
In case you're still working on this, check out PSTCollectionView. It works exactly like UICollection view but supports backwards of iOS 4.3.
Its difficult to answer without knowing why you need to create a custom view similar to the tableview. If you have a developer account you might want to check the new iOS 6 view based on tableview. Not sure if I can talk more about it as it is under NDA.
For the UIImage fading, how about flagging each UIImage as displayed and then do a check when reloading the data or recalling the fade statement. Only fade the images that are not flagged as already presented?
In new iOS 6.0 there is new controllers call UIContainer view,its similar to UITableview but we can also set more then one column with that.
delegate methods for that controllers are almost same as in UITableview.you can use that controller if you have similar requirements.

Detect jump using a UITableViewIndex

How do you know that you scrolled using the UITableViewIndex ?
I have some basic info to show on my cells, and when I jump/scroll I need to retrieve info about thoses cells by a request for a group(page) of items.
So in order to request only thoses I've stopped to, I need a way to know that I've stopped scrolling (I used scrollViewDidEndDecelerating) but with the UITableViewIndex we ca just jump to another index or scroll though them.
The only feedback that you get is in the UITAbleViewDelegate protocol - none of these report that the table view has scrolled.
However, you will get calls to tableView:cellForRowAtIndexPath: calls to your data source - this will tell you that the table view has moved enough to want a new cell.
Also, you have the visibleCells property of the UITableView itself to see where you are in the table?
It might help if you put more detail into your question - why do you need to know that a scroll has happened?
The UITableView inherits from UIScrollView so you can also implement the UIScrollViewDelegate methods such as scrollViewDidScroll. When the table view scrolls, these will be called.
However, if you explain why you need to know whether the table view has scrolled, there might be a better answer.
Edit:
From your updated question, it's still not totally clear whether you need the scrollview delegate methods.
If you just need to update the contents of the cells themselves, put that in cellForRowAtIndexPath and the table view will automatically call it when the cell comes into view.
If you need to update something outside the table view, you might still be able to do it in cellForRowAtIndexPath or you can handle scrollViewDidEndDecelerating: and then use the table view's visibleCells or indexPathsForVisibleRows methods to get the list of cells currently visible.

How to increase the scrolling performance in my table view with images in iphone?

I am new to iPhone development. I am parsing a xml and display the title, date, contents and image in the cell. Now the scrolling is not smooth, it is stuck.
How can I increase it? I have already applied lazy loading in another view, I am not able to apply in the new view. So how can I increase the scrolling performance? Can I check for any condition that if image is already loaded in the image view, so I can stop once again the loading of image view?
What I do to guarantee fast scrolling in a table is to subclass my own UITableViewCell where I implement all properties that I need.
Whenever that tablecell is initialized I draw the properties of the cell on the cell itself. So when you need an image on there, dont use an UIImageView, but just draw the image on the cell. Also all the text I need I just draw on there.
After a long stuggle finding out how to do all this, I also found a nice blog post about this.
http://blog.atebits.com/2008/12/fast-scrolling-in-tweetie-with-uitableview/
First of all, check if you're not resizing the images - that takes a lot of computing power, and will slow down the table for sure.
Second of all, check for view hierarchy - complicated view hierarchy means bad performance. Rembemer to use as much opaque views as possible, and when you're using non-opaque views don't make the cells too complex(by complex Apple means three or more custom views). If the views are too complex - use drawRect method for custom drawing of the content.
There's a great example on how to achieve this provided by Apple called AdvancedTableViewCell (here's a link), and there's a great tutorial by Apple about table view cells (another link).

Strategy to lazy load images for buttons within UIScrollView?

I have a horizontal UIScrollView that contains UIButtons (though it could be any object). I would like to only download images for these buttons as the user scrolls and they are seen. I would also like an activityindicator running on each button while the images are downloading. Here's what I've tried with results:
Check content offset of uiscrollview and download images for visible buttons. Problem: issues getting activity view shown within subclassed UIButton and not desired usability since images are only downloaded once scrolling stops.
Add subviews (not buttons) to the UIScrollview hoping to use the view's ViewController to initiate a downloaded on viewDidAppear. Problem: viewDidAppear never seems to get called (because I am using addSubView?).
I've seen other apps that do this kind of loading but need some guidance on the typical set-up. Ebay's app is a great example. All items have a default image until the item comes into view, then an activityindicator runs and the items unique image is downloaded.
Thanks for assistance.
Without actually trying it out, here's my idea:
You can use the UIScrollViewDelegate method scrollViewDidScroll: to find out when your scroll view finished scrolling and then use [UIScrollView contentOffset] to determine which part of the scroll view is visible and (CGRect)convertRect:(CGRect)rect fromView:(UIView *)view to determine the button's position within the visible part of the scroll view. Have a method that checks if the button has had its image loaded yet and if not, load it and refresh the view if necessary.
Most such apps are using a UITableView, not a plain scroll view. Joe Hewitt's Three20 framework has a TTImageView class that can do lazy image loading and is pretty well suited to this kind of use.