datagrid 1.8.1 → 2.0.0.pre.alpha
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/CHANGELOG.md +31 -7
- data/{Readme.markdown → README.md} +46 -29
- data/app/assets/stylesheets/datagrid.css +145 -0
- data/app/views/datagrid/_enum_checkboxes.html.erb +5 -3
- data/app/views/datagrid/_form.html.erb +4 -5
- data/app/views/datagrid/_head.html.erb +26 -3
- data/app/views/datagrid/_range_filter.html.erb +5 -3
- data/app/views/datagrid/_row.html.erb +12 -1
- data/app/views/datagrid/_table.html.erb +4 -4
- data/datagrid.gemspec +8 -8
- data/lib/datagrid/active_model.rb +9 -17
- data/lib/datagrid/base.rb +39 -0
- data/lib/datagrid/column_names_attribute.rb +12 -12
- data/lib/datagrid/columns/column.rb +155 -133
- data/lib/datagrid/columns.rb +495 -282
- data/lib/datagrid/configuration.rb +23 -10
- data/lib/datagrid/core.rb +184 -150
- data/lib/datagrid/deprecated_object.rb +20 -0
- data/lib/datagrid/drivers/abstract_driver.rb +13 -25
- data/lib/datagrid/drivers/active_record.rb +24 -26
- data/lib/datagrid/drivers/array.rb +26 -17
- data/lib/datagrid/drivers/mongo_mapper.rb +15 -14
- data/lib/datagrid/drivers/mongoid.rb +16 -18
- data/lib/datagrid/drivers/sequel.rb +14 -19
- data/lib/datagrid/drivers.rb +2 -1
- data/lib/datagrid/engine.rb +11 -3
- data/lib/datagrid/filters/base_filter.rb +166 -142
- data/lib/datagrid/filters/boolean_filter.rb +19 -5
- data/lib/datagrid/filters/date_filter.rb +33 -35
- data/lib/datagrid/filters/date_time_filter.rb +24 -16
- data/lib/datagrid/filters/default_filter.rb +9 -3
- data/lib/datagrid/filters/dynamic_filter.rb +151 -105
- data/lib/datagrid/filters/enum_filter.rb +43 -19
- data/lib/datagrid/filters/extended_boolean_filter.rb +39 -27
- data/lib/datagrid/filters/float_filter.rb +16 -5
- data/lib/datagrid/filters/integer_filter.rb +21 -10
- data/lib/datagrid/filters/ranged_filter.rb +66 -45
- data/lib/datagrid/filters/select_options.rb +58 -49
- data/lib/datagrid/filters/string_filter.rb +9 -4
- data/lib/datagrid/filters.rb +234 -106
- data/lib/datagrid/form_builder.rb +116 -128
- data/lib/datagrid/generators/scaffold.rb +185 -0
- data/lib/datagrid/generators/views.rb +20 -0
- data/lib/datagrid/helper.rb +397 -22
- data/lib/datagrid/ordering.rb +81 -87
- data/lib/datagrid/rspec.rb +8 -12
- data/lib/datagrid/utils.rb +42 -38
- data/lib/datagrid/version.rb +3 -1
- data/lib/datagrid.rb +18 -28
- data/templates/base.rb.erb +33 -7
- data/templates/grid.rb.erb +1 -1
- metadata +18 -19
- data/app/assets/stylesheets/datagrid.sass +0 -134
- data/lib/datagrid/filters/composite_filters.rb +0 -49
- data/lib/datagrid/renderer.rb +0 -157
- data/lib/datagrid/scaffold.rb +0 -129
- data/lib/tasks/datagrid_tasks.rake +0 -15
- data/templates/controller.rb.erb +0 -6
- data/templates/index.html.erb +0 -5
data/lib/datagrid/helper.rb
CHANGED
@@ -1,9 +1,245 @@
|
|
1
|
-
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
2
3
|
require "action_view"
|
3
4
|
|
4
5
|
module Datagrid
|
6
|
+
# # Datagrid Frontend Guide
|
7
|
+
#
|
8
|
+
# ## Description
|
9
|
+
#
|
10
|
+
# The easiest way to start with Datagrid frontend is by using the generator:
|
11
|
+
#
|
12
|
+
# ``` sh
|
13
|
+
# rails generate datagrid:scaffold users
|
14
|
+
# ```
|
15
|
+
#
|
16
|
+
# This command builds the controller, view, route, and adds
|
17
|
+
# [built-in CSS](https://github.com/bogdan/datagrid/blob/master/app/assets/stylesheets/datagrid.sass).
|
18
|
+
#
|
19
|
+
# Datagrid includes helpers and a form builder for easy frontend generation.
|
20
|
+
# If you need a fully-featured custom GUI, create your templates manually with the help of the {Datagrid::Columns} API.
|
21
|
+
#
|
22
|
+
# ## Controller and Routing
|
23
|
+
#
|
24
|
+
# Grids usually implement the `index` action of a Rails REST resource. Here's an example:
|
25
|
+
#
|
26
|
+
# resources :models, only: [:index]
|
27
|
+
#
|
28
|
+
# Use the `GET` method in the form, and the controller becomes straightforward:
|
29
|
+
#
|
30
|
+
# class ModelsController < ApplicationController
|
31
|
+
# def index
|
32
|
+
# @grid = ModelsGrid.new(params[:my_report]) do |scope|
|
33
|
+
# scope.page(params[:page]) # See pagination section
|
34
|
+
# end
|
35
|
+
# end
|
36
|
+
# end
|
37
|
+
#
|
38
|
+
# To apply additional scoping conditions, such as visibility based on the current user:
|
39
|
+
#
|
40
|
+
# ModelsGrid.new(params[:my_report]) do |scope|
|
41
|
+
# scope.where(owner_id: current_user.id).page(params[:page])
|
42
|
+
# end
|
43
|
+
#
|
44
|
+
# To pass an object to a grid instance, define it as an accessible attribute:
|
45
|
+
#
|
46
|
+
# class ModelsGrid
|
47
|
+
# attr_accessor :current_user
|
48
|
+
# end
|
49
|
+
#
|
50
|
+
# Then pass it when initializing the grid:
|
51
|
+
#
|
52
|
+
# ModelsGrid.new(params[:models_grid].merge(current_user: current_user))
|
53
|
+
#
|
54
|
+
# ## Form Builder
|
55
|
+
#
|
56
|
+
# ### Basic Method
|
57
|
+
#
|
58
|
+
# Use the built-in partial:
|
59
|
+
#
|
60
|
+
# = datagrid_form_with model: @grid, url: report_path, other_form_for_option: value
|
61
|
+
#
|
62
|
+
# {#datagrid_form_with} supports the same options as Rails `form_with`.
|
63
|
+
#
|
64
|
+
# ### Advanced Method
|
65
|
+
#
|
66
|
+
# You can use Rails built-in tools to create a form. Additionally, Datagrid provides helpers to generate input/select elements for filters:
|
67
|
+
#
|
68
|
+
# ``` haml
|
69
|
+
# - form_with model: UserGrid.new, method: :get, url: users_path do |f|
|
70
|
+
# %div
|
71
|
+
# = f.datagrid_label :name
|
72
|
+
# = f.datagrid_filter :name # => <input name="grid[name]" type="text"/>
|
73
|
+
# %div
|
74
|
+
# = f.datagrid_label :category_id
|
75
|
+
# = f.datagrid_filter :category_id # => <select name="grid[category_id]">....</select>
|
76
|
+
# ```
|
77
|
+
#
|
78
|
+
# For more flexibility, use Rails default helpers:
|
79
|
+
#
|
80
|
+
# %div
|
81
|
+
# = f.label :name
|
82
|
+
# = f.text_field :name
|
83
|
+
#
|
84
|
+
# See the localization section of {Datagrid::Filters}.
|
85
|
+
#
|
86
|
+
# ## Datagrid Table
|
87
|
+
#
|
88
|
+
# Use the helper to display a report:
|
89
|
+
#
|
90
|
+
# %div== Total #{@grid.assets.total}
|
91
|
+
# = datagrid_table(@report)
|
92
|
+
# = will_paginate @report.assets
|
93
|
+
#
|
94
|
+
# Options:
|
95
|
+
#
|
96
|
+
# - `:html` - Attributes for the `<table>` tag.
|
97
|
+
# - `:order` - Set to `false` to disable ordering controls (default: `true`).
|
98
|
+
# - `:columns` - Specify an array of column names to display.
|
99
|
+
#
|
100
|
+
# ## Pagination
|
101
|
+
#
|
102
|
+
# Datagrid is abstracted from pagination but integrates seamlessly with tools like Kaminari, WillPaginate, or Pagy:
|
103
|
+
#
|
104
|
+
# # Kaminari
|
105
|
+
# @grid = MyGrid.new(params[:grid]) do |scope|
|
106
|
+
# scope.page(params[:page]).per(10)
|
107
|
+
# end
|
108
|
+
#
|
109
|
+
# # WillPaginate
|
110
|
+
# @grid = MyGrid.new(params[:grid]) do |scope|
|
111
|
+
# scope.page(params[:page]).per_page(10)
|
112
|
+
# end
|
113
|
+
#
|
114
|
+
# # Pagy
|
115
|
+
# @grid = MyGrid.new(params[:grid])
|
116
|
+
# @pagy, @records = pagy(@grid.assets)
|
117
|
+
#
|
118
|
+
# Render the paginated collection:
|
119
|
+
#
|
120
|
+
# # WillPaginate or Kaminari
|
121
|
+
# <%= datagrid_table(@grid, options) %>
|
122
|
+
# # Pagy
|
123
|
+
# <%= datagrid_table(@grid, @records, options) %>
|
124
|
+
#
|
125
|
+
# ## CSV Export
|
126
|
+
#
|
127
|
+
# Add CSV support to your controller:
|
128
|
+
#
|
129
|
+
# class UsersController < ApplicationController
|
130
|
+
# def index
|
131
|
+
# @grid = UsersGrid.new(params[:users_grid])
|
132
|
+
# respond_to do |f|
|
133
|
+
# f.html { @grid.scope { |scope| scope.page(params[:page]) } }
|
134
|
+
# f.csv do
|
135
|
+
# send_data @grid.to_csv, type: "text/csv", disposition: 'inline', filename: "grid-#{Time.now.to_s}.csv"
|
136
|
+
# end
|
137
|
+
# end
|
138
|
+
# end
|
139
|
+
# end
|
140
|
+
#
|
141
|
+
# Add a button in your interface:
|
142
|
+
#
|
143
|
+
# link_to "Get CSV", url_for(format: 'csv', users_grid: params[:users_grid])
|
144
|
+
#
|
145
|
+
# ## AJAX
|
146
|
+
#
|
147
|
+
# Datagrid supports asynchronous data loading. Add this to your controller:
|
148
|
+
#
|
149
|
+
# if request.xhr?
|
150
|
+
# render json: {table: view_context.datagrid_table(@grid)}
|
151
|
+
# end
|
152
|
+
#
|
153
|
+
# Modify the form for AJAX:
|
154
|
+
#
|
155
|
+
# = datagrid_form_with model: @grid, html: {class: 'js-datagrid-form'}
|
156
|
+
# .js-datagrid-table
|
157
|
+
# = datagrid_table @grid
|
158
|
+
# .js-pagination
|
159
|
+
# = paginate @grid.assets
|
160
|
+
# :javascript
|
161
|
+
# $('.js-datagrid-form').submit(function(event) {
|
162
|
+
# event.preventDefault();
|
163
|
+
# $.get($(this).attr("action"), $(this).serialize(), function (data) {
|
164
|
+
# $('.js-datagrid-table').html(data.table);
|
165
|
+
# });
|
166
|
+
# });
|
167
|
+
#
|
168
|
+
# ## Modifying Built-In Partials
|
169
|
+
#
|
170
|
+
# To customize Datagrid views:
|
171
|
+
#
|
172
|
+
# rake datagrid:copy_partials
|
173
|
+
#
|
174
|
+
# This creates files in `app/views/datagrid/`, which you can modify to suit your needs:
|
175
|
+
#
|
176
|
+
# app/views/datagrid/
|
177
|
+
# ├── _enum_checkboxes.html.erb # datagrid_filter for filter(name, :enum, checkboxes: true)
|
178
|
+
# ├── _form.html.erb # datagrid_form_with
|
179
|
+
# ├── _head.html.erb # datagrid_header
|
180
|
+
# ├── _range_filter.html.erb # datagrid_filter for filter(name, type, range: true)
|
181
|
+
# ├── _row.html.erb # datagrid_rows/datagrid_rows
|
182
|
+
# └── _table.html.erb # datagrid_table
|
183
|
+
#
|
184
|
+
# ## Custom Options
|
185
|
+
#
|
186
|
+
# You can add custom options to Datagrid columns and filters and implement their support on the frontend.
|
187
|
+
# For example, you might want to add a `description` option to a column that appears as a tooltip on mouseover.
|
188
|
+
#
|
189
|
+
# column(
|
190
|
+
# :aov, header: 'AOV',
|
191
|
+
# description: 'Average order value: sum of orders subtotal divided by their count'
|
192
|
+
# ) do |category|
|
193
|
+
# category.orders.sum(:subtotal) / category.orders.count
|
194
|
+
# end
|
195
|
+
#
|
196
|
+
# The `:description` option is not built into Datagrid, but you can implement it
|
197
|
+
# by adding the following to partial `app/views/datagrid/_header.html.erb`:
|
198
|
+
#
|
199
|
+
# <% if column.options[:description] %>
|
200
|
+
# <a data-toggle="tooltip" title="<%= column.options[:description] %>">
|
201
|
+
# <i class="icon-question-sign"></i>
|
202
|
+
# </a>
|
203
|
+
# <% end %>
|
204
|
+
#
|
205
|
+
# This modification allows the `:description` tooltip to work with your chosen UI and JavaScript library.
|
206
|
+
# The same technique can be applied to filters by calling `filter.options` in corresponding partials.
|
207
|
+
#
|
208
|
+
# ## Highlight Rows
|
209
|
+
#
|
210
|
+
# To add custom HTML classes to each row for styling, modify the `_row.html.erb` partial:
|
211
|
+
#
|
212
|
+
# ``` diff
|
213
|
+
# -<tr>
|
214
|
+
# +<tr class="<%= grid.respond_to?(:row_class) ? grid.row_class(asset) : "" %>">
|
215
|
+
# <% grid.html_columns(*options[:columns]).each do |column| %>
|
216
|
+
# <td class="<%= datagrid_column_classes(grid, column) %>">
|
217
|
+
# <%= datagrid_value(grid, column, asset) %>
|
218
|
+
# </td>
|
219
|
+
# <% end %>
|
220
|
+
# ```
|
221
|
+
#
|
222
|
+
# This allows you to define a custom `row_class` method in your grid class, like this:
|
223
|
+
#
|
224
|
+
# class IssuesGrid < ApplicationGrid
|
225
|
+
# scope { Issue }
|
226
|
+
#
|
227
|
+
# def row_class(issue)
|
228
|
+
# case issue.status
|
229
|
+
# when "fixed" then "green"
|
230
|
+
# when "rejected" then "red"
|
231
|
+
# else "blue"
|
232
|
+
# end
|
233
|
+
# end
|
234
|
+
# end
|
235
|
+
#
|
236
|
+
# ## Localization
|
237
|
+
#
|
238
|
+
# You can overwrite Datagrid’s custom localization keys at the application level.
|
239
|
+
# See the localization keys here:
|
240
|
+
#
|
241
|
+
# https://github.com/bogdan/datagrid/blob/master/lib/datagrid/locale/en.yml
|
5
242
|
module Helper
|
6
|
-
|
7
243
|
# @param grid [Datagrid] grid object
|
8
244
|
# @param column [Datagrid::Columns::Column, String, Symbol] column name
|
9
245
|
# @param model [Object] an object from grid scope
|
@@ -15,7 +251,9 @@ module Datagrid
|
|
15
251
|
# <% end %>
|
16
252
|
# </ul>
|
17
253
|
def datagrid_value(grid, column, model)
|
18
|
-
|
254
|
+
column = grid.column_by_name(column) if column.is_a?(String) || column.is_a?(Symbol)
|
255
|
+
|
256
|
+
grid.html_value(column, self, model)
|
19
257
|
end
|
20
258
|
|
21
259
|
# @!visibility private
|
@@ -38,12 +276,20 @@ module Datagrid
|
|
38
276
|
# Default: 'datagrid'.
|
39
277
|
# @param grid [Datagrid] grid object
|
40
278
|
# @param assets [Array] objects from grid scope
|
279
|
+
# @param [Hash{Symbol => Object}] options HTML attributes to be passed to `<table>` tag
|
41
280
|
# @return [String] table tag HTML markup
|
42
281
|
# @example
|
43
282
|
# assets = grid.assets.page(params[:page])
|
44
283
|
# datagrid_table(grid, assets, options)
|
45
284
|
def datagrid_table(grid, assets = grid.assets, **options)
|
46
|
-
|
285
|
+
_render_partial(
|
286
|
+
"table", options[:partials],
|
287
|
+
{
|
288
|
+
grid: grid,
|
289
|
+
options: options,
|
290
|
+
assets: assets,
|
291
|
+
},
|
292
|
+
)
|
47
293
|
end
|
48
294
|
|
49
295
|
# Renders HTML table header for given grid instance using columns defined in it
|
@@ -58,11 +304,19 @@ module Datagrid
|
|
58
304
|
# * <tt>:partials</tt> - Path for partials lookup.
|
59
305
|
# Default: 'datagrid'.
|
60
306
|
# @param grid [Datagrid] grid object
|
307
|
+
# @param [Object] opts (deprecated) pass keyword arguments instead
|
308
|
+
# @param [Hash] options
|
61
309
|
# @return [String] HTML table header tag markup
|
62
|
-
def datagrid_header(grid,
|
63
|
-
|
64
|
-
|
310
|
+
def datagrid_header(grid, opts = :__unspecified__, **options)
|
311
|
+
unless opts == :__unspecified__
|
312
|
+
Datagrid::Utils.warn_once("datagrid_header now requires ** operator when passing options.")
|
313
|
+
options.reverse_merge!(opts)
|
314
|
+
end
|
315
|
+
options[:order] = true unless options.key?(:order)
|
65
316
|
|
317
|
+
_render_partial("head", options[:partials],
|
318
|
+
{ grid: grid, options: options },)
|
319
|
+
end
|
66
320
|
|
67
321
|
# Renders HTML table rows using given grid definition using columns defined in it.
|
68
322
|
# Allows to provide a custom layout for each for in place with a block
|
@@ -75,6 +329,7 @@ module Datagrid
|
|
75
329
|
# * <tt>:partials</tt> - Path for partials lookup.
|
76
330
|
# Default: 'datagrid'.
|
77
331
|
#
|
332
|
+
# @return [String]
|
78
333
|
# @example
|
79
334
|
# = datagrid_rows(grid) # Generic table rows Layout
|
80
335
|
#
|
@@ -83,30 +338,73 @@ module Datagrid
|
|
83
338
|
# %td= row.project_name
|
84
339
|
# %td.project-status{class: row.status}= row.status
|
85
340
|
def datagrid_rows(grid, assets = grid.assets, **options, &block)
|
86
|
-
|
341
|
+
safe_join(
|
342
|
+
assets.map do |asset|
|
343
|
+
datagrid_row(grid, asset, **options, &block)
|
344
|
+
end.to_a,
|
345
|
+
)
|
87
346
|
end
|
88
347
|
|
89
|
-
#
|
348
|
+
# @return [String] renders ordering controls for the given column name
|
90
349
|
#
|
91
350
|
# Supported options:
|
92
351
|
#
|
93
352
|
# * <tt>:partials</tt> - Path for partials lookup.
|
94
353
|
# Default: 'datagrid'.
|
95
354
|
def datagrid_order_for(grid, column, options = {})
|
96
|
-
|
355
|
+
Datagrid::Utils.warn_once(<<~MSG)
|
356
|
+
datagrid_order_for is deprecated.
|
357
|
+
Put necessary code inline inside datagrid/head partial.
|
358
|
+
See built-in partial for example.
|
359
|
+
MSG
|
360
|
+
_render_partial("order_for", options[:partials],
|
361
|
+
{ grid: grid, column: column },)
|
362
|
+
end
|
363
|
+
|
364
|
+
# Renders HTML for grid with all filters inputs and labels defined in it
|
365
|
+
#
|
366
|
+
# Supported options:
|
367
|
+
#
|
368
|
+
# * <tt>:partials</tt> - Path for form partial lookup.
|
369
|
+
# Default: 'datagrid' results in using `app/views/datagrid/` partials.
|
370
|
+
# Example: 'datagrid_admin' results in using `app/views/datagrid_admin` partials.
|
371
|
+
# * <tt>:model</tt> - Datagrid object to be rendedred.
|
372
|
+
# * All options supported by Rails <tt>form_with</tt> helper
|
373
|
+
# @param grid [Datagrid] grid object
|
374
|
+
# @param [Hash{Symbol => Object}] options
|
375
|
+
# @return [String] form HTML tag markup
|
376
|
+
def datagrid_form_with(**options)
|
377
|
+
raise ArgumentError, "datagrid_form_with block argument is invalid. Use form_with instead." if block_given?
|
378
|
+
|
379
|
+
grid = options[:model]
|
380
|
+
raise ArgumentError, "Grid has no available filters" if grid&.filters&.empty?
|
381
|
+
|
382
|
+
_render_partial("form", options[:partials], { grid: options[:model], options: options })
|
97
383
|
end
|
98
384
|
|
99
|
-
# Renders HTML for
|
385
|
+
# Renders HTML for grid with all filters inputs and labels defined in it
|
100
386
|
#
|
101
387
|
# Supported options:
|
102
388
|
#
|
103
389
|
# * <tt>:partials</tt> - Path for form partial lookup.
|
104
390
|
# Default: 'datagrid'.
|
105
|
-
# * All options supported by Rails <tt>
|
391
|
+
# * All options supported by Rails <tt>form_with</tt> helper
|
392
|
+
# @deprecated Use {#datagrid_form_with} instead.
|
106
393
|
# @param grid [Datagrid] grid object
|
394
|
+
# @param [Hash] options
|
107
395
|
# @return [String] form HTML tag markup
|
108
396
|
def datagrid_form_for(grid, options = {})
|
109
|
-
|
397
|
+
Datagrid::Utils.warn_once("datagrid_form_for is deprecated if favor of datagrid_form_with.")
|
398
|
+
_render_partial(
|
399
|
+
"form", options[:partials],
|
400
|
+
grid: grid,
|
401
|
+
options: {
|
402
|
+
method: :get,
|
403
|
+
as: grid.param_name,
|
404
|
+
local: true,
|
405
|
+
**options,
|
406
|
+
},
|
407
|
+
)
|
110
408
|
end
|
111
409
|
|
112
410
|
# Provides access to datagrid columns data.
|
@@ -114,6 +412,7 @@ module Datagrid
|
|
114
412
|
# @param grid [Datagrid] grid object
|
115
413
|
# @param asset [Object] object from grid scope
|
116
414
|
# @param block [Proc] block with Datagrid::Helper::HtmlRow as an argument returning a HTML markup as a String
|
415
|
+
# @param [Hash{Symbol => Object}] options
|
117
416
|
# @return [Datagrid::Helper::HtmlRow, String] captured HTML markup if block given otherwise row object
|
118
417
|
# @example
|
119
418
|
# # Suppose that grid has first_name and last_name columns
|
@@ -130,29 +429,105 @@ module Datagrid
|
|
130
429
|
# @example
|
131
430
|
# <%= datagrid_row(grid, user, columns: [:first_name, :last_name, :actions]) %>
|
132
431
|
def datagrid_row(grid, asset, **options, &block)
|
133
|
-
|
432
|
+
Datagrid::Helper::HtmlRow.new(self, grid, asset, options).tap do |row|
|
433
|
+
return capture(row, &block) if block_given?
|
434
|
+
end
|
134
435
|
end
|
135
436
|
|
136
437
|
# Generates an ascending or descending order url for the given column
|
137
438
|
# @param grid [Datagrid] grid object
|
138
439
|
# @param column [Datagrid::Columns::Column, String, Symbol] column name
|
139
|
-
# @param descending [Boolean]
|
440
|
+
# @param descending [Boolean] order direction, descending if true, otherwise ascending.
|
140
441
|
# @return [String] order layout HTML markup
|
141
442
|
def datagrid_order_path(grid, column, descending)
|
142
|
-
|
443
|
+
column = grid.column_by_name(column)
|
444
|
+
query = request&.query_parameters || {}
|
445
|
+
ActionDispatch::Http::URL.path_for(
|
446
|
+
path: request&.path || "/",
|
447
|
+
params: query.merge(grid.query_params(order: column.name, descending: descending)),
|
448
|
+
)
|
143
449
|
end
|
144
450
|
|
451
|
+
# @!visibility private
|
452
|
+
def datagrid_column_classes(grid, column)
|
453
|
+
Datagrid::Utils.warn_once(<<~MSG)
|
454
|
+
datagrid_column_classes is deprecated. Assign necessary classes manually.
|
455
|
+
Correspond to default datagrid/rows partial for example.)
|
456
|
+
MSG
|
457
|
+
column = grid.column_by_name(column)
|
458
|
+
order_class = if grid.ordered_by?(column)
|
459
|
+
["ordered", grid.descending ? "desc" : "asc"]
|
460
|
+
end
|
461
|
+
class_names(column.name, order_class, column.options[:class], column.tag_options[:class])
|
462
|
+
end
|
145
463
|
|
146
464
|
protected
|
147
465
|
|
148
|
-
def
|
149
|
-
|
466
|
+
def _render_partial(partial_name, partials_path, locals = {})
|
467
|
+
render({
|
468
|
+
partial: File.join(partials_path || "datagrid", partial_name),
|
469
|
+
locals: locals,
|
470
|
+
})
|
150
471
|
end
|
151
472
|
|
152
|
-
|
153
|
-
|
154
|
-
|
473
|
+
# Represents a datagrid row that provides access to column values for the given asset
|
474
|
+
# @example
|
475
|
+
# row = datagrid_row(grid, user)
|
476
|
+
# row.class # => Datagrid::Helper::HtmlRow
|
477
|
+
# row.first_name # => "<strong>Bogdan</strong>"
|
478
|
+
# row.grid # => Grid object
|
479
|
+
# row.asset # => User object
|
480
|
+
# row.each do |value|
|
481
|
+
# puts value
|
482
|
+
# end
|
483
|
+
class HtmlRow
|
484
|
+
include Enumerable
|
485
|
+
|
486
|
+
attr_reader :grid, :asset, :options
|
487
|
+
|
488
|
+
# @!visibility private
|
489
|
+
def initialize(renderer, grid, asset, options)
|
490
|
+
@renderer = renderer
|
491
|
+
@grid = grid
|
492
|
+
@asset = asset
|
493
|
+
@options = options
|
494
|
+
end
|
495
|
+
|
496
|
+
# @return [Object] a column value for given column name
|
497
|
+
def get(column)
|
498
|
+
@renderer.datagrid_value(@grid, column, @asset)
|
499
|
+
end
|
500
|
+
|
501
|
+
# Iterates over all column values that are available in the row
|
502
|
+
# param block [Proc] column value iterator
|
503
|
+
def each(&block)
|
504
|
+
(@options[:columns] || @grid.html_columns).each do |column|
|
505
|
+
block.call(get(column))
|
506
|
+
end
|
507
|
+
end
|
508
|
+
|
509
|
+
# @return [String] HTML row format
|
510
|
+
def to_s
|
511
|
+
@renderer.send(:_render_partial, "row", options[:partials], {
|
512
|
+
grid: grid,
|
513
|
+
options: options,
|
514
|
+
asset: asset,
|
515
|
+
},)
|
516
|
+
end
|
517
|
+
|
518
|
+
protected
|
519
|
+
|
520
|
+
def method_missing(method, *args, &blk)
|
521
|
+
if (column = @grid.column_by_name(method))
|
522
|
+
get(column)
|
523
|
+
else
|
524
|
+
super
|
525
|
+
end
|
526
|
+
end
|
527
|
+
|
528
|
+
def respond_to_missing?(method, include_private = false)
|
529
|
+
!!@grid.column_by_name(method) || super
|
530
|
+
end
|
155
531
|
end
|
156
532
|
end
|
157
533
|
end
|
158
|
-
|