我该如何更改UISearchBar的搜索文本颜色?

100

我如何改变 UISearchBar 的文本颜色?

25个回答

118

您需要访问UISearchBar内部的UITextField。 您可以使用valueForKey("searchField")来实现。

var textFieldInsideSearchBar = yourSearchbar.valueForKey("searchField") as? UITextField

textFieldInsideSearchBar?.textColor = yourcolor

Swift 3更新

let textFieldInsideSearchBar = yourSearchbar.value(forKey: "searchField") as? UITextField

textFieldInsideSearchBar?.textColor = yourcolor

1
我已经修改了我的回答。你可以通过使用 valueForkey("searchField") 来访问该字段。 - Christian
7
这不是私有 API,但非常脆弱,可能在任何 iOS 更新时发生故障。你不应该在生产代码中使用这样的东西。 - Lope
3
@Christian - 原始答案发布时间并不重要,它仍然依赖于私有API。如果它是公共的,你就不需要通过KVC访问searchField - Greg Brown
2
Downvote。请查看@juanjo的答案和我的评论,这是一种更加健壮的方法,已经获得了苹果的批准,并且不太可能出现故障。 - RobP
2
不要使用此答案,您正在访问私有 API,这可能会导致您的应用被拒绝。 - aryaxt
显示剩余6条评论

76

如果您想在Storyboard中为UISearchBar设置文本颜色(无需编码),也很容易做到(在Identity Inspector中)。这是一个搜索栏的红色文本。

输入图像描述


3
最好对视图元素的代码量更少。谢谢。 - NRR
完美的解决方案! - Mona

60
如果您只需要使其在黑色背景上可读,您可以更改barStyle。以下代码可将搜索栏中的文本和按钮变为白色:
searchController.searchBar.barStyle = .black

@Bacon,这也有帮助!谢谢。 - Goppinath

57

对我来说,使用Swift 4很顺畅:

UITextField.appearance(whenContainedInInstancesOf: [UISearchBar.self]).defaultTextAttributes = [NSAttributedStringKey.foregroundColor.rawValue: UIColor.white]

Swift 4.2,IOS 12:

UITextField.appearance(whenContainedInInstancesOf: [UISearchBar.self]).defaultTextAttributes = [NSAttributedString.Key.foregroundColor: UIColor.white]

适用于我。 - Surjeet Rajput
它会为模块中的每个搜索栏更改颜色吗? - Zaporozhchenko Oleksandr

32
public extension UISearchBar {

    public func setTextColor(color: UIColor) {
        let svs = subviews.flatMap { $0.subviews }
        guard let tf = (svs.filter { $0 is UITextField }).first as? UITextField else { return }
        tf.textColor = color
    }
}

喜欢你的解决方案。谢谢。 - Bagusflyer
您也可以添加“searchField.backgroundColor”来控制文本字段的背景颜色,与导航栏色调分开控制。 - Sherwin Zadeh

14

这对于我在iOS 11和Xcode 9上运行有效:

UITextField.appearance(whenContainedInInstancesOf: [UISearchBar.self]).textColor = UIColor.blue

我把它写在AppDelegate中,但我想如果你把它放在其他地方也可以运行。


3
这种方法比被接受答案和其他答案中的键-值无用信息更为强大。但是,苹果公司很明智地废弃了您在此处使用的API,并提供了一个新版本,适用于iOS 9.0及以上版本,如下所示: [[UITextField appearanceWhenContainedInInstancesOfClasses:@[[UISearchBar class]]] setTextColor:[UIColor blueColor]]; 当然,这是Objective-C,可以使用 appearance(whenContainedInInstancesOf:) 进行明显的Swift翻译。 - RobP
2
在 Xcode 10、iOS 12 上,实际设备上似乎对我不起作用。 - Oded
@RobP 这是基于假设在 UISearchBar 内部有一个 UITextField 的相同黑客。但是,与其将丑陋的本地化放在使用的地方,不如将其全部泼洒在整个项目中。 - Zapko

11

我认为最方便的方法是在UISearchBar中设置textColor属性。

Swift 3.0

    extension UISearchBar {

       var textColor:UIColor? {
           get {
               if let textField = self.value(forKey: "searchField") as? 
   UITextField  {
                   return textField.textColor
               } else {
                   return nil
               }
           }

           set (newValue) {
               if let textField = self.value(forKey: "searchField") as? 
   UITextField  {
                   textField.textColor = newValue
               }
           }
       }
   }

使用方法

searchBar.textColor = UIColor.blue // Your color

Swift 2.3

extension UISearchBar {

 var textColor:UIColor? {
     get {
         if let textField = self.valueForKey("searchField") as? UITextField  {
             return textField.textColor
         } else {
             return nil
         }
     }

     set (newValue) {
         if let textField = self.valueForKey("searchField") as? UITextField  {
             textField.textColor = newValue
         }
     }
 }
} 

你可以这样使用它:

searchBar.textColor = UIColor.blueColor() // Your color

对我没用。你什么时候设置textcolor属性? - Kingalione
1
@Kingalione,你可以在 'viewDidLoad()' 中设置这个。 - Tal Zion
是的,我想要改变占位符文本的颜色。现在我找到了解决方案。无论如何还是谢谢。 - Kingalione

11

自从 Xcode 11 和 iOS 13 推出以来,直接访问文本字段已成为可能:

searchBar.searchTextField

您可以编写一些代码,始终使其像这样易于访问。

extension UISearchBar {
    public var textField: UITextField? {
        if #available(iOS 13.0, *) {
            return searchTextField
        } 

        guard let firstSubview = subviews.first else {
            assertionFailure("Could not find text field")
            return nil
        }

        for view in firstSubview.subviews {
            if let textView = view as? UITextField {
                return textView
            }
        }

        assertionFailure("Could not find text field")

        return nil
    }
}

你也可以使用致命错误让它变得不可选,这段代码从iOS 7测试到iOS 13GM都是可行的。但我建议仍然采用可选版本。


extension UISearchBar {
    public var textField: UITextField {
        if #available(iOS 13.0, *) {
            return searchTextField
        }

        guard let firstSubview = subviews.first else {
            fatalError("Could not find text field")
        }

        for view in firstSubview.subviews {
            if let textView = view as? UITextField {
                return textView
            }
        }

       fatalError("Could not find text field")
    }
}

终于!我们可以直接访问文本字段了。谢谢,Saren。 - Mark Moeykens

6

试一下这个:

searchBar.searchTextField.textColor = .white

我正在使用这个应用程序,针对的是 iOS 11 及以上版本。
[更新] 我发现,在老版本( < iOS 13)上应用程序会崩溃,但编译器从未抱怨过版本检查,希望有人能解释一下为什么会出现这种情况。

1
我的编译器报错了。 - FrugalResolution

4

我尝试了上面写的几种解决方案,但它们没有起作用(我猜可能是因为已经过时了)。

如果你只想处理iOS 13:

mySearchBar.searchTextField.textColor = .red

但是如果你也想处理旧版的iOS,这是我所做的方法:

创建一个自定义的UISearchBar类,称为SearchBar: UISearchBar, UISearchBarDelegate。这个SearchBar将具有我想要处理的UISearchBarDelegate方法和它的delegate设置。

然后我添加到这个类中:

    var textField: UITextField? {
        if #available(iOS 13.0, *) {
            return self.searchTextField
        }
        return subviews.first?.subviews.first(where: { $0 as? UITextField != nil }) as? UITextField
    }

简要说明:

现在使用 iOS13 可以通过 UISearchBar.searchTextField 来访问 UITextField,它是一个类型为 UISearchTextField 的子类,而 UISearchTextField 继承自 UITextField

由于我知道我的层次结构,我知道旧版本中我的 textField 不会为空,所以在两种情况下,我都可以获得一个可以轻松自定义的文本字段,在今天从 9 到 13 的每个版本上都可以工作。

以下为使其正常工作所需的完整代码:


class SearchBar: UISearchBar, UISearchBarDelegate {

    var textField: UITextField? {
        if #available(iOS 13.0, *) {
            return self.searchTextField
        }
        return subviews.first?.subviews.first(where: { $0 as? UITextField != nil }) as? UITextField
    }


    override func awakeFromNib() {
        super.awakeFromNib()

        delegate = self

        if let textField = textField {
            textField.textColor = .red
            textField.clearButtonMode = .whileEditing
            textField.returnKeyType = .search
        }
    }

}

您还可以通过在以下位置添加以下信息来对SearchBar进行一些自定义设置:

        let searchBar = UISearchBar.appearance(whenContainedInInstancesOf: [SearchBar.self])
        searchBar.backgroundImage = UIImage()
        searchBar.isTranslucent = false
        searchBar.returnKeyType = .search

然后您将其设置为XIB /故事板,并像处理简单的UISearchBar一样处理它(如果您没有忘记委托!)。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接