更改UIDatePicker字体颜色?

46

我想做的只是改变UIDatePicker的字体颜色。我研究了其他问题,但它们都涉及到更改其他属性和自定义整个外观。我只想把字体颜色从黑色改成白色。我觉得很难相信我不能完成这样一个看似简单的任务。为什么tint color不起作用呢?它甚至有用吗?


在上面的问题中,我找到了我的解决方案。 - MarMass
17个回答

90

在iOS 8.x和9.0上,我所需要的就是这一行代码来改变字体颜色:

        [my_date_picker setValue:[UIColor whiteColor] forKey:@"textColor"];

禁止子类化或调用私有API...


注意:在较新的iOS版本中,当天的当前日期仍将被突出显示。您可以通过使用以下代码来避免此问题:

if ([my_date_picker respondsToSelector:sel_registerName("setHighlightsToday:")]) {

#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Wundeclared-selector"

        [my_date_picker performSelector:@selector(setHighlightsToday:) withObject:[NSNumber numberWithBool:NO]];

#pragma clang diagnostic pop

}

8
我尝试了,但今天日期的部分颜色错了,10和十月是黑色的,年份颜色不对我倒无所谓,但其他两个感觉很奇怪。 - vshade
1
@vshade,你有代码片段发布在某个地方吗?很高兴看一下...对我来说仍然有效... - waffles
3
这将把所有文字都变为白色,除了当前日期(例如2015年8月2日的日期将保留为黑色)。 - rizzes
4
对于当前日期,[my_date_picker performSelector:@selector(setHighlightsToday:) withObject:NO]; 的意思是取消日期选择器中今天日期的高亮显示。 - Nike Kov
1
setHighlightsToday在iOS 14上已不再可用。 - Declan McKenna
显示剩余7条评论

25

除了@Jeremiah的回答之外,还有另一种选择,就是在界面构建器(Interface Builder)中定义这些值。

我更喜欢使用这种方式,因为不需要在您的ViewController中添加任何代码。

点击进入您的DatePicker视图,并像屏幕截图中所示从属性检查器中自定义它。 screenshot

适用于Swift 2、3、4和可能适用于Swift < 2。(未经测试)


1
不幸的是,这只会给“Today”这个单词上色...其他什么都没有。如果你关闭了highlightsToday,textColor就没有效果了。这是在Xcode 11中发生的。 - Oscar
在Xcode 14.2中,高亮显示(highlightsToday)没有效果,但文本颜色(textColor)有效。谢谢! - undefined

24

截至Swift 2.1版本:

picker.setValue(UIColor.whiteColor(), forKey: "textColor")
picker.sendAction("setHighlightsToday:", to: nil, forEvent: nil)
let date = NSDate()
picker.setDate(date, animated: false)

您将看到当前日期而不是“今天”。


2
setHighlightsToday causes a warning, No method declared with Objective-C selector 'setHighlightsToday:' - Daniel Storm
2
Swift 3: picker.setValue(UIColor.white, forKey: "textColor") picker.sendAction(Selector(("setHighlightsToday:")), to: nil, for: nil) Swift 3:picker.setValue(UIColor.white,forKey:“textColor”) picker.sendAction(Selector((“setHighlightsToday:”)),to:nil,for:nil) - david72
在 Xcode12/Swift 5.3 中,…Selector(("setHighlightsToday:"))… 需要删除 : 以变为 …Selector(("setHighlightsToday"))…,否则会导致运行时崩溃。 - l --marc l

20

下一个解决方案来自于“arturgrigor”,在我的应用程序中它表现得非常棒,只需复制粘贴到viewDidLoad方法中,然后享受它:

[my_datePicker setValue:[UIColor whiteColor] forKeyPath:@"textColor"];
SEL selector = NSSelectorFromString( @"setHighlightsToday:" );
NSInvocation *invocation = [NSInvocation invocationWithMethodSignature :
                           [UIDatePicker 
                            instanceMethodSignatureForSelector:selector]];
BOOL no = NO;
[invocation setSelector:selector];
[invocation setArgument:&no atIndex:2];
[invocation invokeWithTarget:my_datePicker];

改变字体怎么样? - androniennn
1
你应该小心处理这个问题。这会调用苹果的私有API,苹果可能因此拒绝你的应用! - Saren Inden
@SarenInden,我的应用程序Acces-o和Acces-o School都在使用它,不用担心! - Jose Manuel Abarca Rodríguez

9

谢谢Michael。我查看了MWDatePicker,但看起来它还没有更新到iOS 7。当我运行示例项目时,它只是一个空白选择器。我已经决定通过自定义UIPicker来模拟UIDatePicker。感谢您的帮助。仍然非常惊讶苹果不允许自定义日期选择器。我想知道为什么? - Milo
我看到有一个pull request正在更新MWDatePicker以适应iOS 7。如果所有者合并它会很好,但至少你可以获取它并加以利用。 - Michael Dautermann

6

我偶然发现了一种惊人的干净解决方案,使用UIAppearance,而不使用任何KVC、swizzling或其他私有API。我发现尝试通过UIAppearance设置UIDatePicker中任何UILabeltextColor没有影响,但一个简单调用常规textColor设置器的自定义外观属性完全可以。

// Implement a custom appearance property via a UILabel category
@interface UILabel (PickerLabelTextColor)

@property (nonatomic, strong) UIColor * textColorWorkaround UI_APPEARANCE_SELECTOR;

@end

@implementation UILabel (PickerLabelTextColor)

- (UIColor *)textColorWorkaround {
    return self.textColor;
}

- (void)setTextColorWorkaround:(UIColor *)textColor {
    self.textColor = textColor;
}

@end

然后按如下方式使用:

UILabel *pickerLabelProxy = [UILabel appearanceWhenContainedInInstancesOfClasses:@[UIDatePicker.class]];
pickerLabelProxy.textColorWorkaround = UIColor.lightGrayColor;

Swift版本

UILabel扩展:

extension UILabel {
    @objc dynamic var textColorWorkaround: UIColor? {
        get {
            return textColor
        }
        set {
            textColor = newValue
        }
    }
}

外观代理使用:

let pickerLabelProxy = UILabel.appearance(whenContainedInInstancesOf: [UIDatePicker.self])
pickerLabelProxy.textColorWorkaround = UIColor.lightGray

你能提供一个 Swift 版本的解决方案吗? - keegan3d
@keegan3d 已添加!它可以编译并且在功能上应该是等效的,但我最近没有使用过这种策略。如果它仍然有效,请告诉我们! - gyratory circus
我现在正在iOS 16.5.1上尝试,当组件首次出现时,它的效果非常好,但是当改变高亮数字并切换到另一个数字时,之前高亮的数字会恢复为白色,同样的情况也发生在同时滑动屏幕或滚动轮子时。 - clearlight
它在2023年8月仍然有效。 - Carl Smith

6

要更改UIDatePicker文本颜色,请使用:

    // MARK: - Helping content 

    private enum DatePickerProperties: String {
        case TextColor = "textColor"
        case HighlightsToday = "highlightsToday"
    }

    // MARK: - Outlets

    @IBOutlet private weak var datePicker: UIDatePicker!

    // MARK: - Lifecicle

    public override func awakeFromNib() {
        super.awakeFromNib()

        self.datePicker.setValue(UIColor.whiteColor(), forKey: DatePickerProperties.TextColor.rawValue)
        self.datePicker.setValue(false, forKey: DatePickerProperties.HighlightsToday.rawValue)
    }

在 xCode 7.3 和 Swift 2.3 上运行得非常好。


4
如果有人需要一个快速的解决方案,我将以下代码放在viewDidLoad中:
    birthdayDatePicker.setValue(DesignHelper.getOffWhiteColor(), forKey: "textColor")
    birthdayDatePicker.performSelector("setHighlightsToday:", withObject:DesignHelper.getOffWhiteColor())

太好了!有没有Swift < 2的解决方案?在1.2中performSelector不可用。 - Dima Deplov
1
有没有办法在Xcode 7.3中消除警告 - 没有使用Objective-C选择器"setHighlightsToday:"声明的方法? - user2643679
我还没有找到一个方法。我已经确认它是可行的并且仍然需要。如果有人有一种不会弹出警告的解决方案,那就太棒了! - Jeremiah
要抑制警告,请查看此解决方案https://dev59.com/pnVC5IYBdhLWcg3wvT_g - Fraser

4

对于Xamarin开发者:

DatePicker.SetValueForKey(UIColor.White, new NSString("textColor"));
DatePicker.SetValueForKey(FromObject(false), new NSString("highlightsToday"));

它的工作效果非常好。在iOS 9和10上进行了测试。


3

如果你想在InterFace Builder中进行配置,你也可以将其添加为IBDesignable。

    import UIKit

@IBDesignable
extension UIDatePicker {
    @IBInspectable var textLabelColor: UIColor? {
        get {
            return self.valueForKey("textColor") as? UIColor
        }
        set {
            self.setValue(newValue, forKey: "textColor")
            self.performSelector("setHighlightsToday:", withObject:newValue) //For some reason this line makes the highlighted text appear the same color but can not be changed from textColor. 
        }
    }
}

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