我想将边框仅保留在UITextField
的底部。
但我不知道如何将它保持在最低端。
你可以告诉我吗?
答案 0 :(得分:287)
最终,我找到了另一种方法,它更简单方便。但唯一的条件是UITextField
必须包含自动布局。
我在这里使用视觉格式语言(VFL),这将允许向任何UIControl
添加一行。
帮助方法:
您可以将此辅助方法添加到全局帮助程序类(我使用全局类方法)或在同一视图控制器中(使用实例方法)。
typedef enum : NSUInteger {
LINE_POSITION_TOP,
LINE_POSITION_BOTTOM
} LINE_POSITION;
- (void) addLineToView:(UIView *)view atPosition:(LINE_POSITION)position withColor:(UIColor *)color lineWitdh:(CGFloat)width {
// Add line
UIView *lineView = [[UIView alloc] init];
[lineView setBackgroundColor:color];
[lineView setTranslatesAutoresizingMaskIntoConstraints:NO];
[view addSubview:lineView];
NSDictionary *metrics = @{@"width" : [NSNumber numberWithFloat:width]};
NSDictionary *views = @{@"lineView" : lineView};
[view addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"H:|[lineView]|" options: 0 metrics:metrics views:views]];
switch (position) {
case LINE_POSITION_TOP:
[view addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"V:|-0-[lineView(width)]" options: 0 metrics:metrics views:views]];
break;
case LINE_POSITION_BOTTOM:
[view addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"V:[lineView(width)]|" options: 0 metrics:metrics views:views]];
break;
default: break;
}
}
<强>用法:强>
[self addLineToView:self.textField atPosition:LINE_POSITION_TOP withColor:[UIColor darkGrayColor] lineWitdh:0.5];
使用Swift:
帮助方法:
enum LINE_POSITION {
case LINE_POSITION_TOP
case LINE_POSITION_BOTTOM
}
func addLineToView(view : UIView, position : LINE_POSITION, color: UIColor, width: Double) {
let lineView = UIView()
lineView.backgroundColor = color
lineView.translatesAutoresizingMaskIntoConstraints = false // This is important!
view.addSubview(lineView)
let metrics = ["width" : NSNumber(value: width)]
let views = ["lineView" : lineView]
view.addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "H:|[lineView]|", options:NSLayoutFormatOptions(rawValue: 0), metrics:metrics, views:views))
switch position {
case .LINE_POSITION_TOP:
view.addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "V:|[lineView(width)]", options:NSLayoutFormatOptions(rawValue: 0), metrics:metrics, views:views))
break
case .LINE_POSITION_BOTTOM:
view.addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "V:[lineView(width)]|", options:NSLayoutFormatOptions(rawValue: 0), metrics:metrics, views:views))
break
default:
break
}
}
<强>用法:强>
self.addLineToView(view: textField, position:.LINE_POSITION_BOTTOM, color: UIColor.darkGray, width: 0.5)
如果以编程方式创建UITextField
对象,此答案将完美无缺。
注意:如果在Storyboard中创建了UITextField
对象,则在Storyboard Attributes Inspector中将其Border Style
属性设置为None
。
以下变量textField
是UITextField
控件的对象,其中将设置底部边框。
Swift代码:
let border = CALayer()
let width = CGFloat(2.0)
border.borderColor = UIColor.darkGray.cgColor
border.frame = CGRect(x: 0, y: textField.frame.size.height - width, width: textField.frame.size.width, height: textField.frame.size.height)
border.borderWidth = width
textField.layer.addSublayer(border)
textField.layer.masksToBounds = true
目标C代码:
CALayer *border = [CALayer layer];
CGFloat borderWidth = 2;
border.borderColor = [UIColor darkGrayColor].CGColor;
border.frame = CGRectMake(0, textField.frame.size.height - borderWidth, textField.frame.size.width, textField.frame.size.height);
border.borderWidth = borderWidth;
[textField.layer addSublayer:border];
textField.layer.masksToBounds = YES;
Xamarin代码:
var border = new CALayer();
nfloat width = 2;
border.BorderColor = UIColor.Black.CGColor;
border.Frame = new CoreGraphics.CGRect(0, textField.Frame.Size.Height - width, textField.Frame.Size.Width, textField.Frame.Size.Height);
border.BorderWidth = width;
textField.Layer.AddSublayer(border);
textField.Layer.MasksToBounds = true;
许多用户遇到自动布局的问题,有些人无法呈现UITextField的边框。这是解决方案:
如果您在viewDidLoad()
方法下面写下代码,那么您将无法获得textField的框架,因此该边框将无法正确呈现。
要获取边框的正确框架,请覆盖viewDidLayoutSubviews()
并在其中编写代码。
viewDidLayoutSubviews()
方法。
不要忘记这个方法被多次调用,并且它不是ViewController生命周期的一部分,所以在使用它时要小心。
答案 1 :(得分:141)
如果你想事先做不知道框架,没有子类化和没有Autolayout :
Swift 4.x / Swift 3.x
extension UITextField {
func setBottomBorder() {
self.borderStyle = .none
self.layer.backgroundColor = UIColor.white.cgColor
self.layer.masksToBounds = false
self.layer.shadowColor = UIColor.gray.cgColor
self.layer.shadowOffset = CGSize(width: 0.0, height: 1.0)
self.layer.shadowOpacity = 1.0
self.layer.shadowRadius = 0.0
}
}
从任何地方呼叫yourTextField.setBottomBorder()
,而不确定帧是否正确。
结果如下所示:
答案 2 :(得分:40)
您可以创建UITextField
的子类,如下所示:
class TextField : UITextField {
override var tintColor: UIColor! {
didSet {
setNeedsDisplay()
}
}
override func draw(_ rect: CGRect) {
let startingPoint = CGPoint(x: rect.minX, y: rect.maxY)
let endingPoint = CGPoint(x: rect.maxX, y: rect.maxY)
let path = UIBezierPath()
path.move(to: startingPoint)
path.addLine(to: endingPoint)
path.lineWidth = 2.0
tintColor.setStroke()
path.stroke()
}
}
答案 3 :(得分:22)
这些解决方案都没有达到我的期望。我想继承 TextField,因为我不想一直手动设置边框。我还想更改边框颜色,例如为了一个错误。所以这是我的Anchors
解决方案:
class CustomTextField: UITextField {
var bottomBorder = UIView()
override func awakeFromNib() {
// Setup Bottom-Border
self.translatesAutoresizingMaskIntoConstraints = false
bottomBorder = UIView.init(frame: CGRect(x: 0, y: 0, width: 0, height: 0))
bottomBorder.backgroundColor = UIColor(rgb: 0xE2DCD1) // Set Border-Color
bottomBorder.translatesAutoresizingMaskIntoConstraints = false
addSubview(bottomBorder)
bottomBorder.bottomAnchor.constraint(equalTo: bottomAnchor).isActive = true
bottomBorder.leftAnchor.constraint(equalTo: leftAnchor).isActive = true
bottomBorder.rightAnchor.constraint(equalTo: rightAnchor).isActive = true
bottomBorder.heightAnchor.constraint(equalToConstant: 1).isActive = true // Set Border-Strength
}
}
----可选----
要像这样更改颜色添加到CustomTextField Class
:
@IBInspectable var hasError: Bool = false {
didSet {
if (hasError) {
bottomBorder.backgroundColor = UIColor.red
} else {
bottomBorder.backgroundColor = UIColor(rgb: 0xE2DCD1)
}
}
}
在创建CustomTextField实例
后触发错误调用textField.hasError = !textField.hasError
希望它可以帮到某人;)
答案 4 :(得分:21)
extension UITextField {
func setBottomBorder(color:String) {
self.borderStyle = UITextBorderStyle.None
let border = CALayer()
let width = CGFloat(1.0)
border.borderColor = UIColor(hexString: color)!.cgColor
border.frame = CGRect(x: 0, y: self.frame.size.height - width, width: self.frame.size.width, height: self.frame.size.height)
border.borderWidth = width
self.layer.addSublayer(border)
self.layer.masksToBounds = true
}
}
然后就这样做:
yourTextField.setBottomBorder(color: "#3EFE46")
答案 5 :(得分:11)
您可以在类外创建此扩展,并将宽度替换为您想要的任何borderWidth。
Swift 4
extension UITextField
{
func setBottomBorder(withColor color: UIColor)
{
self.borderStyle = UITextBorderStyle.none
self.backgroundColor = UIColor.clear
let width: CGFloat = 1.0
let borderLine = UIView(frame: CGRect(x: 0, y: self.frame.height - width, width: self.frame.width, height: width))
borderLine.backgroundColor = color
self.addSubview(borderLine)
}
}
<强>原始强>
extension UITextField
{
func setBottomBorder(borderColor: UIColor)
{
self.borderStyle = UITextBorderStyle.None
self.backgroundColor = UIColor.clearColor()
let width = 1.0
let borderLine = UIView(frame: CGRectMake(0, self.frame.height - width, self.frame.width, width))
borderLine.backgroundColor = borderColor
self.addSubview(borderLine)
}
}
然后将其添加到viewDidLoad中,用您的UITextField变量替换yourTextField,并在边框中使用您想要的任何颜色
yourTextField.setBottomBorder(UIColor.blackColor())
这基本上会在文本字段的底部添加一个带有该颜色的视图。
答案 6 :(得分:10)
目标C
[txt.layer setBackgroundColor: [[UIColor whiteColor] CGColor]];
[txt.layer setBorderColor: [[UIColor grayColor] CGColor]];
[txt.layer setBorderWidth: 0.0];
[txt.layer setCornerRadius:12.0f];
[txt.layer setMasksToBounds:NO];
[txt.layer setShadowRadius:2.0f];
txt.layer.shadowColor = [[UIColor blackColor] CGColor];
txt.layer.shadowOffset = CGSizeMake(1.0f, 1.0f);
txt.layer.shadowOpacity = 1.0f;
txt.layer.shadowRadius = 1.0f;
<强>夫特强>
txt.layer.backgroundColor = UIColor.white.cgColor
txt.layer.borderColor = UIColor.gray.cgColor
txt.layer.borderWidth = 0.0
txt.layer.cornerRadius = 5
txt.layer.masksToBounds = false
txt.layer.shadowRadius = 2.0
txt.layer.shadowColor = UIColor.black.cgColor
txt.layer.shadowOffset = CGSize.init(width: 1.0, height: 1.0)
txt.layer.shadowOpacity = 1.0
txt.layer.shadowRadius = 1.0
答案 7 :(得分:6)
我所做的是为UITextField创建扩展并添加Designer可编辑属性。将此属性设置为任何颜色会将边框(底部)更改为该颜色(将其他边框设置为无)。
由于这也需要更改占位符文本颜色,我还将其添加到扩展名。
extension UITextField {
@IBInspectable var placeHolderColor: UIColor? {
get {
return self.placeHolderColor
}
set {
self.attributedPlaceholder = NSAttributedString(string:self.placeholder != nil ? self.placeholder! : "", attributes:[NSForegroundColorAttributeName: newValue!])
}
}
@IBInspectable var bottomBorderColor: UIColor? {
get {
return self.bottomBorderColor
}
set {
self.borderStyle = UITextBorderStyle.None;
let border = CALayer()
let width = CGFloat(0.5)
border.borderColor = newValue?.CGColor
border.frame = CGRect(x: 0, y: self.frame.size.height - width, width: self.frame.size.width, height: self.frame.size.height)
border.borderWidth = width
self.layer.addSublayer(border)
self.layer.masksToBounds = true
}
}
}
答案 8 :(得分:6)
在Swift上3.您可以创建一个扩展名并在视图类之后添加。
extension UITextField
{
func setBottomBorder(borderColor: UIColor)
{
self.borderStyle = UITextBorderStyle.none
self.backgroundColor = UIColor.clear
let width = 1.0
let borderLine = UIView()
borderLine.frame = CGRect(x: 0, y: Double(self.frame.height) - width, width: Double(self.frame.width), height: width)
borderLine.backgroundColor = borderColor
self.addSubview(borderLine)
}
}
答案 9 :(得分:6)
请查看下面的代码示例;
快捷键4:
@IBDesignable class DesignableUITextField: UITextField {
let border = CALayer()
@IBInspectable var borderColor: UIColor? {
didSet {
setup()
}
}
@IBInspectable var borderWidth: CGFloat = 0.5 {
didSet {
setup()
}
}
func setup() {
border.borderColor = self.borderColor?.cgColor
border.borderWidth = borderWidth
self.layer.addSublayer(border)
self.layer.masksToBounds = true
}
override func layoutSubviews() {
super.layoutSubviews()
border.frame = CGRect(x: 0, y: self.frame.size.height - borderWidth, width: self.frame.size.width, height: self.frame.size.height)
}
}
答案 10 :(得分:3)
这是带有@IBInspectable的swift3代码
创建一个新文件Cocoa Touch Class Swift File
import UIKit
extension UIView {
@IBInspectable var cornerRadius: CGFloat {
get {
return layer.cornerRadius
}
set {
layer.cornerRadius = newValue
layer.masksToBounds = newValue > 0
}
}
@IBInspectable var borderWidth: CGFloat {
get {
return layer.borderWidth
}
set {
layer.borderWidth = newValue
}
}
@IBInspectable var borderColor: UIColor? {
get {
return UIColor(cgColor: layer.borderColor!)
}
set {
layer.borderColor = newValue?.cgColor
}
}
@IBInspectable var leftBorderWidth: CGFloat {
get {
return 0.0 // Just to satisfy property
}
set {
let line = UIView(frame: CGRect(x: 0.0, y: 0.0, width: newValue, height: bounds.height))
line.translatesAutoresizingMaskIntoConstraints = false
line.backgroundColor = UIColor(cgColor: layer.borderColor!)
line.tag = 110
self.addSubview(line)
let views = ["line": line]
let metrics = ["lineWidth": newValue]
addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "|[line(==lineWidth)]", options: [], metrics: metrics, views: views))
addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "V:|[line]|", options: [], metrics: nil, views: views))
}
}
@IBInspectable var topBorderWidth: CGFloat {
get {
return 0.0 // Just to satisfy property
}
set {
let line = UIView(frame: CGRect(x: 0.0, y: 0.0, width: bounds.width, height: newValue))
line.translatesAutoresizingMaskIntoConstraints = false
line.backgroundColor = borderColor
line.tag = 110
self.addSubview(line)
let views = ["line": line]
let metrics = ["lineWidth": newValue]
addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "|[line]|", options: [], metrics: nil, views: views))
addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "V:|[line(==lineWidth)]", options: [], metrics: metrics, views: views))
}
}
@IBInspectable var rightBorderWidth: CGFloat {
get {
return 0.0 // Just to satisfy property
}
set {
let line = UIView(frame: CGRect(x: bounds.width, y: 0.0, width: newValue, height: bounds.height))
line.translatesAutoresizingMaskIntoConstraints = false
line.backgroundColor = borderColor
line.tag = 110
self.addSubview(line)
let views = ["line": line]
let metrics = ["lineWidth": newValue]
addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "[line(==lineWidth)]|", options: [], metrics: metrics, views: views))
addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "V:|[line]|", options: [], metrics: nil, views: views))
}
}
@IBInspectable var bottomBorderWidth: CGFloat {
get {
return 0.0 // Just to satisfy property
}
set {
let line = UIView(frame: CGRect(x: 0.0, y: bounds.height, width: bounds.width, height: newValue))
line.translatesAutoresizingMaskIntoConstraints = false
line.backgroundColor = borderColor
line.tag = 110
self.addSubview(line)
let views = ["line": line]
let metrics = ["lineWidth": newValue]
addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "|[line]|", options: [], metrics: nil, views: views))
addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "V:[line(==lineWidth)]|", options: [], metrics: metrics, views: views))
}
}
func removeborder() {
for view in self.subviews {
if view.tag == 110 {
view.removeFromSuperview()
}
}
}
}
并使用以下代码替换该文件,您将在storyboard属性检查器中获得此选项
享受:)
答案 11 :(得分:1)
**这里myTF是MT TEXT FIELD **的出口
let border = CALayer()
let width = CGFloat(2.0)
border.borderColor = UIColor.darkGray.cgColor
border.frame = CGRect(x: 0, y: self.myTF.frame.size.height - width, width: self.myTF.frame.size.width, height: self.myTF.frame.size.height)
border.borderWidth = width
self.myTF.layer.addSublayer(border)
self.myTF.layer.masksToBounds = true
答案 12 :(得分:1)
迅速5 您可以使用UIView扩展,以便可以在任何视图中添加底边框:
extension UIView {
func addBottomLine(width: CGFloat, color: UIColor) {
let lineView: UIView = {
let view = UIView()
view.translatesAutoresizingMaskIntoConstraints = false
view.backgroundColor = color
return view
}()
addSubview(lineView)
NSLayoutConstraint.activate([
lineView.heightAnchor.constraint(equalToConstant: width),
lineView.leadingAnchor.constraint(equalTo: leadingAnchor),
lineView.trailingAnchor.constraint(equalTo: trailingAnchor),
lineView.bottomAnchor.constraint(equalTo: bottomAnchor)
])
}
}
答案 13 :(得分:0)
您可以为底部边框创建一个图像并将其设置为UITextField的背景:
yourTextField.backgroundColor = [UIColor colorWithPatternImage:[UIImage imageNamed:@"yourBorderedImageName"]];
或将borderStyle设置为none,并将行的图像长度设置为textfield!
答案 14 :(得分:0)
查看:(最推荐)
它使用UIView
UIView extension
子类(视图,文本文件,标签等)。
它更加简单方便。但是唯一的条件是view
必须包含自动布局。
extension UIView {
enum Line_Position {
case top
case bottom
}
func addLine(position : Line_Position, color: UIColor, height: Double) {
let lineView = UIView()
lineView.backgroundColor = color
lineView.translatesAutoresizingMaskIntoConstraints = false // This is important!
self.addSubview(lineView)
let metrics = ["width" : NSNumber(value: height)]
let views = ["lineView" : lineView]
self.addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "H:|[lineView]|", options:NSLayoutConstraint.FormatOptions(rawValue: 0), metrics:metrics, views:views))
switch position {
case .top:
self.addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "V:|[lineView(width)]", options:NSLayoutConstraint.FormatOptions(rawValue: 0), metrics:metrics, views:views))
break
case .bottom:
self.addConstraints(NSLayoutConstraint.constraints(withVisualFormat: "V:[lineView(width)]|", options:NSLayoutConstraint.FormatOptions(rawValue: 0), metrics:metrics, views:views))
break
}
}
}
如何使用?
// UILabel
self.lblDescription.addLine(position: .bottom, color: UIColor.blue, height: 1.0)
// UITextField
self.txtArea.addLine(position: .bottom, color: UIColor.red, height: 1.0)
答案 15 :(得分:0)
更新的代码:
Swift 5.0
extension UITextField {
func addUnderline() {
let layer = CALayer()
layer.backgroundColor = #colorLiteral(red: 0.6666666865, green: 0.6666666865, blue: 0.6666666865, alpha: 1)
layer.frame = CGRect(x: 0.0, y: self.frame.size.height - 1.0, width: self.frame.size.width, height: 1.0)
self.clipsToBounds = true
self.layer.addSublayer(layer)
self.setNeedsDisplay()} }
现在在 viewDidLayoutSubviews()
中调用此函数override func viewDidLayoutSubviews() {
textField.addUnderline()
}
注意::该方法仅适用于 viewDidLayoutSubviews()
答案 16 :(得分:0)
我研究了似乎也可以解决一个问题的每种解决方案。深色模式和背景设置
UITextField的Background设置必须与父视图的背景匹配,否则将不显示任何行
所以这将适用于灯光模式 要在黑暗模式下工作,请将背景颜色更改为黑色,即可使用 排除背景色,线条不出现
let field = UITextField()
field.backgroundColor = UIColor.white
field.bottomBorderColor = UIColor.red
这最终成为我的最佳解决方案
extension UITextField {
func addPadding() {
let paddingView = UIView(frame: CGRect(x:0, y:0, width: 10, height: self.frame.height))
self.leftView = paddingView
self.leftViewMode = .always
}
@IBInspectable var placeHolderColor: UIColor? {
get {
return self.placeHolderColor
}
set {
self.attributedPlaceholder = NSAttributedString(string:self.placeholder != nil ? self.placeholder! : "", attributes:[NSAttributedString.Key.foregroundColor: newValue!])
}
}
@IBInspectable var bottomBorderColor: UIColor? {
get {
return self.bottomBorderColor
}
set {
self.borderStyle = .none
self.layer.masksToBounds = false
self.layer.shadowColor = newValue?.cgColor
self.layer.shadowOffset = CGSize(width: 0.0, height: 1.0)
self.layer.shadowOpacity = 1.0
self.layer.shadowRadius = 0.0
}
}
}
答案 17 :(得分:0)
在SwiftUI中,有一个Divider
与此完美匹配的VStack
。您可以通过将其嵌入到简单的VStack {
Text("This could be any View")
Divider()
}
中来将其添加到任何视图下面:
mvnw
答案 18 :(得分:0)
在SwiftUI中,最简单的实现是
struct MyTextField: View {
var myPlaceHolder: String
@Binding var text: String
var underColor: Color
var height: CGFloat
var body: some View {
VStack {
TextField(self.myPlaceHolder, text: $text)
.padding(.horizontal, 24)
.font(.title)
Rectangle().frame(height: self.height)
.padding(.horizontal, 24).foregroundColor(self.underColor)
}
}
}
用法:
MyTextField(myPlaceHolder: "PlaceHolder", text: self.$text, underColor: .red, height: 3)
答案 19 :(得分:-1)
import UIkit
extension UITextField
{
func underlinedLogin()
{
let border = CALayer()
let width = CGFloat(1.0)
border.borderColor = UIColor.black.cgColor
border.frame = CGRect(x: 0, y: self.frame.size.height - width, width: self.frame.size.width, height: self.frame.size.height)
border.borderWidth = width
self.layer.addSublayer(border)
self.layer.masksToBounds = true
}
}
在viewdidload上调用方法
mobileNumberTextField.underlinedLogin()
passwordTextField.underlinedLogin()
//选择mainstoryboard上的文本字段
答案 20 :(得分:-1)
您可以使用 ORGANIZED ,还可以自定义此扩展程序:
&#34; 一线实施&#34;在 viewDidAppear 中(以便框架大小正确):
// Add layer in your textfield
yourTextField.addLayer(.bottom).addPadding(.left)
// Extension
extension UITextField {
enum Position {
case up, bottom, right, left
}
// MARK: - Add Single Line Layer
func addLayer(_ position: Position) -> UITextField {
// bottom layer
let bottomLayer = CALayer()
// set width
let height = CGFloat(1.0)
bottomLayer.borderWidth = height
// set color
bottomLayer.borderColor = UIColor.white.cgColor
// set frame
// y position changes according to the position
let yOrigin = position == .up ? 0.0 : frame.size.height - height
bottomLayer.frame = CGRect.init(x: 0, y: yOrigin, width: frame.size.width, height: height)
layer.addSublayer(bottomLayer)
layer.masksToBounds = true
return self
}
// Add right/left padding view in textfield
func addPadding(_ position: Position, withImage image: UIImage? = nil) {
let paddingHeight = frame.size.height
let paddingViewFrame = CGRect.init(x: 0.0, y: 0.0, width: paddingHeight * 0.6, height: paddingHeight)
let paddingImageView = UIImageView.init(frame: paddingViewFrame)
paddingImageView.contentMode = .scaleAspectFit
if let paddingImage = image {
paddingImageView.image = paddingImage
}
// Add Left/Right view mode
switch position {
case .left:
leftView = paddingImageView
leftViewMode = .always
case .right:
rightView = paddingImageView
rightViewMode = .always
default:
break
}
}
}