More grid filter improvements; add choice/enum/date value renderers.
This commit is contained in:
		
							parent
							
								
									226ca01720
								
							
						
					
					
						commit
						c9b01f6061
					
				
					 2 changed files with 64 additions and 9 deletions
				
			
		|  | @ -43,9 +43,6 @@ class FilterValueRenderer(object): | ||||||
|     Base class for all filter renderers. |     Base class for all filter renderers. | ||||||
|     """ |     """ | ||||||
| 
 | 
 | ||||||
|     def __init__(self, filter=None): |  | ||||||
|         self.filter = filter |  | ||||||
| 
 |  | ||||||
|     @property |     @property | ||||||
|     def name(self): |     def name(self): | ||||||
|         return self.filter.key |         return self.filter.key | ||||||
|  | @ -69,12 +66,40 @@ class NumericValueRenderer(FilterValueRenderer): | ||||||
|     Input renderer for numeric values. |     Input renderer for numeric values. | ||||||
|     """ |     """ | ||||||
| 
 | 
 | ||||||
|  |     def render(self, value=None, **kwargs): | ||||||
|  |         return tags.text(self.name, value=value, type='number', **kwargs) | ||||||
|  | 
 | ||||||
| 
 | 
 | ||||||
| class DateValueRenderer(FilterValueRenderer): | class DateValueRenderer(FilterValueRenderer): | ||||||
|     """ |     """ | ||||||
|     Input renderer for date values. |     Input renderer for date values. | ||||||
|     """ |     """ | ||||||
| 
 | 
 | ||||||
|  |     def render(self, value=None, **kwargs): | ||||||
|  |         return tags.text(self.name, value=value, type='date', **kwargs) | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | class ChoiceValueRenderer(FilterValueRenderer): | ||||||
|  |     """ | ||||||
|  |     Renders value input as a dropdown/selectmenu of available choices. | ||||||
|  |     """ | ||||||
|  | 
 | ||||||
|  |     def __init__(self, choices): | ||||||
|  |         self.choices = choices | ||||||
|  | 
 | ||||||
|  |     def render(self, value=None, **kwargs): | ||||||
|  |         return tags.select(self.name, [value], self.choices, **kwargs) | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | class EnumValueRenderer(ChoiceValueRenderer): | ||||||
|  |     """ | ||||||
|  |     Renders value input as a dropdown/selectmenu of available choices. | ||||||
|  |     """ | ||||||
|  | 
 | ||||||
|  |     def __init__(self, enum): | ||||||
|  |         sorted_keys = sorted(enum, key=lambda k: enum[k].lower()) | ||||||
|  |         self.choices = [(k, enum[k]) for k in sorted_keys] | ||||||
|  | 
 | ||||||
| 
 | 
 | ||||||
| class GridFilter(object): | class GridFilter(object): | ||||||
|     """ |     """ | ||||||
|  | @ -106,11 +131,7 @@ class GridFilter(object): | ||||||
|         self.key = key |         self.key = key | ||||||
|         self.label = label or prettify(key) |         self.label = label or prettify(key) | ||||||
|         self.verbs = verbs or self.get_default_verbs() |         self.verbs = verbs or self.get_default_verbs() | ||||||
|         if value_renderer is not None: |         self.set_value_renderer(value_renderer or self.value_renderer_factory) | ||||||
|             value_renderer.filter = self |  | ||||||
|             self.value_renderer = value_renderer |  | ||||||
|         else: |  | ||||||
|             self.value_renderer = self.value_renderer_factory(self) |  | ||||||
|         self.default_active = default_active |         self.default_active = default_active | ||||||
|         self.default_verb = default_verb |         self.default_verb = default_verb | ||||||
|         self.default_value = default_value |         self.default_value = default_value | ||||||
|  | @ -130,6 +151,15 @@ class GridFilter(object): | ||||||
|             return verbs |             return verbs | ||||||
|         return ['equal', 'not_equal', 'is_null', 'is_not_null'] |         return ['equal', 'not_equal', 'is_null', 'is_not_null'] | ||||||
| 
 | 
 | ||||||
|  |     def set_value_renderer(self, renderer): | ||||||
|  |         """ | ||||||
|  |         Set the value renderer for the filter, post-construction. | ||||||
|  |         """ | ||||||
|  |         if not isinstance(renderer, FilterValueRenderer): | ||||||
|  |             renderer = renderer() | ||||||
|  |         renderer.filter = self | ||||||
|  |         self.value_renderer = renderer | ||||||
|  | 
 | ||||||
|     def filter(self, data, verb=None, value=UNSPECIFIED): |     def filter(self, data, verb=None, value=UNSPECIFIED): | ||||||
|         """ |         """ | ||||||
|         Filter the given data set according to a verb/value pair.  If no verb |         Filter the given data set according to a verb/value pair.  If no verb | ||||||
|  | @ -278,6 +308,7 @@ class AlchemyNumericFilter(AlchemyGridFilter): | ||||||
|     """ |     """ | ||||||
|     Numeric filter for SQLAlchemy. |     Numeric filter for SQLAlchemy. | ||||||
|     """ |     """ | ||||||
|  |     value_renderer_factory = NumericValueRenderer | ||||||
| 
 | 
 | ||||||
|     def default_verbs(self): |     def default_verbs(self): | ||||||
|         """ |         """ | ||||||
|  | @ -314,6 +345,13 @@ class AlchemyDateFilter(AlchemyGridFilter): | ||||||
|     """ |     """ | ||||||
|     value_renderer_factory = DateValueRenderer |     value_renderer_factory = DateValueRenderer | ||||||
| 
 | 
 | ||||||
|  |     def default_verbs(self): | ||||||
|  |         """ | ||||||
|  |         Expose greater-than / less-than verbs in addition to core. | ||||||
|  |         """ | ||||||
|  |         return ['equal', 'not_equal', 'greater_than', 'greater_equal', | ||||||
|  |                 'less_than', 'less_equal', 'is_null', 'is_not_null'] | ||||||
|  | 
 | ||||||
|     def filter_is_true(self, query, value): |     def filter_is_true(self, query, value): | ||||||
|         """ |         """ | ||||||
|         Filter data with an "is true" query (alias for "is not null"). |         Filter data with an "is true" query (alias for "is not null"). | ||||||
|  |  | ||||||
							
								
								
									
										19
									
								
								tailbone/static/js/jquery.ui.tailbone.js
									
										
									
									
										vendored
									
									
								
							
							
						
						
									
										19
									
								
								tailbone/static/js/jquery.ui.tailbone.js
									
										
									
									
										vendored
									
									
								
							|  | @ -250,6 +250,18 @@ | ||||||
|                 } |                 } | ||||||
|             }); |             }); | ||||||
| 
 | 
 | ||||||
|  |             // Enhance any date values with datepicker widget.
 | ||||||
|  |             this.inputs.find('.value input[type="date"]').datepicker({ | ||||||
|  |                 dateFormat: 'yy-mm-dd', | ||||||
|  |                 changeYear: true, | ||||||
|  |                 changeMonth: true | ||||||
|  |             }); | ||||||
|  | 
 | ||||||
|  |             // Enhance any choice/dropdown values with selectmenu.
 | ||||||
|  |             this.inputs.find('.value select').selectmenu({ | ||||||
|  |                 width: '15em' | ||||||
|  |             }); | ||||||
|  | 
 | ||||||
|             // Listen for button click, to keep checkbox in sync.
 |             // Listen for button click, to keep checkbox in sync.
 | ||||||
|             this._on(this.activebutton, { |             this._on(this.activebutton, { | ||||||
|                 click: function(e) { |                 click: function(e) { | ||||||
|  | @ -269,6 +281,11 @@ | ||||||
|         refresh: function() { |         refresh: function() { | ||||||
|             if (this.checkbox.is(':checked')) { |             if (this.checkbox.is(':checked')) { | ||||||
|                 this.activebutton.button('option', 'icons', {primary: 'ui-icon-check'}); |                 this.activebutton.button('option', 'icons', {primary: 'ui-icon-check'}); | ||||||
|  |                 if (this.verb() in this.valueless_verbs) { | ||||||
|  |                     this.inputs.find('.value').hide(); | ||||||
|  |                 } else { | ||||||
|  |                     this.inputs.find('.value').show(); | ||||||
|  |                 } | ||||||
|                 this.inputs.show(); |                 this.inputs.show(); | ||||||
|             } else { |             } else { | ||||||
|                 this.activebutton.button('option', 'icons', {primary: 'ui-icon-blank'}); |                 this.activebutton.button('option', 'icons', {primary: 'ui-icon-blank'}); | ||||||
|  | @ -312,7 +329,7 @@ | ||||||
|         }, |         }, | ||||||
| 
 | 
 | ||||||
|         value: function() { |         value: function() { | ||||||
|             return this.inputs.find('.value input').val(); |             return this.inputs.find('.value input, .value select').val(); | ||||||
|         }, |         }, | ||||||
| 
 | 
 | ||||||
|         verb: function() { |         verb: function() { | ||||||
|  |  | ||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue
	
	 Lance Edgar
						Lance Edgar