Nick Locking
Nick Locking

Reputation: 2141

NSPredicateEditorRowTemplate, specifying of Key Path with spaces?

As per a previous question, I have reluctantly given up on using IB/Xcode4 to edit an NSPredicateEditor and done it purely in code.

In the GUI way of editing the fields, key paths can be specified with spaces, like 'field name', and it makes them work as 'fieldName'-style key paths, while still displaying them in the UI with spaces. How do I do this in code? When I specify them with spaces, they don't work. When I specify them in camelCase, they work but display in camelCase. I'm just adding a bunch of NSExpressions like this:

[NSExpression expressionForKeyPath:@"original filename"]

Upvotes: 3

Views: 393

Answers (2)

user187676
user187676

Reputation:

If you don't want to localize everything, just map the key paths consider overriding value(forKey:) in your evaluated object like this:

class Match: NSObject {

    var date: Date?
    var fileName: String?

    override func value(forKey key: String) -> Any? {
        // Alternatively use static dictionary for mapping key paths
        super.value(forKey: camelCasedKeyPath(forKey: key))
    }

    private func camelCasedKeyPath(forKey key: String) -> String {
        key.components(separatedBy: .whitespaces)
            .enumerated()
            .map { $0.offset > 0 ? $0.element.capitalized : $0.element.lowercased() }
            .joined()
    }
}

Upvotes: 0

Dave DeLong
Dave DeLong

Reputation: 243156

The proper way to get human readable strings in the predicate editor's row views is to use the localization capabilities of NSRuleEditor and NSPredicateEditor.

If you follow the instructions in this blog post, you'll have everything you need to localize the editor.

As an example, let's say your key path is fileName, you support 2 operators (is and contains), and you want the user to enter a string. You'll end up with a strings file that looks like this:

"%[fileName]@ %[is]@ %@" = "%1$[fileName]@ %2$[is]@ %3$@";
"%[fileName]@ %[contains]@ %@" = "%1$[fileName]@ %2$[contains]@ %3$@";

You can use this file to put in human-readable stuff, and even reorder things:

"%[fileName]@ %[is]@ %@" = "%1$[original filename]@ %2$[is]@ %3$@";
"%[fileName]@ %[contains]@ %@" = "%3$@ %2$[is contained in]@ %1$[original filename]@";

Once you've localized the strings file, you hand that file back to the predicate editor, and it'll pull out the translated values, do its magic, and everything will show up correctly.

Upvotes: 3

Related Questions