I need to create a view like below from the array of emails that I receive which also has the delete option.
Something similar to that of gmail's mail recipient except in my this should be scrollview. My main issue is to create the background with delete button which stretches based on the email length. My current approach is to use 3 images one for the beginning, one for the end with delete button and one in general for middle that will stretch. Is there any other or better way to do this?
NOTE:Need to support from iOS 5 and above
Here you go, I have created a SuperLabel for you though it might need some tweak.. But it will help you for sure..
SuperLabel.h
#import <UIKit/UIKit.h>
#interface SuperLabel : UIView
- (id)initWithFrame:(CGRect)frame andTitle:(NSString *)title;
#end
SuperLabel.m
#import "SuperLabel.h"
#define MAX_HEIGHT 25.0
#implementation SuperLabel
- (id)initWithFrame:(CGRect)frame andTitle:(NSString *)title
{
self = [super initWithFrame:frame];
if (self) {
// Initialization code
//Design your label view
self.backgroundColor=[UIColor colorWithRed:.8 green:.8 blue:.8 alpha:1.0];
self.layer.borderColor=[[UIColor orangeColor] CGColor];
self.layer.borderWidth=1.0;
self.layer.cornerRadius=5.0;
//Add a Label
UILabel *label=[[UILabel alloc] initWithFrame:CGRectMake(5.0, 5.0, 100.0, MAX_HEIGHT)];
label.font=[UIFont systemFontOfSize:12.0];
label.textColor=[UIColor grayColor];
label.text=title;
[label sizeToFit];
[self addSubview:label];
//We will get resized frame after using sizeToFit after setting the text in the label.
CGRect rect=label.frame;
//Add a button
UIButton *btn=[UIButton buttonWithType:UIButtonTypeCustom];
[btn setTitle:#"x" forState:UIControlStateNormal];
btn.titleLabel.font=[UIFont systemFontOfSize:12.0];
btn.titleLabel.textColor=[UIColor grayColor];
rect.origin.x=rect.origin.x+rect.size.width;
rect.origin.y=0;
rect.size=CGSizeMake(25.0, MAX_HEIGHT);
[self addSubview:btn];
[btn addTarget:self action:#selector(deleteMe:) forControlEvents:UIControlEventTouchDragInside];
btn.frame=rect;
//Change the whole frame of the label view
frame.size.height=MAX_HEIGHT;
frame.size.width=btn.frame.origin.x+btn.frame.size.width;
self.frame=frame;
}
return self;
}
-(IBAction)deleteMe:(id)sender{
[self removeFromSuperview];
}
#end
And finally add to your view by using following code..
SuperLabel *label=[[SuperLabel alloc] initWithFrame:CGRectZero andTitle:#"myemail#gmail.com"];
[self.view addSubview:label];
Cheers..
Related
I'm creating custom UIView that contains two UILabels and UIButton so I created a subclass to make this possible.
Now the process looks like:
- (id)initWithFrame:(CGRect)frame {
self = [super initWithFrame:frame];
self.backgroundColor = [UIColor whiteColor];
self.settingsButton = [[UIButton alloc] initWithFrame:CGRectMake(frame.size.width - 2 * margin, frame.size.height - titleHeight - dateHeight, buttonSize, buttonSize)];
[self.settingsButton setImage:[UIImage imageNamed:#"settings_icon"] forState:UIControlStateNormal];
[self addSubview:self.settingsButton];
[self.settingsButton addTarget:self action:#selector(buttonTapped:) forControlEvents:UIControlEventTouchUpInside];
return self;
}
Button appears on UIView but it is not clickable. I tried to set self.userInteractionEnabled = YES; and a couple things but still no result :(
This is the most dumb mistake I've ever made. Transparent UINavigationBar was blocking the touch.
I want to create a bottom tab that could change the view when user press.
To do that I create a view with view controller and sets it's frame in the init
Here is the bottom panel view controller
#implementation BottomTabViewController
-(id) initWithFrame:(CGRect)frame{
if(self = [super init]){
self.view.frame = frame;
return self;
}else{
return nil;
}
}
- (void)viewDidLoad {
[super viewDidLoad];
[self setUpButtons];
// Do any additional setup after loading the view.
}
-(void) featureBtnClick:(id*) sender{
NSLog(#"featureBtn Clicked");
}
-(void) favBtnClick:(id*)sender{
NSLog(#"Fav Btn Clicked");
}
-(void) setUpButtons{
UIButton *features = [[UIButton alloc]initWithFrame:CGRectMake(10, 10, 50, 50)];
[features setBackgroundImage:[UIImage imageNamed:#"feature.png"] forState:UIControlStateNormal];
features.backgroundColor = [UIColor greenColor];
[features addTarget:self action:#selector(featureBtnClick:) forControlEvents:UIControlEventTouchUpInside];
[self.view addSubview:features];
UIButton *favBtn = [[UIButton alloc]initWithFrame:CGRectMake([[UIScreen mainScreen]bounds].size.width - 100, 10, 50, 50)];
[favBtn setBackgroundImage:[UIImage imageNamed:#"favorite.png"] forState:UIControlStateNormal];
[favBtn addTarget:self action:#selector(favBtnClick:) forControlEvents:UIControlEventTouchUpInside];
favBtn.backgroundColor = [UIColor greenColor];
[self.view addSubview:favBtn];
}
#end
And I added that to my view with code like this:
-(void) setUpBottom{
BottomTabViewController *botm = [[BottomTabViewController alloc]initWithFrame:CGRectMake(0, [[UIScreen mainScreen] bounds].size.height - 55, [[UIScreen mainScreen]bounds].size.width, 55)];
botm.view.backgroundColor = [UIColor redColor];
// botm.view.userInteractionEnabled = false;
botm.view.userInteractionEnabled = true;
[self.view addSubview:botm.view];
}
Here here is the result seems, note the bottom panel that works, well pretty silly, but it shows up:
But when press the left and right button, there is not log printed which it expected to be to indict that the button works, What have I done wrong? Thanks
you are adding buttons in the view first then adding the bottom view.
if this is what you are doing then it can be overlapped by the bottom view.
In this case buttons cant be tapped because they have bottom view on top of them.
so make sure u add bottom view first then your buttons. (or change their frames to avoid overlapping)
How to achieve the below design in iOS , is any controls available to achieve this. I am not that much experienced to achieve this design in native . Is it developed in native or kind of hybrid technology is used
Please find the below image for reference
I made a programmatic Example (Kind of "Hello World") for you
(it is programatic for a reason, that I believe it is easier to understand how things are working.
It is not perfect solution it can be done better, (performance wise) but I choose it as a simple example to get you started (Personally I would use CALayer for the backgrounds).
so here:
make a new class as follows:
MyView.h
#import <UIKit/UIKit.h>
#interface MyView : UIView
#end
MyView.m
#import "MyView.h"
#implementation MyView
- (instancetype)initWithFrame:(CGRect)frame
{
if(self = [super initWithFrame:frame])
{
self.backgroundColor = [UIColor grayColor];
//This rect is in self coordinate system
UIView * viewPurple = [[UIView alloc]initWithFrame:CGRectMake(0, 200, frame.size.width, 50)];
viewPurple.backgroundColor = [UIColor purpleColor];
[self addSubview:viewPurple];
//This rect is in viewPurple's coordinate system
UILabel * label = [[UILabel alloc]initWithFrame:CGRectMake(0, 0, frame.size.width/2, 50)];
[label setText:#"Hello World!"];
[label setTextAlignment:(NSTextAlignmentCenter)];
[label setTextColor:[UIColor whiteColor]];
[viewPurple addSubview:label];
//All the frame's rects are in it's `superView`/ parent 's coordinate system.
UIView * viewGreen = [[UIView alloc]initWithFrame:CGRectMake(frame.size.width/2, 200, frame.size.width, 50)];
viewGreen.backgroundColor = [UIColor cyanColor];
[self addSubview:viewGreen];
UILabel * label2 = [[UILabel alloc]initWithFrame:CGRectMake(0, 0, frame.size.width/2, 50)];
[label2 setText:#"World Hello!"];
[label2 setTextAlignment:(NSTextAlignmentCenter)];
[label2 setTextColor:[UIColor whiteColor]];
[viewGreen addSubview:label2];
}
else
{
//Can't allocate the UIView - quite a rare problem.
}
return self;
}
#end
#import "myView.h" in your view controller
and add this snippet to the - (void)viewDidLoad method.
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
MyView * view = [[MyView alloc]initWithFrame:self.view.frame];
[self.view addSubview:view];
}
the result will be as follow
In my app, I am using a UISegmentedcontrol. Because the label in each of the three segments spans two lines, I need to customize the UISegmentedcontrol. I want to do two things: (1) Increase the height of the UISegmentedcontrol, and (2) Make the text label span two lines
I found the solution to #1 here: iOS: change the height of UISegmentedcontrol and here Change Height of UISegmentedControl and here http://iphonedevsdk.com/forum/iphone-sdk-development/74275-change-height-of-segmented-control.html
I couldn't find out how to make the label inside the UISegmentedcontrol span two lines. Any help would be greatly appreciated!
Cheers,
Frank
try this...
create a Category for UISegmentedControl ,suppose UISegmentedControl+Multiline
in UISegmentedControl+Multiline.h
#import <UIKit/UIKit.h>
#interface UISegmentedControl (Multiline)
- (void)insertSegmentWithMultilineTitle:(NSString *)title atIndex:(NSUInteger)segment animated:(BOOL)animated;
#end
and in UISegmentedControl+Multiline.m
#import "UISegmentedControl+Multiline.h"
#interface UIView (LayerShot)
- (UIImage *)imageFromLayer;
#end
#implementation UIView (LayerShot)
- (UIImage *)imageFromLayer {
UIGraphicsBeginImageContextWithOptions(self.bounds.size, NO, 0);
[self.layer renderInContext:UIGraphicsGetCurrentContext()];
UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
return image;
}
#end
#implementation UISegmentedControl (Multiline)
- (void)insertSegmentWithMultilineTitle:(NSString *)title atIndex:(NSUInteger)segment animated:(BOOL)animated {
UILabel *label = [[UILabel alloc] initWithFrame:CGRectZero];
[label setTextColor:[self tintColor]];
[label setBackgroundColor:[UIColor clearColor]];
[label setFont:[UIFont systemFontOfSize:13]];
[label setTextAlignment:NSTextAlignmentCenter];
[label setLineBreakMode:NSLineBreakByWordWrapping];
[label setNumberOfLines:0];
[label setText:title];
[label sizeToFit];
[self insertSegmentWithImage:[label imageFromLayer] atIndex:segment animated:animated];
}
#end
finally import UISegmentedControl+Multiline.h in your class and use as follows
UISegmentedControl * segmentControl = [[UISegmentedControl alloc]initWithFrame:CGRectMake(3, 66, 314, 30)];
[segmentControl insertSegmentWithMultilineTitle:#"First\nLine" atIndex:0 animated:YES];
[segmentControl insertSegmentWithMultilineTitle:#"Second\nLine" atIndex:1 animated:YES];
[segmentControl insertSegmentWithMultilineTitle:#"Third\nLine" atIndex:2 animated:YES];
[segmentControl setSelectedSegmentIndex:0];
[segmentControl addTarget:self action:#selector(segmentControlClicked:) forControlEvents:UIControlEventValueChanged];
[self.view addSubview:segmentControl];
I want to draw a line between two UILabels when i tap or hold both of them at the same time with code, i have no idea how to do this, it will be most appreciated if anyone has an advice , it will be most appreciated
This is how I would do it. My answer is tested btw...
To manage the tappable labels I would create my own label called LabelControl that extends UIControl. This custom control is going to have a UILabel (read-only for simplicity) as a subview. By doing this we will be able to add the Target-Action events UIControlEventTouchDown and UIControlEventTouchUpInside.
Here is the custom label:
The .h file:
#interface LabelControl : UIControl
#property (nonatomic, retain, readonly) UILabel *theLabel;
#end
The .m file:
#implementation LabelControl
#synthesize theLabel = _theLabel;
- (id)initWithFrame:(CGRect)frame
{
self = [super initWithFrame:frame];
if (self) {
_theLabel = [[UILabel alloc] initWithFrame:CGRectMake(0, 0, frame.size.width, frame.size.height)];
_theLabel.backgroundColor = [UIColor clearColor];
_theLabel.userInteractionEnabled = NO;
[self addSubview:_theLabel];
}
return self;
}
-(void)dealloc {
[_theLabel release];
[super dealloc];
}
Then for the "line" that you want to draw, I would use a UIView because that way you could just use it's hidden property to hide/show the line. Add this code inside your ViewController:
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
self.label1 = [[[LabelControl alloc] initWithFrame:CGRectMake(60, 50, 200, 40)] autorelease];
self.label1.theLabel.text = #"Hello";
self.label1.userInteractionEnabled = YES;
self.label1.backgroundColor = [UIColor blueColor];
[self.label1 addTarget:self action:#selector(touchDown:) forControlEvents:UIControlEventTouchDown];
[self.label1 addTarget:self action:#selector(touchUp:) forControlEvents:UIControlEventTouchUpInside];
[self.view addSubview:self.label1];
self.label2 = [[[LabelControl alloc] initWithFrame:CGRectMake(60, 150, 200, 40)] autorelease];
self.label2.theLabel.text = #"World";
self.label2.userInteractionEnabled = YES;
self.label2.backgroundColor = [UIColor purpleColor];
[self.label2 addTarget:self action:#selector(touchDown:) forControlEvents:UIControlEventTouchDown];
[self.label2 addTarget:self action:#selector(touchUp:) forControlEvents:UIControlEventTouchUpInside];
[self.view addSubview:self.label2];
//the position of the line is hard-coded. You will have to modify this yourself
self.theLine = [[UIView alloc] initWithFrame:CGRectMake(60, 120, 200, 3)];
self.theLine.backgroundColor = [UIColor blueColor];
self.theLine.hidden = YES;
[self.view addSubview:self.theLine];
}
-(void)showOrHideLine {
if (self.label1.selected && self.label2.selected) {
NSLog(#"Both are selected");
self.theLine.hidden = NO;
} else {
self.theLine.hidden = YES;
}
}
-(void)touchDown:(id)sender {
//When any of the custom label gets the touch down event set the `selected` property
//to YES. (This property is inherited form `UIControl`
NSLog(#"Touch down");
LabelControl *labelControl = (LabelControl*)sender;
labelControl.selected = YES;
[self showOrHideLine];
}
-(void)touchUp:(id)sender {
//When any of the custom label gets the touch up event set the `selected` property
//to NO. (This property is inherited form `UIControl`
NSLog(#"Touch Up");
LabelControl *labelControl = (LabelControl*)sender;
labelControl.selected = NO;
[self showOrHideLine];
}
Let me know if you have any questions. Hope this helps!
I am going to outline it and give you some code (untested) but you have some work to make the full effect work.
Programtically, you could subclass UIButton. Inside your new subclass, put your touch recognition methods. Call it something like "customUIButton".
From your main view controller, create two instances of your UIButton and add them as subviews
customUIButton *Label1 = [[customUIButton alloc] init];
[Label1 setTitle:#"Your First Label" forState:UIControlStateNormal];
[Label1 addTarget:self action:#selector(itemClicked:) forControlEvents:UIControlEventTouchUpInside];
[self.view addSubview:Label1];
customUIButton *Label2 = [[customUIButton alloc] init];
[Label2 setTitle:#"Your Second Label" forState:UIControlStateNormal];
[Label2 addTarget:self action:#selector(itemClicked:) forControlEvents:UIControlEventTouchUpInside];
[self.view addSubview:Label1];
When you push the buttons, it will try to call the method "itemClicked". Make that method and receive (id)sender... - (void)itemClicked: (id)sender { Put some logic in there to indicate that the button is being pushed. You know which button by referring to the sender that was sent.
Also in your view controller, go to the DrawRect method and put in the drawing logic.
CGContextRef context = UIGraphicsGetCurrentContext();
CGContextSetLineWidth(context, 3.0);
CGContextSetStrokeColorWithColor(context, [UIColor blueColor].CGColor);
CGContextMoveToPoint(context, Label1.center.x, Label1.center.y);
CGContextAddLineToPoint(context, Label2.center.x, Label2.center.y);
CGContextStrokePath(context);
CGContextRestoreGState(context);
Put this in an "if statement" so that if both buttons have focus, it will be drawn (else skip the drawing code).
How about placing a line in IB using an Image View. Hide the Image View in your viewDidLoad method. Then, whenever the user taps one of the the UILabels, unhide the Image View holding your line. It may be tricky depending on your experience with Objective-C to detect touches on a UILabel. If it is, you can place invisible buttons over each label and that should do the trick for you. For more info about detecting touches on UILabels, check this link:
Handling Touch Event in UILabel and hooking it up to an IBAction