使用绑定和格式化程序驯服NSTextField以正确运行
我想要一个窗口,需要接受一些用户输入,为此我有以下几点:
NSWindow
使用NSWindowController
从nib加载,也是它的代表 NSTextField
与NSNumberFormatter
NSTextField
绑定到NSWindowController
的整数属性(为简单起见,我没有使用NSObjectController
,但可以根据需要添加它) NSButton
windowShouldClose:
方法中做一个最终验证并决定我是否可以关闭窗口 我想实现的非常简单,但Cocoa坚持要做到这一点具有挑战性:
NSTextField
应该只接受一个数字作为它的最终值,它也大于零 够简单。 NSNumberFormatter应该已经覆盖了大部分任务,并且与绑定一起,这应该很容易实现。
问题#1:
当NSTextField
失去焦点并且该值对于更具描述性的内容不正确时,我无法找到更改在警报中显示给用户的错误消息的方法。 有没有办法做到这一点? 或者我需要以某种方式实现自己的NSFormatter?
问题2:
当用户更改NSTextField
的值并单击“完成”按钮时,Cocoa不认为这是更新NSTextField
绑定的模型的值的触发器。 这可能是标准的OSX行为,但是没有任何意义。
我可以通过在'done'按钮的操作中调用[window makeFirstResponder:nil]
来解决这个问题,以强制NSTextField
失去焦点并更新值,但我想知道这是否是实现这个目标的正确方法。
问题3:
而这正是我真正挠挠我的地方。 如果用户在NSTextField
输入了不正确的值(如非整数)并单击“完成”按钮,验证不会启动,并且NSTextField
将在模型未更新时继续具有不正确的值。
我期望“无效”警报仍然会显示,我有一些地方可以插入代码来决定是否关闭窗口,但我找不到任何方法来覆盖此行为。
实现这些要求的标准做法应该是什么? 我是否应该放弃格式化程序和/或绑定,并仅使用操作手动完成所有操作?
对于问题1,请尝试设置文本字段的委托并实现-control:didFailToFormatString:errorDescription:
和可能的-control:didFailToValidatePartialString:errorDescription:
出示你想要的任何用户界面,使用错误描述或不使用。
或者,您可以实现NSNumberFormatter
的自定义子类并覆盖-getObjectValue:forString:errorDescription:
和-isPartialStringValid:proposedSelectedRange:originalString:originalSelectedRange:errorDescription:
你可以通过超级调用来实现大部分的实现。 如果失败,则可以替换super提供的错误描述。 如果您需要格式化程序对象(其属性等)的上下文来找出更好的错误描述,则可以使用此方法。
问题2的正确解决方案是不以编程方式更改第一响应者。 相反,你应该确实使用NSObjectController
在文本字段和窗口控制器之间进行调解。 在完成按钮的操作方法中,调用-commitEditing
或-commitEditingWithDelegate:didCommitSelector:contextInfo:
NSObjectController
从NSController
继承这些方法, NSController
采用NSEditor
协议。 当你得到结果时(前者异步,后者异步),则根据提交是成功还是失败,继续执行或不执行任何操作。
我怀疑问题3也是以编程方式更改窗口的第一响应者的结果。 通常情况下,程序变更不会受到与用户操作相应的更改相同的检查。 例如,框架假定你,程序员知道你在做什么,所以将格式化程序的焦点更改转换为验证将是“错误的”。
链接地址: http://www.djcxy.com/p/14929.html上一篇: Taming NSTextField with bindings and formatter to behave properly