How to display an array of UILabels? - iphone

I have a list of items I'd like to show in a UITableViewCell. Right now, I'm simply using a cell.textLabel with commas separating each value, but I'd like to do something a little more dynamic.
How would I achieve something like this?
Would it be an array of UILabels with borders and radius on those borders?
Thanks for your ideas.

Here's a possible quick and easy way to do this. It's based on the code that you can get here.
Note that you have to add the QuartzCore framework to your project and include in the file where you write this code!
Every UIView is backed by a CALayer. You can get at the UIView's CALayer with the .layer property. Since a UILabel is a UIView, you can get its backing layer this way. Once you have the backing layer, you can set its backgroundColor, cornerRadius, borderColor, and borderWidth properties. That should let you create the rounded effect.
To get the centered effect, try setting the UILabel's textAlignment to UITextAlignmentCenter. Then, you could try setting the UILabel's frame based on sizeThatFits, or maybe based on calling sizeWithFont on the string you're putting into the label.
Here's some quick, totally untested code to get you started.
Assume that somewhere you've initialized a UIFont as follows (put in whatever size you want for the font).
labelFont = [UIFont systemFontOfSize:14];
Then, for each label, set it up as follows.I'm assuming you've pulled the text out of an array and put into a variable called "text". X_PADDING and Y_PADDING are how much spacing you want around the label's text. xLoc and yLoc are variables you're using to keep track of the x and y position you want to put the labels at. You'll probably increase xLoc based on textSize + X_PADDING + LABEL_SPACING or something (where you define LABEL_SPACING):
CGSize textSize = [text sizeWithFont:labelFont];
CGRect frame = CGRectMake( xLoc, yLoc,
textSize.width + X_PADDING,
textSize.height + Y_PADDING);
UILabel *label = [[UILabel alloc] initWithFrame:frame];
label.text = text;
label.textAlignment = UITextAlignmentCenter;
CALayer *layer = label.layer;
layer.masksToBounds = YES;
layer.cornerRadius = 7.0; // or whatever works for you
layer.borderWidth = 1.0;
layer.borderColor = [[UIColor redColor].CGColor;
layer.backgroundColor = [UIColor blueColor].CGColor;
// Add the layer into its superview
[yourSuperview addSubview:label];
I hope this helps get you started.

Related

Placing Text in UITextField

textField.layer.backgroundColor = [UIColor lightGreenColorTransparent].CGColor;
textField.layer.cornerRadius = 8.0f;
textField.layer.borderColor = [UIColor lightGrayColor].CGColor;
textField.layer.borderWidth = 1.0f;
How can I set the text for about 5px to the right that there is more space between the border and the beginning of the text?
UIView *paddingView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, 5, 20)];
textField.leftView = paddingView;
textField.leftViewMode = UITextFieldViewModeAlways;
set the leftView property for padding the UITextField.
drawTextInRect:
Draws the receiver’s text in the specified rectangle.
- (void)drawTextInRect:(CGRect)rect
Parameters
rect
The rectangle in which to draw the text.
Discussion
You should not call this method directly. If you want to customize the drawing behavior for the text, you can override this method to do your drawing.
By the time this method is called, the current graphics context is already configured with the default environment and text color for drawing. In your overridden method, you can configure the current context further and then invoke super to do the actual drawing or you can do the drawing yourself. If you do render the text yourself, you should not invoke super.
Availability
Available in iOS 2.0 and later.
Declared In
UITextField.h
textField.contentInset = UIEdgeInsetsMake(4,8,0,0);

Draw rectangle in custom table cell

How would I draw a rectangle in a custom table cell class? The cell currently has a background image with a few text labels. I would like to draw a rectangle behind each of the labels so they are easier to read over the detailed background image.
I know I could just set the background colour of the label but I would like to have padding between the background colour and the text. If that is possible, I'd love to know how! :)
I'm subclassing a TTTableMessageItemCell in Three20, a method below gets called in which you can play with subviews of the cell,
- (void)layoutSubviews {
[super layoutSubviews];
CGFloat padding = 16;
CGFloat boxWidth = self.contentView.width - 2*padding;
CGFloat textWidth = boxWidth - (padding*2);
CGFloat textHeight = 100;
CGFloat top = kTableCellSmallMargin;
// Position Heading Text
_titleLabel.frame = CGRectMake(padding, top, textWidth, _titleLabel.font.ttLineHeight);
top += _titleLabel.height;
// Position Detail Text
[self.detailTextLabel sizeToFit];
self.detailTextLabel.top = top+2*padding;
self.detailTextLabel.left = 2*padding;
self.detailTextLabel.width = textWidth;
self.detailTextLabel.height = 100;
}
I would like the rectangles to be placed behind the _titleLable and detailTextLabel labels.
edit
I have been able to add the right box using the following,
UIView *view = [[UIView alloc] init];
view.backgroundColor = [UIColor whiteColor];
view.frame = CGRectMake(padding, top, textWidth, textHeight+2*padding);
[self insertSubview:view belowSubview:self.detailTextLabel];
It is laying on top of the label and I cant seem to get it behind it...
edit
I was adding the view to the wrong subview, fixed it with,
[[self.subviews objectAtIndex:0] insertSubview:view atIndex:0];
You can add the labels to views and these to the cell.
You could use insertSubview:belowSubview: to add views behind your labels. With backgroundColor and the right frame they will do what you intend to.
You can also bring detailLabel to front

How to draw a line in interface builder in Xcode 4

I'd like to draw a simple inset line in Interface Builder to separate some items in a list and make the UI a bit more tidy. I don't see any "line" or similar objects in the objects library and can't seem to find any drawing commands in Interface builder.
I use a very narrow UIView with backgroundColor set to the appropriate color.
There are no lines in the iPhone UI library. This functionality on Max OS X was supplied by NSBox, but on the iPhone there is no corresponding UI element.
If you're afraid a UIView might affect performance, you can draw a line in code using CoreGraphics' CAShapeLayers.
Every UIView has a CALayer, so draw the line and add it to the views CALayer.
You can do this either in a custom UIView's drawRect or in your view controller:
(Make sure to add Quartz framework to your project)
UIBezierPath *linePath = [UIBezierPath bezierPathWithRect:CGRectMake(0, 0,self.view.frame.size.width, 1)];
//shape layer for the line
CAShapeLayer *line = [CAShapeLayer layer];
line.path = [linePath CGPath];
line.fillColor = [[UIColor blackColor] CGColor];
line.frame = CGRectMake(xPosition, yPosition, self.view.frame.size.width,1);
[self.view.layer addSublayer:line];
In place of view, why not just use a label and set the appropriate background color?
I used a view and made it narrow & changed the color to make it look like a line. But my issue is I am using the line on a vertical scrollview and the lines also get scrolled.
Interface Builder does not allow you to draw the shadows essential for an inset line. If you work with Photoshop you know this.
The following code will draw an "inset" if the line is in front of a white/beige Background.
UIView *line = [[UIView alloc] initWithFrame:CGRectMake(0, 0, width, 1.0f)];
line.backgroundColor = [UIColor colorWithRed:(200.0f/255.0f) green:(200.0f/255.0f) blue:(200.0f/255.0f) alpha:1.0f];
line.layer.shadowColor = [UIColor darkGrayColor].CGColor;
line.layer.shadowOffset = CGSizeMake(0.0f, 1.0f);
line.layer.shadowRadius = 0.5f;
line.layer.shadowOpacity = 0.4f;
line.layer.masksToBounds =NO;
[Background addSubview:line];
Remember to import < QuartzCore/QuartzCore.h>.
As an alliterative - in Interface Builder, add a view who's height is set to 2 points. Wire up a IBOutlet to that view and set its layer border color and width:
self.mySeparatorLine.layer.borderWidth = 1.0f;
self.mySeparatorLine.layer.borderColor = [UIColor lightGrayColor].CGColor;
You can use Progress View as an option for a horizontal line. Just change the tint color and progress to 1 which is 100%.

How to prevent a UILabel cutting off with '...'

I was wondering if there is any way to prevent an UILabel from cutting off with '...'? I have a CGRect which is 55 in width and 20 in height and I would like it to simply cut off after 55 (or clip the contents off) without indicating with '...' that there is more.
UILabel *btnTitle = [[UILabel alloc] initWithFrame:CGRectMake(0, 0, 55, 20)];
btnTitle.text = labelMe;
btnTitle.textColor = [UIColor whiteColor];
btnTitle.backgroundColor = [UIColor clearColor];
btnTitle.transform = CGAffineTransformMakeRotation( ( 90 * M_PI ) / 180 );
I achieved what I wanted (i.e. the clipping) by putting the UILabel (with increased width, i.e. 100 x 20) into an UIView (55 x 20) and set clipsToBounds to YES with the result that I couldn't click my buttons anymore - because I was using the label to label a button. The UIView containing the label was hiding my buttons...
Is there a way around this without using an UIView to clip the contents of my UILabel?
Try this out:
label.lineBreakMode = NSLineBreakByClipping;
For more information, refer UILabel Class Reference
Hope this helps
Use UILineBreakModeClip or one of the other options. Set it with the UILabel lineBreakMode property.
You can tell your view that contains your label to ignore touches and send them to the next available responder to do this just add this method to your view.m file
- (BOOL)pointInside:(CGPoint)point withEvent:(UIEvent *)event{
return NO;
}
Swift4 version of Ole Begemann/eddyce's answer:
label.linebreakMode = NSLineBreakMode.byClipping
Swift 5 version of Ole Begemann's answer:
label.lineBreakMode = .byClipping

Round corners on UITableView

What is the best way to get round corners on an entire UITableView as seen in Stocks and Spotlight? The grouped style doesn't solve the problem because the round corners scroll away with the cell. I'm trying to clip the view so the corners are always round regardless of scroll position.
I saw another discussion about doing this to a UIImage that suggested masking it with another image. I'm not sure if this would work because I need taps to pass through to the table. This isn't isn't ideal for me because I want the background pattern to show through through the corners.
It's an old question but perhaps you still want to know how to do this.
I reproduced a tableView like in Stocks/Spotlight. The trick is
view.layer.cornerRadius = 10;
For this to work you need to include the QuartzCore into the class that you call that property:
#import <QuartzCore/QuartzCore.h>
I heard that this only works since OS 3.0. But since my application is using core data it wasn't a problem because it was already for OS 3.0 and hight.
I created a custom UIView with a subview with cornerRadius 10 and with
view.backgroundColor = [UIColor clearColor];
Then you have to place an UITableView grouped style in that subview. You need to set the backgroundColor to clearColor and the separatorColor to clearColor. Then you have to position the tableview inside the rounded corner view, this is done by setting the frame size and origin. My loadView class of my custom UIView looks like this:
self.view = [[UIView alloc] init];
self.view.backgroundColor = [UIColor clearColor];
CustomUIViewClass *scherm = [[CustomUIViewClass alloc] init];
CGRect frame;
frame.origin.x = 10;
frame.origin.y = 50;
frame.size.width = 300;
frame.size.height = 380;
scherm.frame = frame;
scherm.clipsToBounds = YES;
scherm.layer.cornerRadius = 10;
[self.view addSubview:scherm];
CustomUITableViewClass *table = [[CustomUITableViewClass alloc] initWithStyle:UITableViewStyleGrouped];
frame.origin.y = -10;
frame.origin.x = -10;
frame.size.width = 320;
frame.size.height = 400;
table.tableView.frame = frame;
[scherm addSubview:table.tableView];
I hope you understand my english, maybe I will write a short blog post about this technique with a sample project, will post the link here when I'm ready.
An easier way to do this is to simply import the QuartzCore framework to your project. #import <QuartzCore/QuartzCore.h> to your tableViewController and just set
myTableView.layer.cornerRadius=5;
This will give you rounded corners without having to add your tableview to a superView or clipping it.
Instead of hacking through the code, here's an easy to mimic the grouped style. This works if all you want is one section.
In Interface Builder:
Set UITableView style to Plain and make the frame with some padding on the left and right, perhaps with x = 10 and width = 300.
Then set the corner radius and color yourself:
#import <QuartzCore/QuartzCore.h>
self.tableView.layer.borderColor = [UIColor colorWithWhite:0.6 alpha:1].CGColor;
self.tableView.layer.borderWidth = 1;
self.tableView.layer.cornerRadius = 4;
Have you tried the "grouped" table view style?
self.tableView.style = UITableViewStyleGrouped;
For further reference, see the Table View Programming Guide. The "About Table Views" chapter has some nice screenshots describing the different styles.
Well, there is alot of approach to solve this problem.
However, in my case, all doesn't work correctly. My table sometimes is smaller than table size.
I will share the way I did. I belive is alot easer and faster than some options above.
Make the first and last item rounded.
Create CAShapeLayer for top(left|right) and bottom(left|right).
shapeTop = [CAShapeLayer layer];
shapeTop.path = [UIBezierPath
bezierPathWithRoundedRect:CGRectMake( 0.0f, 0.0f, 306.0f, 58.0f )
byRoundingCorners:UIRectCornerTopLeft | UIRectCornerTopRight
cornerRadii:CGSizeMake( 6.0f, 6.0f )].CGPath;
shapeBottom = [CAShapeLayer layer];
shapeBottom.path = [UIBezierPath
bezierPathWithRoundedRect:CGRectMake( 0.0f, 0.0f, 306.0f, 58.0f )
byRoundingCorners:UIRectCornerBottomLeft | UIRectCornerBottomRight
cornerRadii:CGSizeMake( 6.0f, 6.0f )].CGPath;
The table need to be backgroud clearColor;
The cells has to be a colored background;
Set the layer.mask of it
UIView* backgroundView = [[UIView alloc] initWithFrame:CGRectZero];
backgroundView.backgroundColor = [UIColor whiteColor];
cell.backgroundView = backgroundView;
Don't forget #import <QuartzCore/QuartzCore.h>
I recently came across this problem and solved it a different way. Thought I'd share the results with everyone.
I created a rectangular UIView with a clear, rounded-corner interior, and then laid that on top of the UITableView. You can find the full description at my programming blog.
It works exactly the way I want.
Below code for Swift version :
let redColor = UIColor.redColor()
self.tableView.layer.borderColor = redColor.colorWithAlphaComponent(0.9).CGColor
self.tableView.layer.borderWidth = 1;
self.tableView.layer.cornerRadius = 4;
Make sure that you have import QuartzCore in import section.
Here is swift extension:
extension UITableView {
public var cornerRadius: CGFloat {
get {
return layer.cornerRadius
}
set {
layer.cornerRadius = newValue
layer.masksToBounds = true
}
}
}
Used by this way
tableView.cornerRadius = 7.5
UITableViewStyleInsetGrouped
A table view where the grouped sections are inset with rounded corners.
example code:
self.tableView = [[UITableView alloc] initWithFrame:CGRectZero style:UITableViewStyleInsetGrouped];
looks like:
Settings looking table view sections