Custom UITableViewCell with drawRect + normal blue selection - iphone

I have a custom UITableViewCell. All the drawing is done in the drawRect: method and no subviews are added.
The drawing works fine and the scroll speed is good.
But the problem is with the selected cells. I want the selection to behave like it would normally:
Blue gradient selection color
Inverted text color
Animated deselection
I have not been able to achieve all three.
First attempt:
Set selectionStyle = UITableViewCellSelectionStyleNone and do the selection color in the drawRect method.
With this method, I am able to achieve the first two things, but the deselection is instant. So one second it is selected blue, the next second it is deselected. I do not get the nice fade-out.
Second attempt:
selectionStyle = UITableViewCellSelectionStyleBlue
With this method my cell is all gradient blue when selected. The text I have is not visible. The fade-out works nicely, though.
Third attempt:
Set selectionStyle = UITableViewCellSelectionStyleBlue and also set selectedBackgroundView to a UIView where I set the backgroundColor to a transparent blue.
Here the problem is that the selectedBackgroundView (despite the name) is drawn on top of my normal content. So if the selectedBackgroundView is not transparent, I cannot see the text. And if it is transparent, I can see the text, but the selection color gets "faded" and does not look right.
What would be the correct way of achieving all three bullet points?

OK. So the answer to my own question... Don't subclass UITableViewCell for custom drawing. Instead subclass a UIImageView or a UIView.
This post has a nice description of how to do it:
http://cocoawithlove.com/2009/04/easy-custom-uitableview-drawing.html

I'd suggest using the second attempt in combination with a gesture recognizer. Check if the user presses on a cell, if so, set the textcolor in that cell to yellow (or what is the inversion of blue? xD).
Sample code:
- (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldReceiveTouch:(UITouch *)touch {
if (touch.view isKindOfClass:[UIButton class]]) {
//do something with that view, for example:
//change the color of the text in that view,
//or invert it ;)
return YES;
}
return NO;
}
Alternatively, you can attach a UIGestureRecognizer to that button. That way, you get the class called inserted in the selector.
There might be a better option to do what you asked. This just came up my mind, if you have 2/3 points working already, this should help you to get 3/3.

Related

Subclassing UITableViewCell for grouped table

I'm trying to create a a custom subclass of a UITableViewCell to be used in a grouped table.
I'm laying out the subclass with a nib. (I've just tried doing it without the nib but getting the same problem).
Whenever I've done this before I've wanted to create a whole new cell style with a different background etc... so in awakeFromNib I do this...
- (void)awakeFromNib
{
// N.B. I am not doing this, this is how I normally get rid of border
// in this case I want the border so I am not running this code.
self.backgroundView = [[UIView alloc] initWithFrame:CGRectZero];
self.backgroundColor = [UIColor clearColor];
}
but in this case I want to keep the background with the rounded corners and I'm just adding different UI elements to it.
The cell gets created and all the elements are laid out correctly but I'm getting an annoying "second border" in the top left corner of every section.
I have a screen shot showing this.
At first I thought this was a hair on my screen or something but it isn't.
I've tried setting the backgroundView and backgroundColor but that removes the normal cell background and I want to keep them.
Any ideas how I can get rid of this?
EDIT
Just to clarify what I said above about setting backgroundColor and backgroundView.
Here is what happens when I change them...
In this I set the backgroundView to nil. The border remains but so does the little bit I'm trying to get rid of.
If I set the backgroundView to a new UIView then this happens...
I want the same background with the white background and the rounded corners border. Just not with that annoying little bit.

UITableViewCell - How to set selection clipping?

In my app, I have a UITableView and each UITableViewCell utilizes a custom background and style with the following code in the "WillDisplayCell" method:
UIImage *cellBackgroundImage = [UIImage imageNamed:#"TableView_Cell_Background_iPhone"];
UIImageView *backgroundImage = [[UIImageView alloc] initWithImage:cellBackgroundImage highlightedImage:cellBackgroundImage];
[cell setBackgroundView:backgroundImage];
[backgroundImage release];
The problem is that the PNG I'm using as the background is a rectangle, but the UITableViewCell is a rounded rectangle with a specific layer radius property. When I select a cell, the background overrides the rounded nature of the cell and I get a jarring blue highlighted sharp rectangle. Is there a way to set the selected state corner radius or something along those lines? My only other option if not would be to create a PNG background that fits the rounded rectangle perfectly.
Thanks.
I would set the selectionStyle of the cell to UITableViewCellSelectionStyleNone, this stops the blue highlight. Then start to do a custom selection job.
You will have to make a custom subclass of UITalbeViewCell. Override setSelected or if that doesn't work user a gesture recognizer or override touchesBegan etc. I have done it once, before, I forget exactly how, if you have trouble let me know and ill look it up.
When you detect that the cell is selected, perhaps create a translucent overlay as a PNG and make it appear when the cell is selected. Alternatively lower the transparency of the background image or add a color mask.

UITableViewCell labels opaque=YES looks bad when clicking cell

I want my table cells to load fast, so I am setting all my UILabels inside my cell to be opaque=YES; This is fine, because I also set the backgrounds to white and it looks normal.
The problem comes when you click the cell, since the backgrounds of those labels are white, the blue selected color looks pretty bad when trying to highlight the cell. Is there a work around for this? Would setting the background color of those cells to clearColor just defeat the purpose of setting opaque?
There is something you have to consider. First, setting the labels to opaque is definitely the right way of getting good scrolling performance.
The proper way to do this is declaring a subclass of UITableViewCell and overwrite the setBackgroundColor method like this and forward the background color to each element of the cell:
- (void) setBackgroundColor:(UIColor *)color {
[super setBackgroundColor:color];
[titleLabel setBackgroundColor:color];
[imageView setBackgroundColor:color];
[timeLabel setBackgroundColor:color];
}
I used this as the file's Owner of the XIB where the tableview cell is defined and have connected the UI elements to outlets in this custom subclass.

How to put gradient style table cell in a table?

Hey, I am making a custom table cell right now but my custom cell is just white cell with some buttons and labels in background color which looks not that great.
Is there a way to render the background color so that the cell has some vertical gradient effect?
For example, on top of the cell it looks white and as it gets closer to center of the cell, it gets darker.
But as it gets closer to the bottom of the cell, it gets whiter again.
A great example would be this free app called "friendsaroundme".
Another thing is that I don't want to use custom image to do it (i.e make the cell.backgroundcolor = [uicolor colorwithpatternimage:somethingsomething.png..... ) because it's not that flexible.
So is there anyway to render the gradient style programatically?
You can use a CAGradientLayer as the background layer. Remember a table view cell is just a UIView. You can add a new layer to the layer tree with:
[[[self view] layer] addSublayer:gradientLayer];
I wrote a blog post on how to do this with UIButtons. The same technique applies.

Black corners on UITableView Group Style

I have a problem where my UITableView (group style) has a black "tip" above it's rounded corner.
I'm setting up the background of the tableview like so:
[meetingTableView setBackgroundColor:[[UIColor alloc] initWithPatternImage:[[UIImage alloc] initWithContentsOfFile:#"background.png"]]];
And my table view ends up looking like this:
black pointy edge on rounded corner http://papernapkin.org/pastebin/resource/images/imageEntryId/6487
Any ideas how I can get rid of those black points?
I have got the same problem.
When I set clear color by xib, I have the back corner
The solution is to set it by code !
(The same problem with interface builder exist for webviews)
Try this in your controller's viewDidLoad method:
meetingTableView.backgroundColor = [UIColor clearColor];
You'll get Black corners on UITableView Group Style if you set background color to clear color in XIB.
Instead try this code for removing Black corners on UITableView Group Style
tableViewObject.backgroundColor=[UIColor clearColor];
Just in case you weren't already aware, there's another neat technique you can use to make customized backgrounds for UITableViews:
Not quite as simple as setting the background as you're doing, but it gives you a lot more flexibility and can scale to any table size.
Maybe if you put yourTableViewOutlet.backgroundView=nil;
To avoid the black corners you have to make sure that the UITableViewCells are not opaque. It looks like you're using custom styles table cells and the default value for opaque is YES. Either go to Interface Builder and uncheck the opaque checkbox if the table cell was set up in a XIB file. Or use the setOpaque:NO setter to change value.
Because the table cell view still has a rectangular frame even with the rounded corners the cell view and not the actual table view is causing those black corners.
My guess is that it's related to something that you're doing in your custom table view cells. You might want to experiment with setting the cell background color to [UIColor clearColor].
I think you should set the background color of your table as clearColor and initialsie your view with the background image.
Then it will definitely not show the black corners. But also don't forget to set the background color of your cell as white color
The up-voted answer above (set the tableView's background to [UIColor clearColor]) may not work for you if you are like me and never use the UITableViewController, instead putting a UITableView inside a UIViewController.
In this case it's not the tableView that needs to have a clear background, but the view that holds the tableview.
This is not intuitive, but it works for me. In interface builder you can just set the parent view's background color to clear color, or you could do the same in code in viewDidLoad with:
self.view.backgroundColor = [UIColor clearColor];
I'm guessing the reason for the black corners is something about the internal graphics optimization, and setting the background clear fixes it.