How to Add label to uibutton in Swift? - ios

I want to achieve that look of my button as shown? The right side of button which contains arrow (>) needs to be a simple label with that text. How can i do that? Is there anyway? I have checked many possibilities like taking a UIView and then adding button and labels inside it. I wanna know is that the only solution or there exist any other good one. Thanks.

Do you use Masonry or SnapKit ? Try this:
let label = UILabel()
label.text = ">"
button.addSubview(label)
label.snp.makeConstraints {
$0.right.equalToSuperview()
$0.centerY.equalToSuperview()
}

Related

Custom title view as large title in iOS 11 new navigation bar

I am using a button as a title view for my UITableViewController which opens a dropdown list of categories. Selecting a category filters content of the table view by the selected category.
The button shows the name of the selected category plus a small arrow, similar to how iBooks used to look (or maybe still looks? I haven't used it in a while). I would therefore like it to have the same behaviour as a standard title and have it be large at first and collapse when the table view is scrolled.
Is there a way to do this?
Thanks
It seems because of the new large titles, IOS11 requires the constraints on the custom view in the navigationItem.titleView to be set.
Do this for example:
customView.widthAnchor.constraint(equalToConstant: 200).isActive = true
customView.heightAnchor.constraint(equalToConstant: 44).isActive = true
self.navigationItem.titleView = customView
Note this must be done for both width and height.
It should work. No need to add a button, at least in my case...
This was suggested by Apple to ensure that you don't have zero-size custom views. See slide 33 in https://developer.apple.com/videos/play/wwdc2017/204/
Looks like touches are broken for navigationItem.titleView. Gestures, tap events and buttons - nothing works
Seems like a bug in iOS 11: https://forums.developer.apple.com/thread/82466
I provisionally implemented this workaround:
private lazy var navBarActionButtonIOS11: UIButton = {
button.addTarget(self.navTitleView, action: #selector(self.navTitleView.didTapView), for: .touchUpInside)
return button
}()
[...]
navigationItem.titleView = navTitleView
if #available(iOS 11.0, *), let navBar = navigationController?.navigationBar {
navBarActionButtonIOS11.removeFromSuperview()
navBar.addSubview(navBarActionButtonIOS11)
navBarActionButtonIOS11.center.x = navBar.center.x
}
Another solution could be to just assign a UIButton to navigationItem.titleView directly.
I hope Apple fixes this soon!
Well, I had same problem. I have UIButtons in UINavigationItem.titleView and those were not reacting to touches at all. Problem is that the view where those buttons are where of size (0,0) because of auto layout. So to fix this problem you need to add additional view into your custom view, lets call it "contentView" and put all your controls inside that contentView. Also, contentView must have defined size with constraints. Quick test is to add width and height constraint to contentView. And all works again.
Hope that this helps someone.

Customize Text Field

Hi I want to build some thing that look like the picture !
my problem is that text field can't be two section and use tiny pictures in it just like a picture
I want to make some thing just like the picture even the green part in the right of the each text field
here is what I want to do
Make a custom view and add it as
textField.rightViewMode = .always
// Set rightview mode
var rightImageView = UIImageView(image: UIImage(named: "image_icon"))
textField.rightView = rightImageView// Set right view as image view }
//textField Its your textfield object , Change it with your own
Try like this

Change color of UILabel if UITextField (in corresponding UIView) is disabled? (Swift)

I have multiple inputs that are disabled/enabled based on certain conditions — is there a way to select the adjacent UILabel that is in the same view?
Here's a visual the UITextField/UILabel:
You can find any views in a view with a simple loop.
for view in view.subviews {
if let label = view as? UILabel {
// do something with your view
}
}
Use viewWithTag option ,give specific tag to textField and fetch them
if let theTextField = self.view.viewWithTag(1) as? UITextField {
print(theTextField.text)
}
I don't think there is a direct way of identifying the adjacent label for a field. You'd have to loop through the labels looking for one in the correct position.
Instead give your text fields tags 1-10, and give your labels corresponding tags 101-110.
Then use the tag number to find the label.

Newline before auto-shrunken UIButton text

Background
I am creating an application, and inside of its storyboard I have a UIButton element. I need the text of this UIButton to auto-shrink, since it scales based on the size of the view. In storyboard, it has the following properties:
Inside of my code, it says:
guard button.titleLabel != nil else {
throw AutoshrinkError.noTitleLabel(button: button)
}
button.titleLabel!.adjustsFontSizeToFitWidth = true
button.titleLabel!.numberOfLines = 0
button.titleLabel!.lineBreakMode = NSLineBreakMode.byTruncatingTail
button.titleLabel!.baselineAdjustment = UIBaselineAdjustment.alignBaselines
I know that the guard statement passes (i.e. the code below it gets run).
The Problem
The problem is that with the above setup, my button ends up looking like this:
With a newline before the text.
I have tried editing my code in many ways, including setting button.titleLabel!.numberOfLines to 1, setting button.titleLabel!.lineBreakMode to NSLineBreakMode.byClipping, or removing the line about button.titleLabel!.baselineAdjustment. None of these changes have helped the situation. Instead they wind up causing more problems, such as the text not shrinking at all.
If anybody knows how to prevent this newline-scenario from happening, I would appreciate an answer.
Thanks in advance!
Edit 1
The constraints of the UIButton are:
woodgrain is a UIImageView that is used as a background image.
I figured it out! All I had to do was add this one simple line:
button.titleLabel!.baselineAdjustment = UIBaselineAdjustment.alignCenters
I got the idea to adjust the baselineAdjustment from this answer by #rintaro.
Now my UIButton looks like this:

Update segmented control in ios without change interface

when I update segmented control text, the interface (segment's width) changed and cut some letters.
[segmentedcontoll setTitle:#"test" forSegmentAtIndex:1];
segmentedcontoll.apportionsSegmentWidthsByContent = YES;
How can I solve this ?
EDIT:
It looks like your content has outgrown the dimensions of the standard UISegmentedControl.
If you are okay with smaller font, it's possible to set the entire control to have a smaller font point size, seen here.
Another option is to configure the segments the other supported way.. With images. It's a little bit of a hack, but you can create images on the fly with the UIView Snapshotting API of views/labels configured however you want and set images for each segment instead of using text. This would allow you to create 2 line labels with fixed widths and set images for each section to be images generated from the label as the content changes. More work, but you would still be using the standard class.
The last option, which might work the best for you, is to create some other custom control that does what you would like. After all, UISegmentedControl really is just a nice button container. And it does somewhat seem like you are using the control in a non-standard way - both as a control and an input form section.
Others have gone this route before and created alternatives that you can use.
You can create a separate class as below,
class CustomSegmentedControl: UISegmentedControl {
//code for creating multi line
override func didMoveToSuperview()
{
for segment in subviews
{
for subview in segment.subviews
{
if let segmentLabel = subview as? UILabel
{
segmentLabel.numberOfLines = 0 //just change here the number of lines and check it.
}
}
}
}
}
and create an outlet in your viewcontroller as,
// Initialize
let items = ["Purple", "Green", "New Segment"]
let customSC = CustomSegmentedControl(items: items)
use customSC and do what ever you want to do, similar to segmentedControl object.

Resources