Merging multiple localized left key paths in the same NSPredicateEditorRowTemplate?

300 views Asked by At

I'm attempting to replicate the Finder's NSPredicateEditor-based metadata search in an app.

I'd prefer to get the Finder's exact NSPredicateEditor for free, but unless anyone has a better answer for that question it looks like I'm going to have to replicate Finder's search as best as I can.

When working on mirroring the Kind option, I'm hitting a problem. I start by saving a Finder Spotlight search with all available Kind options.

Every <code>Kind</code> option in Finder search.

When I Get Info on the resulting saved search folder, the Query is listed as:

(kMDItemContentTypeTree=com.apple.application) && 
(kMDItemContentTypeTree=public.archive) && 
(kMDItemContentTypeTree = public.content) && 
(_kMDItemGroupId = 8) && 
(_kMDItemGroupId = 9) && 
(_kMDItemGroupId = 13) && 
(_kMDItemGroupId = 7) && 
(_kMDItemGroupId = 10) && 
(_kMDItemGroupId = 11) && 
(_kMDItemGroupId = 12) && 
(kMDItemContentTypeTree = public.text) && 
(kMDItemKind = "my_Kind_custom_text*"cdw)

The problem I'm seeing is that the single "Kind" user-displayed text contains multiple key paths that are used in the resulting NSPredicate based on whichever right value is picked.

"Kind" can represent (at least) kMDItemContentTypeTree, _kMDItemGroupId, or kMDItemKind.

When I create an NSPredicateEditorRowTemplate, I pass an array of Left Expressions, Operators, and Right Expressions. The row template is then created containing all possible permutations of Left/Operator/Right.

(Note: I'm creating all NSPredicateEditorRowTemplates programatically rather than in Interface Builder).

Finder is not creating all possible permutations of the 3 Left key paths and 12 Right values. It is selectively assigning a certain left key path based on the value picked on the right.

I am localizing the row templates using NSRuleEditor's formattingDictionary property, based on the guide found here: http://funwithobjc.tumblr.com/post/1482915398/localizing-nspredicateeditor

I can assign the same localization of "Kind" to two different key path expressions in two different NSPredicateEditorRowTemplates.

When I have two row templates localized to "Kind" using the same left key path expression, the following "merge the templates" quote is true and only one "Kind" shows up in the list. The right popup is a union set of all of the vaules from the two templates.

two row templates, single key path, same localization

At runtime, NSPredicateEditor will merge the templates together, and the second popup will show a union of all the operators of your date templates. http://www.cocoabuilder.com/archive/cocoa/282859-nspredicateeditorrowtemplate-and-dynamic-templateviews.html

However, when I create two row templates, both localized to "Kind", using different left key path expressions, I instead get two "Kind" rows in my left expression popup. The templates are not merged.

two row templates, two key paths, same localization

How should I replicate Finder's behavior? I need to somehow merge the left key paths if they have the same localization even if they represent different key paths / expressions, resulting in a single row template with multiple left key paths each with independent sets of right values.

1

There are 1 answers

0
pkamb On

My solution was to have a single source property, then multiple renamed getters that return that property.

Each kindImage-type getter is a key path that can be targeted independently in the predicate editor.

@objc lazy var kind: String = { return getKind() }()
@objc lazy var kindImage      = kind
@objc lazy var kindText       = kind
@objc lazy var kindDocument   = kind

Despite returning the same value, the predicate editor rows will not merge because they are using different key paths.