当我尝试过时如何设置可以使用swift输入到UITextField中的最大字符数?,我看到如果我全部使用10个字符,我也无法删除该字符。
我唯一能做的就是取消该操作(一起删除所有字符)。
有谁知道如何不阻塞键盘(这样我就不能添加其他字母/符号/数字,但是我可以使用退格键)?
当我尝试过时如何设置可以使用swift输入到UITextField中的最大字符数?,我看到如果我全部使用10个字符,我也无法删除该字符。
我唯一能做的就是取消该操作(一起删除所有字符)。
有谁知道如何不阻塞键盘(这样我就不能添加其他字母/符号/数字,但是我可以使用退格键)?
Answers:
对于Swift 5和iOS 12,请尝试以下协议实现textField(_:shouldChangeCharactersIn:replacementString:)
方法的实现UITextFieldDelegate
:
func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
guard let textFieldText = textField.text,
let rangeOfTextToReplace = Range(range, in: textFieldText) else {
return false
}
let substringToReplace = textFieldText[rangeOfTextToReplace]
let count = textFieldText.count - substringToReplace.count + string.count
return count <= 10
}
range
(NSRange
)到rangeOfTextToReplace
(Range<String.Index>
)的转换。观看此视频教程以了解为何此转换很重要。textField
的smartInsertDeleteType
值设置为UITextSmartInsertDeleteType.no
。这将防止在执行粘贴操作时可能会插入(多余的)多余空间。下面展示了如何实现完整的示例代码textField(_:shouldChangeCharactersIn:replacementString:)
中UIViewController
:
import UIKit
class ViewController: UIViewController, UITextFieldDelegate {
@IBOutlet var textField: UITextField! // Link this to a UITextField in Storyboard
override func viewDidLoad() {
super.viewDidLoad()
textField.smartInsertDeleteType = UITextSmartInsertDeleteType.no
textField.delegate = self
}
func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
guard let textFieldText = textField.text,
let rangeOfTextToReplace = Range(range, in: textFieldText) else {
return false
}
let substringToReplace = textFieldText[rangeOfTextToReplace]
let count = textFieldText.count - substringToReplace.count + string.count
return count <= 10
}
}
text.characters.count
已弃用text.count
我这样做是这样的:
func checkMaxLength(textField: UITextField!, maxLength: Int) {
if (countElements(textField.text!) > maxLength) {
textField.deleteBackward()
}
}
该代码对我有用。但是我使用情节提要。在情节提要中,我在编辑更改时为视图控制器中的文本字段添加了一个动作。
添加来自@Martin答案的更多详细信息
// linked your button here
@IBAction func mobileTFChanged(sender: AnyObject) {
checkMaxLength(sender as! UITextField, maxLength: 10)
}
// linked your button here
@IBAction func citizenTFChanged(sender: AnyObject) {
checkMaxLength(sender as! UITextField, maxLength: 13)
}
func checkMaxLength(textField: UITextField!, maxLength: Int) {
// swift 1.0
//if (count(textField.text!) > maxLength) {
// textField.deleteBackward()
//}
// swift 2.0
if (textField.text!.characters.count > maxLength) {
textField.deleteBackward()
}
}
在Swift 4中
文本字段最多10个字符,并允许删除(退格)
func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
if textField == userNameFTF{
let char = string.cString(using: String.Encoding.utf8)
let isBackSpace = strcmp(char, "\\b")
if isBackSpace == -92 {
return true
}
return textField.text!.count <= 9
}
return true
}
迅捷3
func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
let nsString = NSString(string: textField.text!)
let newText = nsString.replacingCharacters(in: range, with: string)
return newText.characters.count <= limitCount
}
您可以扩展UITextField并添加一个@IBInspectable
用于处理它的对象:
SWIFT 5
import UIKit
private var __maxLengths = [UITextField: Int]()
extension UITextField {
@IBInspectable var maxLength: Int {
get {
guard let l = __maxLengths[self] else {
return 150 // (global default-limit. or just, Int.max)
}
return l
}
set {
__maxLengths[self] = newValue
addTarget(self, action: #selector(fix), for: .editingChanged)
}
}
@objc func fix(textField: UITextField) {
if let t = textField.text {
textField.text = String(t.prefix(maxLength))
}
}
}
然后在属性检查器上定义它
您可以在swift 5或swift 4中使用 类似波纹管的图像
在视图ViewController中添加代码
class ViewController: UIViewController , UITextFieldDelegate {
@IBOutlet weak var txtName: UITextField!
var maxLen:Int = 8;
override func viewDidLoad() {
super.viewDidLoad()
txtName.delegate = self
}
func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
if(textField == txtName){
let currentText = textField.text! + string
return currentText.count <= maxLen
}
return true;
}
}
您可以从GitHub下载完整源代码表单: https : //github.com/enamul95/TextFieldMaxLen
谨防本文中提到的UITextField的撤消错误:设置UITextField的最大字符长度
这是您迅速解决的方法
if(range.length + range.location > count(textField.text)) {
return false;
}
Here is my version of code. Hope it helps!
func textField(textField: UITextField, shouldChangeCharactersInRange range: NSRange, replacementString string: String) -> Bool {
let invalidCharacters = NSCharacterSet(charactersInString: "0123456789").invertedSet
if let range = string.rangeOfCharacterFromSet(invalidCharacters, options: nil, range:Range<String.Index>(start: string.startIndex, end: string.endIndex))
{
return false
}
if (count(textField.text) > 10 && range.length == 0)
{
self.view.makeToast(message: "Amount entry is limited to ten digits", duration: 0.5, position: HRToastPositionCenter)
return false
}
else
{
}
return true
}
我一直在我的一个应用程序中使用此协议/扩展名,它更具可读性。我喜欢它如何识别退格键,并明确告诉您何时字符是退格键。
要考虑的一些事情:
1.无论采用哪种协议扩展,都需要指定字符数限制。通常,这将是您的ViewController,但是您可以将字符限制实现为计算属性,并返回其他内容,例如,对一个模型的字符限制。
2.您将需要在文本字段的shouldChangeCharactersInRange委托方法内调用此方法。否则,您将无法通过返回false等来阻止文本输入。
3.您可能希望允许使用退格字符。这就是为什么我添加了额外的功能来检测退格键的原因。您的shouldChangeCharacters方法可以进行检查并尽早返回“ true”,因此您始终允许退格。
protocol TextEntryCharacterLimited{
var characterLimit:Int { get }
}
extension TextEntryCharacterLimited{
func charactersInTextField(textField:UITextField, willNotExceedCharacterLimitWithReplacementString string:String, range:NSRange) -> Bool{
let startingLength = textField.text?.characters.count ?? 0
let lengthToAdd = string.characters.count
let lengthToReplace = range.length
let newLength = startingLength + lengthToAdd - lengthToReplace
return newLength <= characterLimit
}
func stringIsBackspaceWith(string:String, inRange range:NSRange) -> Bool{
if range.length == 1 && string.characters.count == 0 { return true }
return false
}
}
如果您有兴趣,我可以在Github仓库中使用一些字符限制行为并将其放入iOS框架中。您可以实施一种协议来获得类似Twitter的字符数限制显示,向您显示超出字符数限制的距离。
由于委托是一对一关系,由于其他原因,我可能想在其他地方使用它,因此我想限制文本字段的长度,在其设置中添加以下代码:
required init(coder aDecoder: NSCoder) {
super.init(coder: aDecoder)!
setup()
}
required override init(frame: CGRect) {
super.init(frame: frame)
setup()
}
func setup() {
// your setup...
setMaxLength()
}
let maxLength = 10
private func setMaxLength() {
addTarget(self, action: #selector(textfieldChanged(_:)), for: UIControlEvents.editingChanged)
}
@objc private func textfieldChanged(_ textField: UITextField) {
guard let text = text else { return }
let trimmed = text.characters.prefix(maxLength)
self.text = String(trimmed)
}
斯威夫特5
func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
let MAX_LENGTH = 4
let updatedString = (textField.text! as NSString).replacingCharacters(in: range, with: string)
return updatedString.count <= MAX_LENGTH
}
您需要检查现有字符串加上输入是否大于10。
func textField(textField: UITextField!,shouldChangeCharactersInRange range: NSRange, replacementString string: String!) -> Bool {
NSUInteger newLength = textField.text.length + string.length - range.length;
return !(newLength > 10)
}