From 628c5e40844aa54baff93cfb5cafd5d2b473458a Mon Sep 17 00:00:00 2001 From: Bibiko Date: Wed, 30 Sep 2009 20:22:21 +0000 Subject: =?UTF-8?q?=E2=80=A2=20further=20progress=20on=20the=20Content=20F?= =?UTF-8?q?ilter=20Editor=20=E2=80=A2=20fixed=20issue=20for=20"Add"=20a=20?= =?UTF-8?q?new=20favorite=20in=20SPQueryFavoriteManager:=20-=20save=20pend?= =?UTF-8?q?ing=20changes=20in=20the=20query=20textView=20in=20beforehand?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- Interfaces/English.lproj/ContentFilterManager.xib | 1259 +++++++++++++-------- Resources/English.lproj/ContentFilters.plist | 18 +- Source/SPContentFilterManager.h | 47 +- Source/SPContentFilterManager.m | 486 ++++---- Source/SPQueryFavoriteManager.m | 3 + Source/SPTableView.m | 4 + Source/TableContent.h | 3 + Source/TableContent.m | 60 +- 8 files changed, 1142 insertions(+), 738 deletions(-) diff --git a/Interfaces/English.lproj/ContentFilterManager.xib b/Interfaces/English.lproj/ContentFilterManager.xib index 2014d3e4..c5922b3b 100644 --- a/Interfaces/English.lproj/ContentFilterManager.xib +++ b/Interfaces/English.lproj/ContentFilterManager.xib @@ -21,6 +21,7 @@ YES + YES @@ -39,7 +40,7 @@ YES - SPQueryFavoriteManager + SPContentFilterManager FirstResponder @@ -67,7 +68,6 @@ 10 {{0, 358}, {500, 5}} - {0, 0} 67239424 @@ -117,7 +117,6 @@ 292 {{-1, -1}, {32, 25}} - YES 67239424 @@ -142,7 +141,6 @@ 292 {{30, -1}, {32, 25}} - YES 67239424 @@ -167,7 +165,6 @@ 292 {{61, -1}, {32, 24}} - YES 71433792 @@ -233,7 +230,7 @@ - Export Selected Favorites… + Export Selected Filters… 2147483647 @@ -244,7 +241,7 @@ YES - Import Favorites by Replacing… + Import Filter by Replacing… 1048576 2147483647 @@ -255,53 +252,7 @@ - Import Favorites… - - 2147483647 - - - _popUpItemAction: - - - - - YES - YES - - - 2147483647 - - - _popUpItemAction: - - - - - Save Query to File... - - 2147483647 - - - _popUpItemAction: - - - - - YES - YES - YES - - - 2147483647 - - - _popUpItemAction: - - - - - YES - Remove All... + Import Filters… 2147483647 @@ -320,7 +271,6 @@ {249, 23} - YES YES NO @@ -341,14 +291,12 @@ 4352 {249, 322} - YES 4352 {249, 17} - @@ -356,19 +304,18 @@ -2147483392 {{-22, 0}, {12, 17}} - YES - name - 186 + MenuLabel + 246 40 1000 75628096 2048 - Favorites + Content Filters LucidaGrande 11 @@ -378,7 +325,7 @@ 3 MC4zMzMzMzI5OQA - + 6 System headerTextColor @@ -415,37 +362,6 @@ YES - - tabtrigger - 57 - 10 - 3.4028229999999999e+38 - - 75628096 - 2048 - - - - 6 - System - headerColor - - - - - - 337772096 - 133120 - Text Cell - - - - - - 3 - YES - - 3 2 @@ -468,11 +384,11 @@ 16 - 1245741056 + 1245708288 - SPQueryFavoriteManagerTable - 1 + SPContentFilterManagerTable + 5 15 0 YES @@ -482,7 +398,6 @@ {{0, 17}, {249, 322}} - @@ -493,7 +408,6 @@ -2147483392 {{158, 17}, {11, 322}} - 256 _doScroller: @@ -505,7 +419,6 @@ -2147483392 {{-100, -100}, {311, 15}} - 1 _doScroller: @@ -520,7 +433,6 @@ {249, 17} - @@ -530,7 +442,6 @@ {{0, 22}, {249, 339}} - 528 @@ -543,7 +454,6 @@ {249, 361} - NSView @@ -551,12 +461,229 @@ 274 YES + + + -2147483358 + {{17, 125}, {216, 14}} + + YES + + 68288064 + 4326400 + + + + + 6 + System + controlColor + + + + + + + + 34 + {{0, 56}, {250, 5}} + + {0, 0} + + 67239424 + 0 + Box + + + + 3 + MCAwLjgwMDAwMDAxMTkAA + + + 3 + 2 + 0 + NO + + + + -2147483358 + {{28, 67}, {205, 55}} + + YES + + 67239424 + 4325632 + Multiline Label + + + + + + + + + -2147483382 + {{82, 306}, {151, 14}} + + YES + + 68288064 + 71435264 + Label + + + + + + + + + 292 + {{20, 181}, {124, 25}} + + YES + + 608304704 + 133120 + + + -2035138305 + 164 + + + 400 + 75 + + + YES + Insert Placeholder + + 2147483647 + + + _popUpItemAction: + + + YES + + OtherViews + + YES + + + + Argument + + 1048576 + 2147483647 + 1 + + + _popUpItemAction: + + + + + Quoted Argument + + 2147483647 + + + _popUpItemAction: + + + + + Current Field + + 1048576 + 2147483647 + + + _popUpItemAction: + + + + + BINARY + + 1048576 + 2147483647 + + + _popUpItemAction: + + + + + + 4 + YES + 1 + YES + YES + 1 + + + + + -2147483360 + {{17, 165}, {104, 14}} + + YES + + 68288064 + 272761856 + Conjunction Label: + + + + + + + + + -2147483356 + {{20, 144}, {124, 19}} + + YES + + -1804468671 + 272761856 + + + + YES + + + 6 + System + textColor + + + + + + + 268 + {{17, 306}, {55, 14}} + + YES + + 68288064 + 272761856 + Clause: + + + + + + 268 {{17, 330}, {45, 14}} - YES 68288064 @@ -564,12 +691,7 @@ Name: - - 6 - System - controlColor - - + @@ -578,7 +700,6 @@ 266 {{56, 328}, {174, 19}} - YES -1804468671 @@ -589,12 +710,7 @@ YES - - 6 - System - textColor - - + @@ -620,7 +736,6 @@ Apple PNG pasteboard type Apple URL pasteboard type CorePasteboardFlavorType 0x6D6F6F76 - CorePasteboardFlavorType 0x75726C20 NSColor pasteboard type NSFilenamesPboardType NSStringPboardType @@ -636,7 +751,6 @@ {208, 14} - @@ -705,13 +819,12 @@ 6 {592, 1e+07} - {180, 0} + {177, 0} - {{1, 1}, {208, 264}} + {{1, 1}, {208, 98}} - @@ -726,7 +839,6 @@ -2147483392 {{-100, -100}, {11, 133}} - 256 _doScroller: @@ -737,7 +849,6 @@ -2147483392 {{-100, -100}, {87, 18}} - 1 _doScroller: @@ -745,9 +856,8 @@ 0.94565220000000005 - {{20, 54}, {210, 266}} + {{20, 204}, {210, 100}} - 514 @@ -759,7 +869,6 @@ 289 {{130, 16}, {100, 25}} - 1 YES @@ -786,7 +895,6 @@ 289 {{20, 16}, {100, 25}} - YES 67239424 @@ -805,16 +913,14 @@ {{250, 0}, {250, 361}} - NSView {500, 361} - YES 2 - SPQueryFavoriteSplitView + SPContentFilterSplitView 1 MC42NjY2NjY2NjY3IDAuNjY2NjY2NjY2NyAwLjY2NjY2NjY2NjcAA @@ -834,11 +940,8 @@ - YES - - - YES - + + YES @@ -872,7 +975,6 @@ {500, 371} - {{0, 0}, {1680, 1028}} {500, 393} @@ -902,32 +1004,14 @@ - - - YES - YES - - - 2147483647 - - - - - - Save to File... - - 2147483647 - - - YES - name - query - tabtrigger + Clause + MenuLabel + ConjunctionLabel YES @@ -941,316 +1025,319 @@ YES - window - - + delegate + + - 133 + 187 - favoriteNameTextField - - + delegate + + - 139 + 188 - favoriteQueryTextView - - + delegate + + - 140 + 198 - favoritesTableView - - - - 141 - - - - addQueryFavorite: + removeButton - + - 180 + 275 - - removeQueryFavorite: - - + + value: selection.Clause + + + + + + value: selection.Clause + value + selection.Clause + 2 + - 181 + 300 - - closeQueryManagerSheet: - - + + font: values.CustomQueryEditorFont + + + + + + font: values.CustomQueryEditorFont + font + values.CustomQueryEditorFont + + NSValueTransformerName + NSUnarchiveFromData + + 2 + - 184 + 306 - - nextKeyView + + value: selection.MenuLabel - + + + + + value: selection.MenuLabel + value + selection.MenuLabel + 2 + - 185 + 308 - nextKeyView - - + window + + - 186 + 310 - - delegate - - + + closeContentFilterManagerSheet: + + - 187 + 311 - - delegate - - + + closeContentFilterManagerSheet: + + - 188 + 312 - - delegate - - + + addContentFilter: + + - 193 + 313 - - scrollView - - + + removeContentFilter: + + - 197 + 314 - delegate - - + contentFilterTableView + + - 198 + 316 - menu - - - - 209 - - - - removeQueryFavorite: + contentFilterConjunctionTextField - + - 211 + 323 - - saveFavoriteToFile: - - + + dataSource + + - 249 + 324 - - saveFavoriteToFile: - - + + delegate + + - 250 + 325 - removeAllQueryFavorites: - - + duplicateContentFilter: + + - 251 + 326 - exportFavorites: - + exportContentFilter: + - 257 + 327 - importFavoritesByAdding: - + importContentFilterByAdding: + - 261 + 328 - importFavoritesByReplacing: - - + removeContentFilter: + + - 262 + 329 - closeQueryManagerSheet: - - + duplicateContentFilter: + + - 273 + 330 - dataSource + menu - + - 274 + 331 - removeButton + contentFilterNameTextField - + - 275 + 332 - nextKeyView - - - - 277 - - - - duplicateQueryFavorite: + contentFilterTextView - - - 282 - - - - duplicateQueryFavorite: - - + - 283 + 333 - value: selection.name - + value: arrangedObjects.MenuLabel + - + - value: selection.name + value: arrangedObjects.MenuLabel value - selection.name + arrangedObjects.MenuLabel 2 - 287 + 335 + + + + contentFilterArrayController + + + + 336 - value: selection.query - + value: selection.ConjunctionLabel + - + - value: selection.query + value: selection.ConjunctionLabel value - selection.query + selection.ConjunctionLabel 2 - 291 + 338 - favoritesArrayController + contentFilterConjunctionLabel - + - 297 + 339 - - value: arrangedObjects.name - - - - - - value: arrangedObjects.name - value - arrangedObjects.name - - NSCreatesSortDescriptor - - - 2 - + + numberOfArgsLabel + + + + 354 + + + + insertPlaceholder: + + + + 356 + + + + resultingClauseContentLabel + + + + 363 + + + + resultingClauseLabel + + - 298 + 364 - - value: arrangedObjects.tabtrigger - - - - - - value: arrangedObjects.tabtrigger - value - arrangedObjects.tabtrigger - - YES - - YES - NSConditionallySetsEditable - NSCreatesSortDescriptor - - - YES - - - - - 2 - + + insertPlaceholderButton + + + + 365 + + + + nextKeyView + + - 299 + 366 @@ -1317,8 +1404,6 @@ YES - - Favorite Context Menu @@ -1333,16 +1418,6 @@ - - 247 - - - - - 248 - - - 278 @@ -1359,10 +1434,18 @@ YES - - + + + + + + + + + + @@ -1439,14 +1522,10 @@ YES - - - - @@ -1456,21 +1535,11 @@ - - 243 - - - 255 - - 259 - - - 258 @@ -1486,16 +1555,6 @@ - - 246 - - - - - 244 - - - 241 @@ -1533,20 +1592,10 @@ YES - - - 263 - - - YES - - - - 26 @@ -1561,11 +1610,6 @@ - - 264 - - - 121 @@ -1654,6 +1698,151 @@ Favorites Controller + + 303 + + + YES + + + + + + 304 + + + + + 319 + + + YES + + + + + + 320 + + + + + 321 + + + YES + + + + + + 322 + + + + + 340 + + + YES + + + + + + 341 + + + YES + + + + + + 342 + + + YES + + + + + + + + + + 343 + + + + + 344 + + + + + 345 + + + + + 350 + + + YES + + + + + + 351 + + + + + 352 + + + YES + + + + + + 353 + + + + + 357 + + + + + 358 + + + + + 360 + + + + + 361 + + + YES + + + + + + 362 + + + @@ -1706,13 +1895,6 @@ 240.IBEditorWindowLastContentRect 240.IBPluginDependency 241.IBPluginDependency - 243.IBAttributePlaceholdersKey - 243.IBPluginDependency - 244.IBPluginDependency - 246.IBAttributePlaceholdersKey - 246.IBPluginDependency - 247.IBPluginDependency - 248.IBPluginDependency 25.IBPluginDependency 25.IBShouldRemoveOnLegacySave 252.IBPluginDependency @@ -1721,13 +1903,10 @@ 255.IBAttributePlaceholdersKey 255.IBPluginDependency 258.IBPluginDependency - 259.IBPluginDependency 26.IBPluginDependency 26.ImportedFromIB2 260.IBAttributePlaceholdersKey 260.IBPluginDependency - 263.IBPluginDependency - 264.IBPluginDependency 265.IBPluginDependency 27.CustomClassName 27.IBPluginDependency @@ -1739,13 +1918,40 @@ 280.IBPluginDependency 281.IBPluginDependency 284.IBPluginDependency + 303.IBPluginDependency + 304.IBPluginDependency + 319.IBPluginDependency + 320.IBPluginDependency + 321.IBAttributePlaceholdersKey + 321.IBPluginDependency + 322.IBPluginDependency + 340.IBPluginDependency + 341.IBPluginDependency + 342.IBEditorWindowLastContentRect + 342.IBPluginDependency + 343.IBAttributePlaceholdersKey + 343.IBPluginDependency + 344.IBAttributePlaceholdersKey + 344.IBPluginDependency + 345.IBAttributePlaceholdersKey + 345.IBPluginDependency + 350.IBPluginDependency + 351.IBPluginDependency + 352.IBPluginDependency + 353.IBPluginDependency + 357.IBAttributePlaceholdersKey + 357.IBPluginDependency + 358.IBPluginDependency + 360.IBPluginDependency + 361.IBPluginDependency + 362.IBPluginDependency YES com.apple.InterfaceBuilder.CocoaPlugin - {{209, 69}, {500, 371}} + {{118, 69}, {500, 371}} com.apple.InterfaceBuilder.CocoaPlugin - {{209, 69}, {500, 371}} + {{118, 69}, {500, 371}} {196, 240} {{357, 418}, {480, 270}} @@ -1787,7 +1993,7 @@ com.apple.InterfaceBuilder.CocoaPlugin com.apple.InterfaceBuilder.CocoaPlugin com.apple.InterfaceBuilder.CocoaPlugin - {{693, 450}, {145, 73}} + {{495, 480}, {116, 43}} com.apple.InterfaceBuilder.CocoaPlugin com.apple.InterfaceBuilder.CocoaPlugin com.apple.InterfaceBuilder.CocoaPlugin @@ -1806,76 +2012,114 @@ com.brandonwalkin.BWToolkit com.apple.InterfaceBuilder.CocoaPlugin - {{234, 203}, {241, 152}} + {{267, 40}, {217, 98}} com.brandonwalkin.BWToolkit com.brandonwalkin.BWToolkit + com.apple.InterfaceBuilder.CocoaPlugin + + com.apple.InterfaceBuilder.CocoaPlugin ToolTip ToolTip - - Save query of selected favorite to file + + Export selected favorites as SPF file com.apple.InterfaceBuilder.CocoaPlugin - com.apple.InterfaceBuilder.CocoaPlugin ToolTip ToolTip - - Remove all favorites + + Import query favorites from SPF file and append them to the favorite list com.apple.InterfaceBuilder.CocoaPlugin com.apple.InterfaceBuilder.CocoaPlugin com.apple.InterfaceBuilder.CocoaPlugin - com.apple.InterfaceBuilder.CocoaPlugin - com.apple.InterfaceBuilder.CocoaPlugin ToolTip ToolTip - - Export selected favorites as SPF file + + Import query favorites from SPF file and replace the current favorites com.apple.InterfaceBuilder.CocoaPlugin + com.apple.InterfaceBuilder.CocoaPlugin + ImageAndTextCell + com.apple.InterfaceBuilder.CocoaPlugin + + com.apple.InterfaceBuilder.CocoaPlugin + com.apple.InterfaceBuilder.CocoaPlugin + com.brandonwalkin.BWToolkit + com.brandonwalkin.BWToolkit + com.brandonwalkin.BWToolkit + com.brandonwalkin.BWToolkit + com.apple.InterfaceBuilder.CocoaPlugin + com.apple.InterfaceBuilder.CocoaPlugin + com.apple.InterfaceBuilder.CocoaPlugin + com.apple.InterfaceBuilder.CocoaPlugin + com.apple.InterfaceBuilder.CocoaPlugin ToolTip ToolTip - - Import query favorites from SPF file and append them to the favorite list + + Label which appears between the argument input fields (as short as possible) com.apple.InterfaceBuilder.CocoaPlugin com.apple.InterfaceBuilder.CocoaPlugin com.apple.InterfaceBuilder.CocoaPlugin com.apple.InterfaceBuilder.CocoaPlugin - + {{377, 187}, {156, 88}} + com.apple.InterfaceBuilder.CocoaPlugin ToolTip ToolTip - - Import query favorites from SPF file and replace the current favorites + + ${} – Argument placeholder. com.apple.InterfaceBuilder.CocoaPlugin + + ToolTip + + ToolTip + + $CURRENT_FIELD – placeholder. That placeholder will be replaced by the current field name. + + com.apple.InterfaceBuilder.CocoaPlugin + + ToolTip + + ToolTip + + $BINARY – placeholder. The keyword BINARY will be inserted if ⇧ is pressed while invoking “Filter”. + + com.apple.InterfaceBuilder.CocoaPlugin com.apple.InterfaceBuilder.CocoaPlugin - ImageAndTextCell com.apple.InterfaceBuilder.CocoaPlugin - com.apple.InterfaceBuilder.CocoaPlugin com.apple.InterfaceBuilder.CocoaPlugin - com.brandonwalkin.BWToolkit - com.brandonwalkin.BWToolkit - com.brandonwalkin.BWToolkit - com.brandonwalkin.BWToolkit + + ToolTip + + ToolTip + + '${}' – quoted argument placeholder. + + + com.apple.InterfaceBuilder.CocoaPlugin + com.apple.InterfaceBuilder.CocoaPlugin + com.apple.InterfaceBuilder.CocoaPlugin + com.apple.InterfaceBuilder.CocoaPlugin com.apple.InterfaceBuilder.CocoaPlugin @@ -1895,7 +2139,7 @@ - 299 + 366 @@ -1954,7 +2198,7 @@ NSObject - + IBProjectSource Source/SPContentFilterManager.h @@ -1968,7 +2212,7 @@ NSObject - + IBProjectSource Source/SPQueryFavoriteManager.h @@ -2034,21 +2278,18 @@ - SPQueryFavoriteManager + SPContentFilterManager NSWindowController YES YES - addQueryFavorite: - closeQueryManagerSheet: - duplicateQueryFavorite: - exportFavorites: - importFavoritesByAdding: - importFavoritesByReplacing: - removeAllQueryFavorites: - removeQueryFavorite: - saveFavoriteToFile: + addContentFilter: + closeContentFilterManagerSheet: + duplicateContentFilter: + exportContentFilter: + importContentFilterByAdding: + removeContentFilter: YES @@ -2058,33 +2299,34 @@ id id id - id - id - id YES YES + contentFilterArrayController + contentFilterConjunctionTextField + contentFilterNameTextField + contentFilterTableView + contentFilterTextView encodingPopUp - favoriteNameTextField - favoriteQueryTextView - favoritesArrayController - favoritesTableView removeButton + tableHeader YES - NSPopUpButton - NSTextField - NSTextView - NSArrayController - NSTableView + id + id + id + id + id + id + id id - + SPTableView @@ -2095,6 +2337,77 @@ + + YES + + NSObject + + IBDocumentRelativeSource + ../../Source/SPContentFilterManager.h + + + + SPContentFilterManager + NSWindowController + + YES + + YES + addContentFilter: + closeContentFilterManagerSheet: + duplicateContentFilter: + exportContentFilter: + importContentFilterByAdding: + insertPlaceholder: + removeContentFilter: + + + YES + id + id + id + id + id + id + id + + + + YES + + YES + contentFilterArrayController + contentFilterConjunctionLabel + contentFilterConjunctionTextField + contentFilterNameTextField + contentFilterTableView + contentFilterTextView + encodingPopUp + insertPlaceholderButton + numberOfArgsLabel + removeButton + resultingClauseContentLabel + resultingClauseLabel + + + YES + id + id + id + id + id + id + id + id + id + id + id + id + + + + + YES @@ -2108,21 +2421,21 @@ NSApplication NSResponder - + IBFrameworkSource AppKit.framework/Headers/NSApplication.h NSApplication - + IBFrameworkSource AppKit.framework/Headers/NSApplicationScripting.h NSApplication - + IBFrameworkSource AppKit.framework/Headers/NSColorPanel.h @@ -2191,7 +2504,7 @@ NSControl NSView - + IBFrameworkSource AppKit.framework/Headers/NSControl.h @@ -2215,7 +2528,7 @@ NSMenu NSObject - + IBFrameworkSource AppKit.framework/Headers/NSMenu.h @@ -2223,7 +2536,7 @@ NSMenuItem NSObject - + IBFrameworkSource AppKit.framework/Headers/NSMenuItem.h @@ -2245,19 +2558,19 @@ NSObject - + NSObject - + NSObject - + NSObject - + NSObject @@ -2296,7 +2609,7 @@ NSObject - + NSObject @@ -2328,7 +2641,7 @@ NSObject - + IBFrameworkSource AppKit.framework/Headers/NSTableView.h @@ -2342,7 +2655,7 @@ NSObject - + IBFrameworkSource AppKit.framework/Headers/NSView.h @@ -2653,7 +2966,7 @@ NSTableView NSControl - + NSText @@ -2704,7 +3017,7 @@ NSView - + NSView @@ -2716,7 +3029,7 @@ NSView NSResponder - + NSWindow diff --git a/Resources/English.lproj/ContentFilters.plist b/Resources/English.lproj/ContentFilters.plist index 5d79edc0..d153a108 100644 --- a/Resources/English.lproj/ContentFilters.plist +++ b/Resources/English.lproj/ContentFilters.plist @@ -106,8 +106,6 @@ 1 Clause LIKE $BINARY '${}' - Tooltip - Press ⇧ for case-sensitive search. MenuLabel @@ -116,8 +114,6 @@ 1 Clause NOT LIKE $BINARY '${}' - Tooltip - Press ⇧ for case-sensitive search. MenuLabel @@ -126,8 +122,6 @@ 1 Clause LIKE $BINARY '%${}%' - Tooltip - Press ⇧ for case-sensitive search. MenuLabel @@ -136,8 +130,6 @@ 1 Clause NOT LIKE $BINARY '%${}%' - Tooltip - Press ⇧ for case-sensitive search. MenuLabel @@ -146,8 +138,6 @@ 1 Clause LIKE $BINARY '${}' - Tooltip - Press ⇧ for case-sensitive search. MenuLabel @@ -156,8 +146,6 @@ 1 Clause NOT LIKE $BINARY '${}' - Tooltip - Press ⇧ for case-sensitive search. MenuLabel @@ -167,7 +155,9 @@ Clause IN (${}) Tooltip - Do quote strings manually. + IN ([arg]) + +Do quote strings manually. MenuLabel @@ -180,8 +170,6 @@ Clause BETWEEN $BINARY '${}' AND '${}' - Tooltip - Press ⇧ for case-sensitive search. MenuLabel diff --git a/Source/SPContentFilterManager.h b/Source/SPContentFilterManager.h index c0b22cd9..50cdb95a 100644 --- a/Source/SPContentFilterManager.h +++ b/Source/SPContentFilterManager.h @@ -4,8 +4,8 @@ // SPContentFilterManager.h // sequel-pro // -// Created by Stuart Connolly (stuconnolly.com) on Aug 23, 2009 -// Copyright (c) 2009 Stuart Connolly. All rights reserved. +// Created by Hans-Jörg Bibiko on Sep 29, 2009 +// Copyright (c) 2009 Hans-Jörg Bibiko. All rights reserved. // // This program is free software; you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by @@ -27,7 +27,7 @@ @interface NSObject (SPContentFilterManagerDelegate) -- (void)queryFavoritesHaveBeenUpdated:(id)manager; +- (void)contentFiltersHaveBeenUpdated:(id)manager; @end @@ -36,34 +36,41 @@ NSUserDefaults *prefs; NSURL *delegatesFileURL; - IBOutlet NSPopUpButton *encodingPopUp; - IBOutlet NSTableView *favoritesTableView; - IBOutlet NSTextField *favoriteNameTextField; - IBOutlet NSTextView *favoriteQueryTextView; + IBOutlet id encodingPopUp; + IBOutlet id contentFilterTableView; + IBOutlet id contentFilterNameTextField; + IBOutlet id contentFilterConjunctionTextField; + IBOutlet id contentFilterConjunctionLabel; + IBOutlet id contentFilterTextView; IBOutlet id removeButton; + IBOutlet id numberOfArgsLabel; + IBOutlet id resultingClauseLabel; + IBOutlet id resultingClauseContentLabel; + IBOutlet id insertPlaceholderButton; - IBOutlet NSArrayController *favoritesArrayController; + IBOutlet id contentFilterArrayController; - NSMutableArray *favorites; + NSMutableArray *contentFilters; BOOL isTableCellEditing; + + NSString *filterType; } -- (id)initWithDelegate:(id)managerDelegate; +- (id)initWithDelegate:(id)managerDelegate forFilterType:(NSString *)compareType; // Accessors -- (NSMutableArray *)queryFavoritesForFileURL:(NSURL *)fileURL; +- (NSMutableArray *)contentFilterForFileURL:(NSURL *)fileURL; - (id)customQueryInstance; // IBAction methods -- (IBAction)addQueryFavorite:(id)sender; -- (IBAction)removeQueryFavorite:(id)sender; -- (IBAction)removeAllQueryFavorites:(id)sender; -- (IBAction)duplicateQueryFavorite:(id)sender; -- (IBAction)saveFavoriteToFile:(id)sender; -- (IBAction)exportFavorites:(id)sender; -- (IBAction)importFavoritesByAdding:(id)sender; -- (IBAction)importFavoritesByReplacing:(id)sender; -- (IBAction)closeQueryManagerSheet:(id)sender; +- (IBAction)addContentFilter:(id)sender; +- (IBAction)removeContentFilter:(id)sender; +- (IBAction)insertPlaceholder:(id)sender; +- (IBAction)duplicateContentFilter:(id)sender; +- (IBAction)exportContentFilter:(id)sender; +- (IBAction)importContentFilterByAdding:(id)sender; +// - (IBAction)importContentFilterByReplacing:(id)sender; +- (IBAction)closeContentFilterManagerSheet:(id)sender; @end diff --git a/Source/SPContentFilterManager.m b/Source/SPContentFilterManager.m index 46726bb8..8ac609b9 100644 --- a/Source/SPContentFilterManager.m +++ b/Source/SPContentFilterManager.m @@ -4,8 +4,8 @@ // SPContentFilterManager.m // sequel-pro // -// Created by Stuart Connolly (stuconnolly.com) on Aug 23, 2009 -// Copyright (c) 2009 Stuart Connolly. All rights reserved. +// Created by Hans-Jörg Bibiko on Sep 29, 2009 +// Copyright (c) 2009 Hans-Jörg Bibiko. All rights reserved. // // This program is free software; you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by @@ -25,16 +25,15 @@ #import "SPContentFilterManager.h" #import "ImageAndTextCell.h" -#import "SPEncodingPopupAccessory.h" +#import "RegexKitLite.h" #import "SPQueryController.h" -#define DEFAULT_QUERY_FAVORITE_FILE_EXTENSION @"sql" #define DEFAULT_SEQUELPRO_FILE_EXTENSION @"spf" #define SP_MULTIPLE_SELECTION_PLACEHOLDER_STRING NSLocalizedString(@"[multiple selection]", @"[multiple selection]") #define SP_NO_SELECTION_PLACEHOLDER_STRING NSLocalizedString(@"[no selection]", @"[no selection]") -#define QUERY_FAVORITES_PB_DRAG_TYPE @"SequelProQueryFavoritesPasteboard" +#define CONTENT_FILTER_PB_DRAG_TYPE @"SequelProContentFilterPasteboard" @interface SPContentFilterManager (Private) - (void)_initWithNoSelection; @@ -45,20 +44,22 @@ /** * Initialize the manager with the supplied delegate */ -- (id)initWithDelegate:(id)managerDelegate +- (id)initWithDelegate:(id)managerDelegate forFilterType:(NSString *)compareType { - if ((self = [super initWithWindowNibName:@"QueryFavoriteManager"])) { + if ((self = [super initWithWindowNibName:@"ContentFilterManager"])) { prefs = [NSUserDefaults standardUserDefaults]; - favorites = [[NSMutableArray alloc] init]; + contentFilters = [[NSMutableArray alloc] init]; if(managerDelegate == nil) { NSBeep(); - NSLog(@"Query Favorite Manger was called without a delegate."); + NSLog(@"ContentFilterManager was called without a delegate."); return nil; } delegatesFileURL = [[managerDelegate valueForKeyPath:@"tableDocumentInstance"] fileURL]; + filterType = [NSString stringWithString:compareType]; + } return self; @@ -66,7 +67,7 @@ - (void)dealloc { - [favorites release]; + [contentFilters release]; [super dealloc]; } @@ -76,60 +77,68 @@ - (void)awakeFromNib { - [favoriteQueryTextView setAllowsDocumentBackgroundColorChange:YES]; + [contentFilterTextView setAllowsDocumentBackgroundColorChange:YES]; NSMutableDictionary *bindingOptions = [NSMutableDictionary dictionary]; [bindingOptions setObject:NSUnarchiveFromDataTransformerName forKey:@"NSValueTransformerName"]; - [favoriteQueryTextView bind:@"backgroundColor" + [contentFilterTextView bind:@"backgroundColor" toObject:[NSUserDefaultsController sharedUserDefaultsController] withKeyPath:@"values.CustomQueryEditorBackgroundColor" options:bindingOptions]; - [favorites addObject:[NSDictionary dictionaryWithObjectsAndKeys: - @"Global", @"name", + [contentFilters addObject:[NSDictionary dictionaryWithObjectsAndKeys: + @"Global", @"MenuLabel", @"", @"headerOfFileURL", - @"", @"query", + @"", @"Clause", + @"", @"ConjunctionLabel", nil]]; // Build data source for global queryFavorites (as mutable copy! otherwise each // change will be stored in the prefs at once) - if([prefs objectForKey:@"queryFavorites"]) { - for(id fav in [prefs objectForKey:@"queryFavorites"]) - [favorites addObject:[[fav mutableCopy] autorelease]]; + if([[prefs objectForKey:@"ContentFilters"] objectForKey:filterType]) { + for(id fav in [[prefs objectForKey:@"ContentFilters"] objectForKey:filterType]) { + id f = [[fav mutableCopy] autorelease]; + if([f objectForKey:@"ConjunctionLabels"]) + [f setObject:[[f objectForKey:@"ConjunctionLabels"] objectAtIndex:0] forKey:@"ConjunctionLabel"]; + [contentFilters addObject:f]; + } } - [favorites addObject:[NSDictionary dictionaryWithObjectsAndKeys: - [[[delegatesFileURL absoluteString] stringByReplacingPercentEscapesUsingEncoding:NSUTF8StringEncoding] lastPathComponent], @"name", + [contentFilters addObject:[NSDictionary dictionaryWithObjectsAndKeys: + [[[delegatesFileURL absoluteString] stringByReplacingPercentEscapesUsingEncoding:NSUTF8StringEncoding] lastPathComponent], @"MenuLabel", [delegatesFileURL absoluteString], @"headerOfFileURL", - @"", @"query", + @"", @"Clause", nil]]; - if([[SPQueryController sharedQueryController] favoritesForFileURL:delegatesFileURL]) { - for(id fav in [[SPQueryController sharedQueryController] favoritesForFileURL:delegatesFileURL]) - [favorites addObject:[[fav mutableCopy] autorelease]]; - } + // if([[SPQueryController sharedQueryController] favoritesForFileURL:delegatesFileURL]) { + // for(id fav in [[SPQueryController sharedQueryController] favoritesForFileURL:delegatesFileURL]) + // [contentFilters addObject:[[fav mutableCopy] autorelease]]; + // } // Select the first query if any NSUInteger i = 0; - for(i=0; i < [favorites count]; i++ ) - if(![[favorites objectAtIndex:i] objectForKey:@"headerOfFileURL"]) + for(i=0; i < [contentFilters count]; i++ ) + if(![[contentFilters objectAtIndex:i] objectForKey:@"headerOfFileURL"]) break; - [[self window] makeFirstResponder:favoritesTableView]; + [[self window] makeFirstResponder:contentFilterTableView]; [self _initWithNoSelection]; // Register drag types - [favoritesTableView registerForDraggedTypes:[NSArray arrayWithObject:QUERY_FAVORITES_PB_DRAG_TYPE]]; + [contentFilterTableView registerForDraggedTypes:[NSArray arrayWithObject:CONTENT_FILTER_PB_DRAG_TYPE]]; - [favoritesArrayController setContent:favorites]; - [favoritesTableView reloadData]; + [contentFilterArrayController setContent:contentFilters]; + [contentFilterTableView reloadData]; // Set Remove button state - [removeButton setEnabled:([favoritesTableView numberOfSelectedRows] > 0)]; + [removeButton setEnabled:([contentFilterTableView numberOfSelectedRows] > 0)]; + + // Set column header + [[[contentFilterTableView tableColumnWithIdentifier:@"MenuLabel"] headerCell] setStringValue:[NSString stringWithFormat:NSLocalizedString(@"‘%@’ Fields Content Filters", @"content filter for field type ‘%@’"), filterType]]; } @@ -137,12 +146,12 @@ #pragma mark Accessor methods /** - * Returns the query favorites array for fileURL. - * fileURL == nil → global favorites + * Returns the content filters array for fileURL. + * fileURL == nil → global content filters */ -- (NSMutableArray *)queryFavoritesForFileURL:(NSURL *)fileURL +- (NSMutableArray *)contentFilterForFileURL:(NSURL *)fileURL { - NSMutableArray *favs = [NSMutableArray array]; + NSMutableArray *filters = [NSMutableArray array]; NSString *fileURLstring; if(fileURL == nil) @@ -153,26 +162,43 @@ NSUInteger i = 0; // Look for the header specified by fileURL - while(i<[favorites count]) { - if ([[favorites objectAtIndex:i] objectForKey:@"headerOfFileURL"] - && [[[favorites objectAtIndex:i] objectForKey:@"headerOfFileURL"] isEqualToString:fileURLstring]) { + while(i<[contentFilters count]) { + if ([[contentFilters objectAtIndex:i] objectForKey:@"headerOfFileURL"] + && [[[contentFilters objectAtIndex:i] objectForKey:@"headerOfFileURL"] isEqualToString:fileURLstring]) { i++; break; } i++; } - // Take all favorites until the next header or end of favorites - for(i; i<[favorites count]; i++) { - - if(![[favorites objectAtIndex:i] objectForKey:@"headerOfFileURL"]) - [favs addObject:[favorites objectAtIndex:i]]; - else + // Take all content filters until the next header or end of all content filters + NSUInteger numOfArgs; + for(i; i<[contentFilters count]; i++) { + + if(![[contentFilters objectAtIndex:i] objectForKey:@"headerOfFileURL"]) { + NSMutableDictionary *d = [[NSMutableDictionary alloc] init]; + [d setDictionary:[contentFilters objectAtIndex:i]]; + NSMutableArray *conjLabel = [[NSMutableArray alloc] init]; + numOfArgs = [[[contentFilterTextView string] componentsMatchedByRegex:@"(? 1) { + if([d objectForKey:@"ConjunctionLabel"]) { + [conjLabel addObject:[d objectForKey:@"ConjunctionLabel"]]; + [d setObject:conjLabel forKey:@"ConjunctionLabels"]; + } + } else { + [d removeObjectForKey:@"ConjunctionLabels"]; + } + [d removeObjectForKey:@"ConjunctionLabel"]; + [conjLabel release]; + [d setObject:[NSNumber numberWithInteger:numOfArgs] forKey:@"NumberOfArguments"]; + [filters addObject:d]; + [d release]; + } else break; } - return favs; + return filters; } /** @@ -183,88 +209,70 @@ return [[[NSApp mainWindow] delegate] valueForKey:@"customQueryInstance"]; } + #pragma mark - #pragma mark IBAction methods /** - * Adds/Inserts a query favorite + * Adds/Inserts a content filter */ -- (IBAction)addQueryFavorite:(id)sender +- (IBAction)addContentFilter:(id)sender { - NSMutableDictionary *favorite; + NSMutableDictionary *filter; NSUInteger insertIndex; - // Duplicate a selected favorite if sender == self + // Store pending changes in Clause + [[self window] makeFirstResponder:contentFilterNameTextField]; + + // Duplicate a selected filter if sender == self if(sender == self) - favorite = [NSMutableDictionary dictionaryWithObjects:[NSArray arrayWithObjects:[[favoriteNameTextField stringValue] stringByAppendingFormat:@" Copy"], [favoriteQueryTextView string], nil] forKeys:[NSArray arrayWithObjects:@"name", @"query", nil]]; - // Add a new favorite + filter = [NSMutableDictionary dictionaryWithObjects:[NSArray arrayWithObjects:[[contentFilterNameTextField stringValue] stringByAppendingFormat:@" Copy"], [contentFilterTextView string], nil] forKeys:[NSArray arrayWithObjects:@"MenuLabel", @"Clause", nil]]; + // Add a new filter else - favorite = [NSMutableDictionary dictionaryWithObjects:[NSArray arrayWithObjects:@"New Favorite", @"", nil] forKeys:[NSArray arrayWithObjects:@"name", @"query", nil]]; - - if([favoritesTableView numberOfSelectedRows] > 0) { - insertIndex = [[favoritesTableView selectedRowIndexes] lastIndex]+1; - [favorites insertObject:favorite atIndex:insertIndex]; + filter = [NSMutableDictionary dictionaryWithObjects:[NSArray arrayWithObjects:@"New Filter", @"", @"", nil] forKeys:[NSArray arrayWithObjects:@"MenuLabel", @"Clause", @"ConjunctionLabel", nil]]; + + if([contentFilterTableView numberOfSelectedRows] > 0) { + insertIndex = [[contentFilterTableView selectedRowIndexes] lastIndex]+1; + [contentFilters insertObject:filter atIndex:insertIndex]; } else { - [favorites addObject:favorite]; - insertIndex = [favorites count] - 1; + [contentFilters addObject:filter]; + insertIndex = [contentFilters count] - 1; } - [favoritesArrayController rearrangeObjects]; - [favoritesTableView reloadData]; + [contentFilterArrayController rearrangeObjects]; + [contentFilterTableView reloadData]; - [favoritesTableView selectRowIndexes:[NSIndexSet indexSetWithIndex:insertIndex] byExtendingSelection:NO]; + [contentFilterTableView selectRowIndexes:[NSIndexSet indexSetWithIndex:insertIndex] byExtendingSelection:NO]; - [favoritesTableView scrollRowToVisible:[favoritesTableView selectedRow]]; + [contentFilterTableView scrollRowToVisible:[contentFilterTableView selectedRow]]; - [removeButton setEnabled:([favoritesTableView numberOfSelectedRows] > 0)]; - [[self window] makeFirstResponder:favoriteNameTextField]; + [removeButton setEnabled:([contentFilterTableView numberOfSelectedRows] > 0)]; + [[self window] makeFirstResponder:contentFilterNameTextField]; } /** - * Duplicates a query favorite + * Duplicates a filter */ -- (IBAction)duplicateQueryFavorite:(id)sender +- (IBAction)duplicateContentFilter:(id)sender { - if ([favoritesTableView numberOfSelectedRows] == 1) - [self addQueryFavorite:self]; + if ([contentFilterTableView numberOfSelectedRows] == 1) + [self addContentFilter:self]; else NSBeep(); } /** - * Removes a query favorite + * Removes a filter */ -- (IBAction)removeQueryFavorite:(id)sender +- (IBAction)removeContentFilter:(id)sender { - NSAlert *alert = [NSAlert alertWithMessageText:NSLocalizedString(@"Remove selected query favorites?", @"remove selected query favorites message") + NSAlert *alert = [NSAlert alertWithMessageText:NSLocalizedString(@"Remove selected content filters?", @"remove selected content filters message") defaultButton:NSLocalizedString(@"Cancel", @"cancel button") alternateButton:NSLocalizedString(@"Remove", @"remove button") otherButton:nil - informativeTextWithFormat:NSLocalizedString(@"Are you sure you want to remove all selected query favorites? This action cannot be undone.", @"remove all selected query favorites informative message")]; - - [alert setAlertStyle:NSCriticalAlertStyle]; - - NSArray *buttons = [alert buttons]; - - // Change the alert's cancel button to have the key equivalent of return - [[buttons objectAtIndex:0] setKeyEquivalent:@"\r"]; - [[buttons objectAtIndex:1] setKeyEquivalent:@""]; - - [alert beginSheetModalForWindow:[self window] modalDelegate:self didEndSelector:@selector(sheetDidEnd:returnCode:contextInfo:) contextInfo:@"removeSelectedFavorites"]; -} - -/** - * Removes all query favorites - */ -- (IBAction)removeAllQueryFavorites:(id)sender -{ - NSAlert *alert = [NSAlert alertWithMessageText:NSLocalizedString(@"Remove all query favorites?", @"remove all query favorites message") - defaultButton:NSLocalizedString(@"Cancel", @"cancel button") - alternateButton:NSLocalizedString(@"Remove All", @"remove all button") - otherButton:nil - informativeTextWithFormat:NSLocalizedString(@"Are you sure you want to remove all of your saved query favorites? This action cannot be undone.", @"remove all query favorites informative message")]; + informativeTextWithFormat:NSLocalizedString(@"Are you sure you want to remove all selected content filters? This action cannot be undone.", @"remove all selected content filters informative message")]; [alert setAlertStyle:NSCriticalAlertStyle]; @@ -274,31 +282,18 @@ [[buttons objectAtIndex:0] setKeyEquivalent:@"\r"]; [[buttons objectAtIndex:1] setKeyEquivalent:@""]; - [alert beginSheetModalForWindow:[self window] modalDelegate:self didEndSelector:@selector(sheetDidEnd:returnCode:contextInfo:) contextInfo:@"removeAllFavorites"]; + [alert beginSheetModalForWindow:[self window] modalDelegate:self didEndSelector:@selector(sheetDidEnd:returnCode:contextInfo:) contextInfo:@"removeSelectedFilters"]; } /** - * Saves the currently selected query favorite to a user specified file. + * Insert placeholder - the placeholder string is stored as tooltip */ -- (IBAction)saveFavoriteToFile:(id)sender +- (IBAction)insertPlaceholder:(id)sender { - NSSavePanel *panel = [NSSavePanel savePanel]; - - [panel setRequiredFileType:DEFAULT_QUERY_FAVORITE_FILE_EXTENSION]; - - [panel setExtensionHidden:NO]; - [panel setAllowsOtherFileTypes:YES]; - [panel setCanSelectHiddenExtension:YES]; - [panel setCanCreateDirectories:YES]; - - [panel setAccessoryView:[SPEncodingPopupAccessory encodingAccessory:[prefs integerForKey:@"lastSqlFileEncoding"] includeDefaultEntry:NO encodingPopUp:&encodingPopUp]]; - - [encodingPopUp setEnabled:YES]; - - [panel beginSheetForDirectory:nil file:[favoriteNameTextField stringValue] modalForWindow:[self window] modalDelegate:self didEndSelector:@selector(savePanelDidEnd:returnCode:contextInfo:) contextInfo:@"saveQuery"]; + [contentFilterTextView insertText:[[[sender selectedItem] toolTip] substringToIndex:[[[sender selectedItem] toolTip] rangeOfString:@" – "].location]]; } -- (IBAction)exportFavorites:(id)sender +- (IBAction)exportContentFilter:(id)sender { NSSavePanel *panel = [NSSavePanel savePanel]; @@ -309,10 +304,10 @@ [panel setCanSelectHiddenExtension:YES]; [panel setCanCreateDirectories:YES]; - [panel beginSheetForDirectory:nil file:nil modalForWindow:[self window] modalDelegate:self didEndSelector:@selector(savePanelDidEnd:returnCode:contextInfo:) contextInfo:@"exportFavorites"]; + [panel beginSheetForDirectory:nil file:nil modalForWindow:[self window] modalDelegate:self didEndSelector:@selector(savePanelDidEnd:returnCode:contextInfo:) contextInfo:@"exportFilter"]; } -- (IBAction)importFavoritesByAdding:(id)sender +- (IBAction)importContentFilterByAdding:(id)sender { NSOpenPanel *panel = [NSOpenPanel openPanel]; [panel setCanSelectHiddenExtension:YES]; @@ -323,7 +318,7 @@ [panel beginSheetForDirectory:nil file:@"" - types:[NSArray arrayWithObjects:@"spf", @"sql", nil] + types:[NSArray arrayWithObjects:@"spf", nil] modalForWindow:[self window] modalDelegate:self didEndSelector:@selector(importPanelDidEnd:returnCode:contextInfo:) @@ -336,14 +331,14 @@ } /** - * Closes the query favorite manager + * Closes the content filter manager */ -- (IBAction)closeQueryManagerSheet:(id)sender +- (IBAction)closeContentFilterManagerSheet:(id)sender { // First check for ESC if pressed while inline editing if(![sender tag] && isTableCellEditing) { - [favoritesTableView abortEditing]; + [contentFilterTableView abortEditing]; isTableCellEditing = NO; return; } @@ -355,22 +350,24 @@ if([sender tag]) { // Ensure that last changes will be written back - // if only one favorite is selected; otherwise unstable state - if ([favoritesTableView numberOfSelectedRows] == 1) { - [[self window] makeFirstResponder:favoritesTableView]; + // if only one filter is selected; otherwise unstable state + if ([contentFilterTableView numberOfSelectedRows] == 1) { + [[self window] makeFirstResponder:contentFilterTableView]; } - - // Update current document's query favorites in the SPQueryController - [[SPQueryController sharedQueryController] replaceFavoritesByArray: - [self queryFavoritesForFileURL:delegatesFileURL] forFileURL:delegatesFileURL]; - + + // Update current document's content filters in the SPQueryController + // [[SPQueryController sharedQueryController] replaceFavoritesByArray: + // [self contentFilterForFileURL:delegatesFileURL] forFileURL:delegatesFileURL]; + // // Update global preferences' list - [prefs setObject:[self queryFavoritesForFileURL:nil] forKey:@"queryFavorites"]; + id cf = [[prefs objectForKey:@"ContentFilters"] mutableCopy]; + [cf setObject:[self contentFilterForFileURL:nil] forKey:filterType]; + [prefs setObject:cf forKey:@"ContentFilters"]; - // Inform all opened documents to update the query favorites list - for(id doc in [[NSDocumentController sharedDocumentController] documents]) - if([[doc valueForKeyPath:@"customQueryInstance"] respondsToSelector:@selector(queryFavoritesHaveBeenUpdated:)]) - [[doc valueForKeyPath:@"customQueryInstance"] queryFavoritesHaveBeenUpdated:self]; + // // Inform all opened documents to update the query favorites list + // for(id doc in [[NSDocumentController sharedDocumentController] documents]) + // if([[doc valueForKeyPath:@"customQueryInstance"] respondsToSelector:@selector(queryFavoritesHaveBeenUpdated:)]) + // [[doc valueForKeyPath:@"customQueryInstance"] queryFavoritesHaveBeenUpdated:self]; } @@ -400,11 +397,11 @@ #pragma mark TableView datasource methods /** - * Returns the number of query favorites. + * Returns the number of all content filters. */ - (NSInteger)numberOfRowsInTableView:(NSTableView *)aTableView { - return [favorites count]; + return [contentFilters count]; } /** @@ -412,49 +409,55 @@ */ - (id)tableView:(NSTableView *)aTableView objectValueForTableColumn:(NSTableColumn *)aTableColumn row:(NSInteger)rowIndex { - if(![[favorites objectAtIndex:rowIndex] objectForKey:[aTableColumn identifier]]) return @""; + if(![[contentFilters objectAtIndex:rowIndex] objectForKey:[aTableColumn identifier]]) return @""; - return [[favorites objectAtIndex:rowIndex] objectForKey:[aTableColumn identifier]]; + return [[contentFilters objectAtIndex:rowIndex] objectForKey:[aTableColumn identifier]]; } /* - * Save favorite names if inline edited (suppress empty names) + * Save content filter name (MenuLabel) if inline edited (suppress empty names) */ - (void)tableView:(NSTableView *)aTableView setObjectValue:(id)anObject forTableColumn:(NSTableColumn *)aTableColumn row:(NSInteger)rowIndex { - if([[aTableColumn identifier] isEqualToString:@"name"] && [anObject length]) { - [[favorites objectAtIndex:rowIndex] setObject:[anObject description] forKey:@"name"]; - // [[favorites objectAtIndex:rowIndex] setObject:[favoriteQueryTextView string] forKey:@"query"]; - [favoriteNameTextField setStringValue:[anObject description]]; + if([[aTableColumn identifier] isEqualToString:@"MenuLabel"] && [anObject length]) { + [[contentFilters objectAtIndex:rowIndex] setObject:[anObject description] forKey:@"MenuLabel"]; + [contentFilterNameTextField setStringValue:[anObject description]]; } - [favoritesTableView reloadData]; + [contentFilterTableView reloadData]; } /* - * Before selecting an other favorite save pending query string changes + * Before selecting an other filter save pending query string changes * and make sure that no group table item can be selected */ - (BOOL)tableView:(NSTableView *)aTableView shouldSelectRow:(NSInteger)rowIndex { - return ([[favorites objectAtIndex:rowIndex] objectForKey:@"headerOfFileURL"]) ? NO : YES; + BOOL enable = ([contentFilterTableView numberOfSelectedRows] > 0); + [removeButton setEnabled:enable]; + [numberOfArgsLabel setHidden:!enable]; + [resultingClauseLabel setHidden:!enable]; + [resultingClauseContentLabel setHidden:!enable]; + [insertPlaceholderButton setEnabled:enable]; + + return ([[contentFilters objectAtIndex:rowIndex] objectForKey:@"headerOfFileURL"]) ? NO : YES; } /* - * Set indention levels for headers and favorites + * Set indention levels for headers and filters * (maybe in the future use an image for headers for expanding and collapsing) */ - (void)tableView:(NSTableView *)aTableView willDisplayCell:(id)aCell forTableColumn:(NSTableColumn *)aTableColumn row:(NSInteger)rowIndex { - if([[favorites objectAtIndex:rowIndex] objectForKey:@"headerOfFileURL"] && [[aTableColumn identifier] isEqualToString:@"name"]) { + if([[contentFilters objectAtIndex:rowIndex] objectForKey:@"headerOfFileURL"] && [[aTableColumn identifier] isEqualToString:@"MenuLabel"]) { // if([[[favoriteProperties objectAtIndex:rowIndex] objectForKey:@"isGroup"] isEqualToString:@"1"]) // [(ImageAndTextCell*)aCell setImage:[NSImage imageNamed:@"NSRightFacingTriangleTemplate"]]; // else // [(ImageAndTextCell*)aCell setImage:[NSImage imageNamed:@"NSLeftFacingTriangleTemplate"]]; [(ImageAndTextCell*)aCell setIndentationLevel:0]; } - else if(![[favorites objectAtIndex:rowIndex] objectForKey:@"headerOfFileURL"] && [[aTableColumn identifier] isEqualToString:@"name"]) { + else if(![[contentFilters objectAtIndex:rowIndex] objectForKey:@"headerOfFileURL"] && [[aTableColumn identifier] isEqualToString:@"MenuLabel"]) { // [(ImageAndTextCell*)aCell setImage:[NSImage imageNamed:@"dummy-small"]]; [(ImageAndTextCell*)aCell setIndentationLevel:1]; } @@ -465,15 +468,15 @@ */ - (CGFloat)tableView:(NSTableView *)aTableView heightOfRow:(NSInteger)rowIndex { - return ([[favorites objectAtIndex:rowIndex] objectForKey:@"headerOfFileURL"]) ? 20 : 18; + return ([[contentFilters objectAtIndex:rowIndex] objectForKey:@"headerOfFileURL"]) ? 20 : 18; } /* - * Only favorite name can be edited inline + * Only filter name can be edited inline */ - (BOOL)tableView:(NSTableView *)aTableView shouldEditTableColumn:(NSTableColumn *)aTableColumn row:(NSInteger)rowIndex { - if([[favorites objectAtIndex:rowIndex] objectForKey:@"headerOfFileURL"]) { + if([[contentFilters objectAtIndex:rowIndex] objectForKey:@"headerOfFileURL"]) { return NO; } else { isTableCellEditing = YES; @@ -491,11 +494,11 @@ } /* - * favoriteProperties holds the data if a table row is a group header or not + * contentFilters holds the data if a table row is a group header or not */ - (BOOL)tableView:(NSTableView *)aTableView isGroupRow:(NSInteger)rowIndex { - return ([[favorites objectAtIndex:rowIndex] objectForKey:@"headerOfFileURL"]) ? YES : NO; + return ([[contentFilters objectAtIndex:rowIndex] objectForKey:@"headerOfFileURL"]) ? YES : NO; } /* * Detect if inline editing was done - then ESC to close the sheet will be activate @@ -512,18 +515,59 @@ - (void)controlTextDidChange:(NSNotification *)notification { - // Do nothing if no favorite is selected - if([favoritesTableView numberOfSelectedRows] < 1) return; + // Do nothing if no filter is selected + if([contentFilterTableView numberOfSelectedRows] < 1) return; id object = [notification object]; - if(object == favoriteNameTextField) { - [[favorites objectAtIndex:[favoritesTableView selectedRow]] setObject:[favoriteNameTextField stringValue] forKey:@"name"]; - [favoritesTableView reloadData]; + if(object == contentFilterNameTextField) { + [[contentFilters objectAtIndex:[contentFilterTableView selectedRow]] setObject:[contentFilterNameTextField stringValue] forKey:@"MenuLabel"]; + [contentFilterTableView reloadData]; } } +/* + * Parse clause and update labels accordingly + */ +- (void)textViewDidChangeSelection:(NSNotification *)notification +{ + // Do nothing if no filter is selected + if([contentFilterTableView numberOfSelectedRows] < 1) return; + + id object = [notification object]; + + if(object == contentFilterTextView) { + [insertPlaceholderButton setEnabled:([[contentFilterTextView string] length])]; + [resultingClauseLabel setHidden:(![[contentFilterTextView string] length])]; + [resultingClauseContentLabel setHidden:(![[contentFilterTextView string] length])]; + [numberOfArgsLabel setHidden:(![[contentFilterTextView string] length])]; + + NSUInteger numOfArgs = [[[contentFilterTextView string] componentsMatchedByRegex:@"(? 2) { + [resultingClauseLabel setStringValue:NSLocalizedString(@"Error", @"Error")]; + [resultingClauseContentLabel setStringValue:NSLocalizedString(@"Maximum number of arguments is 2!", @"Maximum number of arguments is 2!")]; + } else { + [resultingClauseLabel setStringValue:@"SELECT * FROM WHERE"]; + NSMutableString *c = [[NSMutableString alloc] init]; + [c setString:[contentFilterTextView string]]; + [c replaceOccurrencesOfRegex:@"(?"]; + [c flushCachedRegexData]; + [resultingClauseContentLabel setStringValue:[NSString stringWithFormat:@" %@", c]]; + [c release]; + } + + } +} #pragma mark - #pragma mark Menu validation @@ -534,22 +578,18 @@ { // Disable all if only GLOBAL is in the table - if([favorites count] < 2) return NO; + if([contentFilters count] < 2) return NO; SEL action = [menuItem action]; - if ( (action == @selector(duplicateQueryFavorite:)) || - (action == @selector(saveFavoriteToFile:))) + if ( (action == @selector(duplicateContentFilter:))) { - return ([favoritesTableView numberOfSelectedRows] == 1); + return ([contentFilterTableView numberOfSelectedRows] == 1); } - else if ( (action == @selector(removeQueryFavorite:)) || + else if ( (action == @selector(removeContentFilter:)) || ( action == @selector(exportFavorites:))) { - return ([favoritesTableView numberOfSelectedRows] > 0); - } - else if (action == @selector(removeAllQueryFavorites:)) { - return ([favorites count] > 0); + return ([contentFilterTableView numberOfSelectedRows] > 0); } return YES; @@ -564,30 +604,24 @@ - (BOOL)tableView:(NSTableView *)tableView writeRows:(NSArray *)rows toPasteboard:(NSPasteboard *)pboard { - // Up to now only one row can be dragged - // if ([rows count] == 1) { - - NSArray *pboardTypes = [NSArray arrayWithObject:QUERY_FAVORITES_PB_DRAG_TYPE]; - NSInteger originalRow = [[rows objectAtIndex:0] intValue]; + NSArray *pboardTypes = [NSArray arrayWithObject:CONTENT_FILTER_PB_DRAG_TYPE]; + NSInteger originalRow = [[rows objectAtIndex:0] intValue]; - if(originalRow < 1) return NO; + if(originalRow < 1) return NO; - // Do not drag headers - if([[favorites objectAtIndex:originalRow] objectForKey:@"headerOfFileURL"]) return NO; + // Do not drag headers + if([[contentFilters objectAtIndex:originalRow] objectForKey:@"headerOfFileURL"]) return NO; - [pboard declareTypes:pboardTypes owner:nil]; + [pboard declareTypes:pboardTypes owner:nil]; - NSMutableData *indexdata = [[[NSMutableData alloc] init] autorelease]; - NSKeyedArchiver *archiver = [[[NSKeyedArchiver alloc] initForWritingWithMutableData:indexdata] autorelease]; - [archiver encodeObject:rows forKey:@"indexdata"]; - [archiver finishEncoding]; - [pboard setData:indexdata forType:QUERY_FAVORITES_PB_DRAG_TYPE]; + NSMutableData *indexdata = [[[NSMutableData alloc] init] autorelease]; + NSKeyedArchiver *archiver = [[[NSKeyedArchiver alloc] initForWritingWithMutableData:indexdata] autorelease]; + [archiver encodeObject:rows forKey:@"indexdata"]; + [archiver finishEncoding]; + [pboard setData:indexdata forType:CONTENT_FILTER_PB_DRAG_TYPE]; - return YES; - - // } + return YES; - // return NO; } /** @@ -598,7 +632,7 @@ NSArray *pboardTypes = [[info draggingPasteboard] types]; if (([pboardTypes count] > 1) && (row != -1)) { - if (([pboardTypes containsObject:QUERY_FAVORITES_PB_DRAG_TYPE]) && (operation == NSTableViewDropAbove)) { + if (([pboardTypes containsObject:CONTENT_FILTER_PB_DRAG_TYPE]) && (operation == NSTableViewDropAbove)) { if (row > 0) { return NSDragOperationMove; } @@ -617,7 +651,7 @@ if(row < 1) return NO; - NSKeyedUnarchiver *unarchiver = [[[NSKeyedUnarchiver alloc] initForReadingWithData:[[info draggingPasteboard] dataForType:QUERY_FAVORITES_PB_DRAG_TYPE]] autorelease]; + NSKeyedUnarchiver *unarchiver = [[[NSKeyedUnarchiver alloc] initForReadingWithData:[[info draggingPasteboard] dataForType:CONTENT_FILTER_PB_DRAG_TYPE]] autorelease]; NSArray *draggedRows = [NSArray arrayWithArray:(NSArray *)[unarchiver decodeObjectForKey:@"indexdata"]]; [unarchiver finishDecoding]; @@ -635,23 +669,23 @@ originalRow += offset; // For safety reasons - if(originalRow > [favorites count]-1) originalRow = [favorites count] - 1; + if(originalRow > [contentFilters count]-1) originalRow = [contentFilters count] - 1; - NSMutableDictionary *draggedRow = [NSMutableDictionary dictionaryWithDictionary:[favorites objectAtIndex:originalRow]]; - [favorites removeObjectAtIndex:originalRow]; - [favoritesTableView reloadData]; + NSMutableDictionary *draggedRow = [NSMutableDictionary dictionaryWithDictionary:[contentFilters objectAtIndex:originalRow]]; + [contentFilters removeObjectAtIndex:originalRow]; + [contentFilterTableView reloadData]; - if(destinationRow+i >= [favorites count]) - [favorites addObject:draggedRow]; + if(destinationRow+i >= [contentFilters count]) + [contentFilters addObject:draggedRow]; else - [favorites insertObject:draggedRow atIndex:destinationRow+i]; + [contentFilters insertObject:draggedRow atIndex:destinationRow+i]; if(originalRow < row) offset--; } - [favoritesTableView reloadData]; - [favoritesArrayController rearrangeObjects]; + [contentFilterTableView reloadData]; + [contentFilterArrayController rearrangeObjects]; return YES; } @@ -670,26 +704,26 @@ // [favorites removeObjects:[queryFavoritesController arrangedObjects]]; // } // } - if([contextInfo isEqualToString:@"removeSelectedFavorites"]) { + if([contextInfo isEqualToString:@"removeSelectedFilters"]) { if (returnCode == NSAlertAlternateReturn) { - NSIndexSet *indexes = [favoritesTableView selectedRowIndexes]; + NSIndexSet *indexes = [contentFilterTableView selectedRowIndexes]; // get last index NSUInteger currentIndex = [indexes lastIndex]; while (currentIndex != NSNotFound) { - [favorites removeObjectAtIndex:currentIndex]; + [contentFilters removeObjectAtIndex:currentIndex]; // get next index (beginning from the end) currentIndex = [indexes indexLessThanIndex:currentIndex]; } - [favoritesArrayController rearrangeObjects]; - [favoritesTableView reloadData]; + [contentFilterArrayController rearrangeObjects]; + [contentFilterTableView reloadData]; - // Set focus to favorite list to avoid an unstable state - [[self window] makeFirstResponder:favoritesTableView]; + // Set focus to filter list to avoid an unstable state + [[self window] makeFirstResponder:contentFilterTableView]; - [removeButton setEnabled:([favoritesTableView numberOfSelectedRows] > 0)]; + [removeButton setEnabled:([contentFilterTableView numberOfSelectedRows] > 0)]; } } } @@ -727,26 +761,26 @@ return; } - if([spf objectForKey:@"queryFavorites"] && [[spf objectForKey:@"queryFavorites"] count]) { - if([favoritesTableView numberOfSelectedRows] > 0) { - // Insert imported queries after the last selected favorite - NSUInteger insertIndex = [[favoritesTableView selectedRowIndexes] lastIndex] + 1; + if([[spf objectForKey:@"ContentFilters"] objectForKey:filterType] && [[[spf objectForKey:@"ContentFilters"] objectForKey:filterType] count]) { + if([contentFilterTableView numberOfSelectedRows] > 0) { + // Insert imported filters after the last selected filter + NSUInteger insertIndex = [[contentFilterTableView selectedRowIndexes] lastIndex] + 1; NSUInteger i; - for(i=0; i<[[spf objectForKey:@"queryFavorites"] count]; i++) { - [favorites insertObject:[[spf objectForKey:@"queryFavorites"] objectAtIndex:i] atIndex:insertIndex+i]; + for(i=0; i<[[[spf objectForKey:@"ContentFilters"] objectForKey:filterType] count]; i++) { + [contentFilters insertObject:[[spf objectForKey:@"queryFavorites"] objectAtIndex:i] atIndex:insertIndex+i]; } } else { // If no selection add them - [favorites addObjectsFromArray:[spf objectForKey:@"queryFavorites"]]; + [contentFilters addObjectsFromArray:[[spf objectForKey:@"ContentFilters"] objectForKey:filterType]]; } - [favoritesArrayController rearrangeObjects]; - [favoritesTableView reloadData]; + [contentFilterArrayController rearrangeObjects]; + [contentFilterTableView reloadData]; } else { NSAlert *alert = [NSAlert alertWithMessageText:[NSString stringWithFormat:NSLocalizedString(@"Error while reading data file", @"error while reading data file")] defaultButton:NSLocalizedString(@"OK", @"OK button") alternateButton:nil otherButton:nil - informativeTextWithFormat:NSLocalizedString(@"No query favorites found.", @"error that no query favorites found")]; + informativeTextWithFormat:NSLocalizedString(@"No content filters found.", @"error that no content filters found")]; [alert setAlertStyle:NSInformationalAlertStyle]; [alert runModal]; @@ -770,7 +804,7 @@ [prefs setInteger:[[encodingPopUp selectedItem] tag] forKey:@"lastSqlFileEncoding"]; [prefs synchronize]; - [[favoriteQueryTextView string] writeToFile:[panel filename] atomically:YES encoding:[[encodingPopUp selectedItem] tag] error:&error]; + [[contentFilterTextView string] writeToFile:[panel filename] atomically:YES encoding:[[encodingPopUp selectedItem] tag] error:&error]; if (error) [[NSAlert alertWithError:error] runModal]; } @@ -778,24 +812,24 @@ else if([contextInfo isEqualToString:@"exportFavorites"]) { if (returnCode == NSOKButton) { - // Build a SPF with format = "query favorites" + // Build a SPF with format = "content filters" NSMutableDictionary *spfdata = [NSMutableDictionary dictionary]; - NSMutableArray *favoriteData = [NSMutableArray array]; + NSMutableArray *filterData = [NSMutableArray array]; [spfdata setObject:[NSNumber numberWithInt:1] forKey:@"version"]; - [spfdata setObject:@"query favorites" forKey:@"format"]; + [spfdata setObject:@"content filters" forKey:@"format"]; [spfdata setObject:[NSNumber numberWithBool:NO] forKey:@"encrypted"]; - NSIndexSet *indexes = [favoritesTableView selectedRowIndexes]; + NSIndexSet *indexes = [contentFilterTableView selectedRowIndexes]; // Get selected items and preserve the order NSUInteger i; - for (i=1; i<[favorites count]; i++) + for (i=1; i<[contentFilters count]; i++) if([indexes containsIndex:i]) - [favoriteData addObject:[favorites objectAtIndex:i]]; + [filterData addObject:[contentFilters objectAtIndex:i]]; - [spfdata setObject:favoriteData forKey:@"queryFavorites"]; + [spfdata setObject:filterData forKey:@"ContentFilter"]; NSString *err = nil; NSData *plist = [NSPropertyListSerialization dataFromPropertyList:spfdata @@ -803,7 +837,7 @@ errorDescription:&err]; if(err != nil) { - NSAlert *alert = [NSAlert alertWithMessageText:[NSString stringWithFormat:NSLocalizedString(@"Error while converting query favorite data", @"error while converting query favorite data")] + NSAlert *alert = [NSAlert alertWithMessageText:[NSString stringWithFormat:NSLocalizedString(@"Error while converting content filter data", @"error while converting content filter data")] defaultButton:NSLocalizedString(@"OK", @"OK button") alternateButton:nil otherButton:nil @@ -824,9 +858,9 @@ - (void)_initWithNoSelection { - [favoritesTableView selectRowIndexes:[NSIndexSet indexSet] byExtendingSelection:NO]; - [[favoriteNameTextField cell] setPlaceholderString:SP_NO_SELECTION_PLACEHOLDER_STRING]; - [favoriteNameTextField setStringValue:@""]; - [favoriteQueryTextView setString:@""]; + [contentFilterTableView selectRowIndexes:[NSIndexSet indexSet] byExtendingSelection:NO]; + [[contentFilterNameTextField cell] setPlaceholderString:SP_NO_SELECTION_PLACEHOLDER_STRING]; + [contentFilterNameTextField setStringValue:@""]; + [contentFilterTextView setString:@""]; } @end diff --git a/Source/SPQueryFavoriteManager.m b/Source/SPQueryFavoriteManager.m index 202cfa09..590bf3c9 100644 --- a/Source/SPQueryFavoriteManager.m +++ b/Source/SPQueryFavoriteManager.m @@ -195,6 +195,9 @@ NSMutableDictionary *favorite; NSUInteger insertIndex; + // Store pending changes in Query + [[self window] makeFirstResponder:favoriteNameTextField]; + // Duplicate a selected favorite if sender == self if(sender == self) favorite = [NSMutableDictionary dictionaryWithObjects:[NSArray arrayWithObjects:[[favoriteNameTextField stringValue] stringByAppendingFormat:@" Copy"], [favoriteQueryTextView string], nil] forKeys:[NSArray arrayWithObjects:@"name", @"query", nil]]; diff --git a/Source/SPTableView.m b/Source/SPTableView.m index 9a0db4fc..1727494a 100644 --- a/Source/SPTableView.m +++ b/Source/SPTableView.m @@ -51,6 +51,10 @@ if([NSArrayObjectAtIndex([[self delegate] valueForKeyPath:@"favorites"], row) objectForKey:@"headerOfFileURL"]) return nil; } + if([[[[self delegate] class] description] isEqualToString:@"SPContentFilterManager"]) { + if([NSArrayObjectAtIndex([[self delegate] valueForKeyPath:@"contentFilters"], row) objectForKey:@"headerOfFileURL"]) + return nil; + } [self selectRowIndexes:[NSIndexSet indexSetWithIndex:row] byExtendingSelection:NO]; [[self window] makeFirstResponder:self]; diff --git a/Source/TableContent.h b/Source/TableContent.h index e2d7237b..6ecc3a8e 100644 --- a/Source/TableContent.h +++ b/Source/TableContent.h @@ -69,6 +69,8 @@ NSMutableDictionary *contentFilters; NSMutableDictionary *numberOfDefaultFilters; + NSUInteger lastSelectedContentFilterIndex; + id contentFilterManager; BOOL sortColumnToRestoreIsAsc; NSString *sortColumnToRestore; @@ -131,5 +133,6 @@ - (void) clearDetailsToRestore; - (NSString *)escapeFilterArgument:(NSString *)argument againstClause:(NSString *)clause; +- (void)openContentFilterManager; @end diff --git a/Source/TableContent.m b/Source/TableContent.m index 8fcf0454..369cfaec 100644 --- a/Source/TableContent.m +++ b/Source/TableContent.m @@ -45,6 +45,7 @@ #import "SPFieldEditorController.h" #import "SPTooltip.h" #import "RegexKitLite.h" +#import "SPContentFilterManager.h" @implementation TableContent @@ -169,7 +170,7 @@ [countText setStringValue:@""]; // Reset sort column - if (sortCol) [sortCol release], sortCol = nil; + if (sortCol) [sortCol release]; sortCol = nil; isDesc = NO; // Empty and disable filter options @@ -585,7 +586,9 @@ NSMutableString *clause = [[NSMutableString alloc] init]; [clause setString:[filter objectForKey:@"Clause"]]; - [clause replaceOccurrencesOfRegex:@"\\$BINARY" withString:(caseSensitive) ? @"BINARY" : @""]; + [clause replaceOccurrencesOfRegex:@"(?  Please be patient. Under constructions.   " atLocation:[NSEvent mouseLocation] ofType:@"html"]; + return; + + // init query favorites controller + [prefs synchronize]; + if(contentFilterManager) [contentFilterManager release]; + contentFilterManager = [[SPContentFilterManager alloc] initWithDelegate:self forFilterType:compareType]; + + // Open query favorite manager + [NSApp beginSheet:[contentFilterManager window] + modalForWindow:tableWindow + modalDelegate:contentFilterManager + didEndSelector:nil + contextInfo:nil]; +} + - (IBAction)stepLimitRows:(id)sender /* steps the start row up or down (+/- limitRowsValue) -- cgit v1.2.3