Module: Wice::GridViewHelper

Defined in:
lib/helpers/wice_grid_view_helpers.rb,
lib/helpers/wice_grid_misc_view_helpers.rb,
lib/helpers/wice_grid_serialized_queries_view_helpers.rb

Instance Method Summary collapse

Instance Method Details

:nodoc:


749
750
751
752
753
754
755
756
757
758
759
760
# File 'lib/helpers/wice_grid_view_helpers.rb', line 749

def back_to_pagination_link(parameters, grid_name) #:nodoc:
  pagination_override_parameter_name = "#{grid_name}[pp]"
  parameters = parameters.reject{|k, v| k == pagination_override_parameter_name}

  js =  JsAdaptor.back_to_pagination_link_initialization(grid_name, parameters.to_json)

  tooltip = WiceGridNlMessageProvider.get_message(:SWITCH_BACK_TO_PAGINATED_MODE_TOOLTIP)
  html = %/ <span class="show_all_link"><a href="#" title="#{tooltip}">/ +
    WiceGridNlMessageProvider.get_message(:SWITCH_BACK_TO_PAGINATED_MODE_LABEL) +
    '</a></span>'
  [html, js]
end

#call_block_as_erb_or_ruby(rendering, block, ar) ⇒ Object

:nodoc:


217
218
219
220
221
222
223
# File 'lib/helpers/wice_grid_view_helpers.rb', line 217

def call_block_as_erb_or_ruby(rendering, block, ar)  #:nodoc:
  if rendering.erb_mode
    capture(ar, &block)
  else
    block.call(ar)
  end
end

#dump_filter_parameters_as_hidden_fields(grid) ⇒ Object

This method dumps all HTTP parameters related to filtering and ordering of a certain grid as hidden form fields. This might be required if you want to keep the state of a grid while reloading the page using other forms.

The only parameter is a grid object returned by initialize_grid in the controller.


10
11
12
13
14
15
16
17
18
# File 'lib/helpers/wice_grid_misc_view_helpers.rb', line 10

def dump_filter_parameters_as_hidden_fields(grid)
  unless grid.kind_of? WiceGrid
    raise WiceGridArgumentError.new("dump_filter_parameters_as_hidden_fields: the parameter must be a WiceGrid instance.")
  end

  grid.get_state_as_parameter_value_pairs(true).collect{|param_name, value|
    hidden_field_tag(param_name, value, :id => "hidden-#{param_name.gsub(/[\[\]]/, '-')}")
  }.join("\n").html_safe_if_necessary
end

#dump_state(grid) ⇒ Object

:nodoc:


20
21
22
# File 'lib/helpers/wice_grid_misc_view_helpers.rb', line 20

def dump_state(grid)  #:nodoc:
  debug(grid.get_state_as_parameter_value_pairs)
end

#export_to_csv_javascript(grid) ⇒ Object

Returns javascript which triggers export to CSV. The parameter is a WiceGrid instance. Use it with button_to_function to create your own Export To CSV button.


679
680
681
682
683
684
# File 'lib/helpers/wice_grid_view_helpers.rb', line 679

def export_to_csv_javascript(grid)
  unless grid.kind_of? WiceGrid
    raise WiceGridArgumentError.new("export_csv_javascript: the parameter must be a WiceGrid instance.")
  end
  "#{grid.name}.export_to_csv()"
end

#generate_blank_slate(grid, rendering) ⇒ Object

:nodoc:


198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
# File 'lib/helpers/wice_grid_view_helpers.rb', line 198

def generate_blank_slate(grid, rendering) #:nodoc:
  buff = GridOutputBuffer.new

  buff <<  if rendering.blank_slate_handler.is_a?(Proc)
    call_block_as_erb_or_ruby(rendering, rendering.blank_slate_handler, nil)
  elsif rendering.blank_slate_handler.is_a?(Hash)
    render(rendering.blank_slate_handler)
  else
    rendering.blank_slate_handler
  end

  if rendering.find_one_for(:in_html){|column| column.detach_with_id}
    buff.stubborn_output_mode = true
    buff.return_empty_strings_for_nonexistent_filters = true
    grid.output_buffer   = buff
  end
  buff
end

#grid(grid, opts = {}, &block) ⇒ Object

View helper for rendering the grid.

The first parameter is a grid object returned by initialize_grid in the controller.

The second parameter is a hash of options:

  • :table_html_attrs - a hash of HTML attributes to be included into the table tag.

  • :class - a shortcut for :table_html_attrs => {:class => 'css_class'}

  • :header_tr_html_attrs - a hash of HTML attributes to be included into the first tr tag (or two first tr's if the filter row is present).

  • :show_filters - defines when the filter is shown. Possible values are:

    • :when_filtered - the filter is shown when the current table is the result of filtering

    • :always or true - show the filter always

    • :no or false - never show the filter

  • :upper_pagination_panel - a boolean value which defines whether there is an additional pagination panel on top of the table. By default it is false.

  • :extra_request_parameters - a hash which will be added as additional HTTP request parameters to all links generated by the grid, be it sorting links, filters, or the 'Reset Filter' icon. Please note that WiceGrid respects and retains all request parameters already present in the URL which formed the page, so there is no need to enumerate them in :extra_request_parameters. A typical usage of :extra_request_parameters is a page with javascript tabs - changing the active tab does not reload the page, but if one such tab contains a WiceGrid, it could be required that if the user orders or filters the grid, the result page should have the tab with the grid activated. For this we need to send an additional parameter specifying from which tab the request was generated.

  • :sorting_dependant_row_cycling - When set to true (by default it is false) the row styles odd and even will be changed only when the content of the cell belonging to the sorted column changes. In other words, rows with identical values in the ordered column will have the same style (color).

  • :erb_mode - can be true or false. Defines the style of the helper method in the view. The default is false.

  • :allow_showing_all_records - allow or prohibit the “All Records” mode.

  • :hide_reset_button - Do not show the default Filter Reset button. Useful when using a custom reset button (helper reset_grid_javascript). By default it is false.

  • :hide_submit_button - Do not show the default Filter Submit button. Useful when using a custom submit button (helper submit_grid_javascript). By default it is false.

  • :hide_csv_button - a boolean value which defines whether the default Export To CSV button should be rendered. Useful when using a custom Export To CSV button (helper export_to_csv_javascript). By default it is false. Please read README for more insights.

The block contains definitions of grid columns using the column method sent to the object yielded into the block. In other words, the value returned by each of the blocks defines the content of a cell, the first block is called for cells of the first column for each row (each ActiveRecord instance), the second block is called for cells of the second column, and so on. See the example:

<%= grid(@accounts_grid, :table_html_attrs => {:class => 'grid_style', :id => 'accounts_grid'}, :header_tr_html_attrs => {:class => 'grid_headers'}) do |g|

  g.column :column_name => 'Username', :attribute_name => 'username' do ||
    .username
  end

  g.column :column_name => 'application_account.field.identity_id'._, :attribute_name => 'firstname', :model_class =>  Person do ||
    link_to(.identity.name, identity_path(.identity))
  end

  g.column do ||
    link_to('Edit', ())
  end

end -%>

The helper may have two styles defined by the erb_mode parameter to the initialize_grid in the contoller. By default (erb_mode = false) this is a simple helper surrounded by <%= and %>:

<%= grid(@countries_grid) do |g|

  g.column :column_name => 'Name', :attribute_name => 'name' do |country|
    link_to(country.name, country_path(country))
  end

  g.column :column_name => 'Numeric Code', :attribute_name => 'numeric_code' do |country|
    country.numeric_code
  end

end -%>

The second style (erb_mode = true) is called ERB mode and it allows to embed any ERB content inside blocks, which is basically the style of the form_for helper, only form_for takes one block, while inside the grid block there are other method calls taking blocks as parameters:

<% grid(@countries_grid) do |g|

  <% g.column :column_name => 'Name', :attribute_name => 'name' do |country| %>
    <b>Name: <%= link_to(country.name, country_path(country)) %></b>
  <% end %>

  <% g.column :column_name => 'Numeric Code', :attribute_name => 'numeric_code' do |country| %>
    <i>Numeric Code: <%= country.numeric_code %></i>
  <% end %>

<% end -%>

This mode can be usable if you like to have much HTML code inside cells.

Please remember that in this mode the helper opens with <% instead of <%=, similar to form_for.

Defaults for parameters :show_filters and :upper_pagination_panel can be changed in lib/wice_grid_config.rb using constants Wice::Defaults::SHOW_FILTER and WiceGrid::Defaults::SHOW_UPPER_PAGINATION_PANEL, this is convenient if you want to set a project wide setting without having to repeat it for every grid instance.

Pease read documentation about the column method to achieve the enlightenment.


111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
# File 'lib/helpers/wice_grid_view_helpers.rb', line 111

def grid(grid, opts = {}, &block)
  unless grid.class == WiceGrid
    raise WiceGridArgumentError.new("The first argument for the grid helper must be an instance of the WiceGrid class")
  end

  if grid.output_buffer
    if grid.output_buffer == true
      raise  WiceGridException.new("Second occurence of grid helper with the same grid object. " +
                            "Did you intend to use detached filters and forget to define them?")
    else
      return grid.output_buffer
    end
  end

  options = {
    :allow_showing_all_records     => Defaults::ALLOW_SHOWING_ALL_QUERIES,
    :class                         => nil,
    :erb_mode                      => Defaults::ERB_MODE,
    :extra_request_parameters      => {},
    :header_tr_html_attrs          => {},
    :hide_reset_button             => false,
    :hide_submit_button            => false,
    :hide_csv_button               => false,
    :show_filters                  => Defaults::SHOW_FILTER,
    :sorting_dependant_row_cycling => false,
    :table_html_attrs              => {},
    :upper_pagination_panel        => Defaults::SHOW_UPPER_PAGINATION_PANEL
  }

  opts.assert_valid_keys(options.keys)

  options.merge!(opts)

  options[:show_filters] = :no     if options[:show_filters] == false
  options[:show_filters] = :always if options[:show_filters] == true

  options[:table_html_attrs].add_or_append_class_value!('wice_grid', true)

  if options[:class]
    options[:table_html_attrs].add_or_append_class_value!(options[:class])
    options.delete(:class)
  end

  rendering = GridRenderer.new(grid, self)
  rendering.erb_mode = options[:erb_mode]

  block.call(rendering) # calling block containing column() calls

  reuse_last_column_for_filter_buttons =
    Defaults::REUSE_LAST_COLUMN_FOR_FILTER_ICONS && rendering.last_column_for_html.capable_of_hosting_filter_related_icons?

  if grid.output_csv?
    content = grid_csv(grid, rendering)
  else
    # If blank_slate is defined we don't show any grid at all
    if rendering.blank_slate_handler &&  grid.resultset.size == 0 && ! grid.filtering_on?
      content = generate_blank_slate(grid, rendering)
      return prepare_result(rendering, grid, content, block)
    end

    content = grid_html(grid, options, rendering, reuse_last_column_for_filter_buttons)
  end

  grid.view_helper_finished = true
  prepare_result(rendering, grid, content, block)
end

#grid_csv(grid, rendering) ⇒ Object

:nodoc:


687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
# File 'lib/helpers/wice_grid_view_helpers.rb', line 687

def grid_csv(grid, rendering) #:nodoc:


  field_separator = (grid.export_to_csv_enabled && grid.export_to_csv_enabled.is_a?(String)) ? grid.export_to_csv_enabled : ','
  spreadsheet = ::Wice::Spreadsheet.new(grid.name, field_separator)

  # columns
  spreadsheet << rendering.column_labels(:in_csv)

  # rendering  rows
  grid.each do |ar| # rows
    row = []

    rendering.each_column(:in_csv) do |column|
      cell_block = column.cell_rendering_block

      column_block_output = call_block_as_erb_or_ruby(rendering, cell_block, ar)

      if column_block_output.kind_of?(Array)
        column_block_output, additional_opts = column_block_output
      end

      row << column_block_output
    end
    spreadsheet << row
  end
  grid.csv_tempfile = spreadsheet.tempfile
  return grid.csv_tempfile.path
end

#grid_filter(grid, filter_key) ⇒ Object

Renders a detached filter. The parameters are:

  • grid the WiceGrid object

  • filter_key an identifier of the filter specified in the column declaration by parameter :detach_with_id


642
643
644
645
646
647
648
649
650
651
652
653
654
655
# File 'lib/helpers/wice_grid_view_helpers.rb', line 642

def grid_filter(grid, filter_key)
  unless grid.kind_of? WiceGrid
    raise WiceGridArgumentError.new("submit_grid_javascript: the parameter must be a WiceGrid instance.")
  end
  if grid.output_buffer.nil?
    raise WiceGridArgumentError.new("grid_filter: You have attempted to run 'grid_filter' before 'grid'. Read about detached filters in the documentation.")
  end
  if grid.output_buffer == true
    raise WiceGridArgumentError.new("grid_filter: You have defined no detached filters, or you try use detached filters with" +
      ":show_filters => :no (set :show_filters to :always in this case). Read about detached filters in the documentation.")
  end

   :span, grid.output_buffer.filter_for(filter_key), :class => "#{grid.name}_detached_filter"
end

#grid_html(grid, options, rendering, reuse_last_column_for_filter_buttons) ⇒ Object

the longest method? :(


226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
# File 'lib/helpers/wice_grid_view_helpers.rb', line 226

def grid_html(grid, options, rendering, reuse_last_column_for_filter_buttons) #:nodoc:

  table_html_attrs, header_tr_html_attrs = options[:table_html_attrs], options[:header_tr_html_attrs]

  cycle_class = nil
  sorting_dependant_row_cycling = options[:sorting_dependant_row_cycling]

  content = GridOutputBuffer.new
  # Ruby 1.9.1
  content.force_encoding('UTF-8') if content.respond_to?(:force_encoding)

  content << %!<div class="wice_grid_container" id="#{grid.name}"><div id="#{grid.name}_title">!
  content << (:h3, grid.saved_query.name) if grid.saved_query
  content << "</div><table #{tag_options(table_html_attrs, true)}>"
  content << "<thead>"

  no_filters_at_all = (options[:show_filters] == :no || rendering.no_filter_needed?) ? true: false

  if no_filters_at_all
    no_rightmost_column = no_filter_row = no_filters_at_all
  else
    no_rightmost_column = no_filter_row = (options[:show_filters] == :no || rendering.no_filter_needed_in_main_table?) ? true: false
  end

  no_rightmost_column = true if reuse_last_column_for_filter_buttons

  pagination_panel_content_html, pagination_panel_content_js = nil, nil
  if options[:upper_pagination_panel]
    content << rendering.pagination_panel(no_rightmost_column, options[:hide_csv_button]) do
      pagination_panel_content_html, pagination_panel_content_js =
        pagination_panel_content(grid, options[:extra_request_parameters], options[:allow_showing_all_records])
      pagination_panel_content_html
    end
  end

  title_row_attrs = header_tr_html_attrs.clone
  title_row_attrs.add_or_append_class_value!('wice_grid_title_row', true)

  content << %!<tr #{tag_options(title_row_attrs, true)}>!

  filter_row_id = grid.name + '_filter_row'

  # first row of column labels with sorting links

  filter_shown = if options[:show_filters] == :when_filtered
    grid.filtering_on?
  elsif options[:show_filters] == :always
    true
  end

  cached_javascript = []

  rendering.each_column_aware_of_one_last_one(:in_html) do |column, last|

    column_name = column.column_name
    if column_name.is_a? Array
      column_name, js = column_name
      cached_javascript << js
    end

    if column.attribute_name && column.allow_ordering

      css_class = grid.filtered_by?(column) ? 'active_filter' : nil

      direction = 'asc'
      link_style = nil
      if grid.ordered_by?(column)
        css_class = css_class.nil? ? 'sorted' : css_class + ' sorted'
        link_style = grid.order_direction
        direction = 'desc' if grid.order_direction == 'asc'
      end

      col_link = link_to(
        column_name,
        rendering.column_link(column, direction, params, options[:extra_request_parameters]),
        :class => link_style)
      content << (:th, col_link, Hash.make_hash(:class, css_class))
      column.css_class = css_class
    else
      if reuse_last_column_for_filter_buttons && last
        content << (:th,
          hide_show_icon(filter_row_id, grid, filter_shown, no_filter_row, options[:show_filters], rendering),
          :class => 'hide_show_icon'
        )
      else
        content << (:th, column_name)
      end
    end
  end

  content << (:th,
    hide_show_icon(filter_row_id, grid, filter_shown, no_filter_row, options[:show_filters], rendering),
    :class => 'hide_show_icon'
  ) unless no_rightmost_column

  content << '</tr>'
  # rendering first row end


  unless no_filters_at_all # there are filters, we don't know where, in the table or detached
    if no_filter_row # they are all detached
      content.stubborn_output_mode = true
      rendering.each_column(:in_html) do |column|
        if column.filter_shown?
          filter_html_code, filter_js_code = column.render_filter
          filter_html_code = filter_html_code.html_safe_if_necessary
          cached_javascript << filter_js_code
          content.add_filter(column.detach_with_id, filter_html_code)
        end
      end

    else # some filters are present in the table

      filter_row_attrs = header_tr_html_attrs.clone
      filter_row_attrs.add_or_append_class_value!('wice_grid_filter_row', true)
      filter_row_attrs['id'] = filter_row_id

      content << %!<tr #{tag_options(filter_row_attrs, true)} !
      content << 'style="display:none"' unless filter_shown
      content << '>'

      rendering.each_column_aware_of_one_last_one(:in_html) do |column, last|
        if column.filter_shown?

          filter_html_code, filter_js_code = column.render_filter
          filter_html_code = filter_html_code.html_safe_if_necessary
          cached_javascript << filter_js_code
          if column.detach_with_id
            content.stubborn_output_mode = true
            content << (:th, '', Hash.make_hash(:class, column.css_class))
            content.add_filter(column.detach_with_id, filter_html_code)
          else
            content << (:th, filter_html_code, Hash.make_hash(:class, column.css_class))
          end
        else
          if reuse_last_column_for_filter_buttons && last
            content << (:th,
              reset_submit_buttons(options, grid, rendering),
              Hash.make_hash(:class, column.css_class).add_or_append_class_value!('filter_icons')
            )
          else
            content << (:th, '', Hash.make_hash(:class, column.css_class))
          end
        end
      end
      unless no_rightmost_column
        content << (:th, reset_submit_buttons(options, grid, rendering), :class => 'filter_icons' )
      end
      content << '</tr>'
    end
  end

  rendering.each_column(:in_html) do |column|
    unless column.css_class.blank?
      column.td_html_attrs.add_or_append_class_value!(column.css_class)
    end
  end

  content << '</thead><tfoot>'
  content << rendering.pagination_panel(no_rightmost_column, options[:hide_csv_button]) do
    if pagination_panel_content_html
      pagination_panel_content_html
    else
      pagination_panel_content_html, pagination_panel_content_js =
        pagination_panel_content(grid, options[:extra_request_parameters], options[:allow_showing_all_records])
      pagination_panel_content_html
    end
  end

  content << '</tfoot><tbody>'
  cached_javascript << pagination_panel_content_js

  # rendering  rows
  cell_value_of_the_ordered_column = nil
  previous_cell_value_of_the_ordered_column = nil

  grid.each do |ar| # rows

    before_row_output = if rendering.before_row_handler
      call_block_as_erb_or_ruby(rendering, rendering.before_row_handler, ar)
    else
      nil
    end

    after_row_output = if rendering.after_row_handler
      call_block_as_erb_or_ruby(rendering, rendering.after_row_handler, ar)
    else
      nil
    end

    row_content = ''
    rendering.each_column(:in_html) do |column|
      cell_block = column.cell_rendering_block

      opts = column.td_html_attrs.clone

      column_block_output = if column.class == Wice::ActionViewColumn
        cell_block.call(ar, params)
      else
        call_block_as_erb_or_ruby(rendering, cell_block, ar)
      end

      if column_block_output.kind_of?(Array)

        unless column_block_output.size == 2
          raise WiceGridArgumentError.new('When WiceGrid column block returns an array it is expected to contain 2 elements only - '+
            'the first is the contents of the table cell and the second is a hash containing HTML attributes for the <td> tag.')
        end

        column_block_output, additional_opts = column_block_output

        unless additional_opts.is_a?(Hash)
          raise WiceGridArgumentError.new('When WiceGrid column block returns an array its second element is expected to be a ' +
            "hash containing HTML attributes for the <td> tag. The returned value is #{additional_opts.inspect}. Read documentation.")
        end

        additional_css_class = nil
        if additional_opts.has_key?(:class)
          additional_css_class = additional_opts[:class]
          additional_opts.delete(:class)
        elsif additional_opts.has_key?('class')
          additional_css_class = additional_opts['class']
          additional_opts.delete('class')
        end
        opts.merge!(additional_opts)
        opts.add_or_append_class_value!(additional_css_class) unless additional_css_class.blank?
      end

      if sorting_dependant_row_cycling && column.attribute_name && grid.ordered_by?(column)
        cell_value_of_the_ordered_column = column_block_output
      end
      row_content += (:td, column_block_output, opts)
    end

    row_attributes = rendering.get_row_attributes(ar)

    if sorting_dependant_row_cycling
      cycle_class = cycle('odd', 'even', :name => grid.name) if cell_value_of_the_ordered_column != previous_cell_value_of_the_ordered_column
      previous_cell_value_of_the_ordered_column = cell_value_of_the_ordered_column
    else
      cycle_class = cycle('odd', 'even', :name => grid.name)
    end

    row_attributes.add_or_append_class_value!(cycle_class)

    content << before_row_output if before_row_output
    content << "<tr #{tag_options(row_attributes)}>#{row_content}"
    content << (:td, '') unless no_rightmost_column
    content << '</tr>'
    content << after_row_output if after_row_output
  end

  last_row_output = if rendering.last_row_handler
    call_block_as_erb_or_ruby(rendering, rendering.last_row_handler, nil)
  else
    nil
  end

  content << last_row_output if last_row_output

  content << '</tbody></table></div>'

  base_link_for_filter, base_link_for_show_all_records = rendering.base_link_for_filter(controller, options[:extra_request_parameters])

  link_for_export      = rendering.link_for_export(controller, 'csv', options[:extra_request_parameters])

  parameter_name_for_query_loading = {grid.name => {:q => ''}}.to_query
  parameter_name_for_focus = {grid.name => {:foc => ''}}.to_query

  prototype_and_js_version_check = if ENV['RAILS_ENV'] == 'development'
    %$ if (typeof(WiceGridProcessor) == "undefined"){\n$ +
    %$   alert('wice_grid.js not loaded, WiceGrid cannot proceed! ' +\n$ +
    %$     'Please make sure that you include WiceGrid javascript in your page. ' +\n$ +
    %$     'Use <%= include_wice_grid_assets %> or <%= include_wice_grid_assets(:include_calendar => true) %> ' +\n$ +
    %$     'for WiceGrid javascripts and assets.')\n$ +
    %$ } else if ((typeof(WiceGridProcessor._version) == "undefined") || ( WiceGridProcessor._version != "0.4.4")) {\n$ +
    %$    alert("wice_grid.js in your /public is outdated, please run\\n ./script/generate wice_grid_assets_jquery\\n$ +
    %$ or\\n ./script/generate wice_grid_assets_prototype\\nto update it.");\n$ +
    %$ }\n$
  else
    ''
  end

  if rendering.show_hide_button_present
    cached_javascript << JsAdaptor.show_hide_button_initialization(grid.name, filter_row_id)
  end

  if rendering.reset_button_present
    cached_javascript << JsAdaptor.reset_button_initialization(grid.name, reset_grid_javascript(grid))
  end

  if rendering.submit_button_present
    cached_javascript << JsAdaptor.submit_button_initialization(grid.name, submit_grid_javascript(grid))
  end

  if rendering.contains_a_text_input?
    cached_javascript << JsAdaptor.enter_key_event_registration(grid.name)
  end

  if rendering.csv_export_icon_present
    cached_javascript << JsAdaptor.csv_export_icon_initialization(grid.name)
  end

  if rendering.contains_auto_reloading_selects
    cached_javascript << JsAdaptor.auto_reloading_selects_event_initialization(grid.name)
  end

  if rendering.contains_auto_reloading_inputs
    cached_javascript << JsAdaptor.auto_reloading_inputs_event_initialization(grid.name)
  end

  if rendering.contains_auto_reloading_inputs_with_negation_checkboxes
    cached_javascript << JsAdaptor.auto_reloading_inputs_with_negation_checkboxes_event_initialization(grid.name)
  end

  if rendering.contains_auto_reloading_calendars
    cached_javascript << JsAdaptor.auto_reloading_calendar_event_initialization(grid.name)
  end

  if rendering.element_to_focus
    cached_javascript << JsAdaptor.focus_element(rendering.element_to_focus)
  end

  if Wice::ConfigurationProvider.value_for(:SECOND_RANGE_VALUE_FOLLOWING_THE_FIRST) && rendering.contains_range_filters
    cached_javascript << JsAdaptor.update_ranges(grid.name)
  end


  content << javascript_tag(
    JsAdaptor.dom_loaded +
    %/ #{prototype_and_js_version_check}\n/ +
    %/ window['#{grid.name}'] = new WiceGridProcessor('#{grid.name}', '#{base_link_for_filter}',\n/ +
    %/  '#{base_link_for_show_all_records}', '#{link_for_export}', '#{parameter_name_for_query_loading}',\n/ +
    %/ '#{parameter_name_for_focus}', '#{ENV['RAILS_ENV']}');\n/ +
    if no_filters_at_all
      ''
    else
      rendering.select_for(:in_html) do |vc|
        vc.attribute_name and not vc.no_filter
      end.collect{|column| column.yield_javascript}.join("\n")
    end +
    "\n" + cached_javascript.compact.join('') +
    '})'
  )

  if content.stubborn_output_mode
    grid.output_buffer = content
  else
    # this will serve as a flag that the grid helper has already processed the grid but in a normal mode,
    # not in the mode with detached filters.
    grid.output_buffer = true
  end
  return content
end

#hide_show_icon(filter_row_id, grid, filter_shown, no_filter_row, show_filters, rendering) ⇒ Object

:nodoc:


581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
# File 'lib/helpers/wice_grid_view_helpers.rb', line 581

def hide_show_icon(filter_row_id, grid, filter_shown, no_filter_row, show_filters, rendering)  #:nodoc:
  grid_name = grid.name
  no_filter_opening_closing_icon = (show_filters == :always) || no_filter_row

  styles = ["display: block;", "display: none;"]
  styles.reverse! unless filter_shown


  if no_filter_opening_closing_icon
    hide_icon = show_icon = ''
  else


    rendering.show_hide_button_present = true
    filter_tooltip = WiceGridNlMessageProvider.get_message(:HIDE_FILTER_TOOLTIP)

    hide_icon = (:span,
      image_tag(Defaults::SHOW_HIDE_FILTER_ICON,
        :title => filter_tooltip,
        :alt   => filter_tooltip),
      :id => grid_name + '_hide_icon',
      :style => styles[0],
      :class => 'clickable'
    )


    filter_tooltip = WiceGridNlMessageProvider.get_message(:SHOW_FILTER_TOOLTIP)

    show_icon = (:span,
      image_tag(Defaults::SHOW_HIDE_FILTER_ICON,
        :title => filter_tooltip,
        :alt   => filter_tooltip),
      :id => grid_name + '_show_icon',
      :style => styles[1],
      :class => 'clickable'
    )

    hide_icon + show_icon
  end
end

#include_wice_grid_assets(options = {}) ⇒ Object

View helper to include all stylesheets and javascript files needed for WiceGrid to function. Add it to template/layout in the page header section.

By default the helper returns WiceGrid javascripts and stylesheets include statements only on demand, that is, only if at least one initialize_grid has been called in the controller. Otherwise the helper returns an empty string. However, you can force the old unconditioned behavior if you need by submitting parameter :load_on_demand set to false:

<%= include_wice_grid_assets(:load_on_demand => false) %>

By default include_wice_grid_assets adds include statements for the javascript calendar widget used for date/datetime filters, but it's possible not to include them setting parameter include_calendar to false:

<%= include_wice_grid_assets(:include_calendar => false) %>

63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
# File 'lib/helpers/wice_grid_misc_view_helpers.rb', line 63

def include_wice_grid_assets(options = {})
  Wice::JsAdaptor.init
  opts = {:include_calendar => true, :load_on_demand => true}
  options.assert_valid_keys(opts.keys)
  opts.merge!(options)

  if @__wice_grid_on_page || ! opts[:load_on_demand]
    javascript_include_tag('wice_grid') +
    stylesheet_link_tag('wice_grid') +
    if opts[:include_calendar]
      JsAdaptor.js_framework_specific_calendar_assets(self)
    else
      ''
    end
  end
end

#names_of_wice_grid_javascripts(options = {}) ⇒ Object

Returns a list of names of javascript files for WiceGrid thus providing compatibility with Rails asset caching.

Mind the parameters, and the fact that Prototype has to be loaded before WiceGrid javascripts:

  <%= javascript_include_tag *([:defaults] + names_of_wice_grid_javascripts + [ 'ui', 'swfobject', {:cache => true}]) %>

By default +names_of_wice_grid_javascripts+ returns all javascripts, but it's possible not to include calendar widget javascripts by
setting parameter <tt>:include_calendar</tt>  to +false+.

87
88
89
90
91
92
93
94
95
96
# File 'lib/helpers/wice_grid_misc_view_helpers.rb', line 87

def names_of_wice_grid_javascripts(options = {})
  Wice::JsAdaptor.init
  opts = {:include_calendar => true}
  options.assert_valid_keys(opts.keys)
  opts.merge!(options)
  res = ['wice_grid']
  n = JsAdaptor.js_framework_specific_calendar_js_name
  res <<  n if n && opts[:include_calendar]
  res
end

#names_of_wice_grid_stylesheets(options = {}) ⇒ Object

Returns a list of names of stylesheet files for WiceGrid thus providing compatibility with Rails asset caching.

Mind the parameters, for example:

  <%= stylesheet_link_tag *(['core',  'modalbox'] + names_of_wice_grid_stylesheets + [ {:cache => true}]) %>

By default +names_of_wice_grid_stylesheets+ returns all javascripts, but it's possible not to include calendar widget javascripts by
setting parameter <tt>:include_calendar</tt>  to +false+.

105
106
107
108
109
110
111
112
113
114
# File 'lib/helpers/wice_grid_misc_view_helpers.rb', line 105

def names_of_wice_grid_stylesheets(options = {})
  Wice::JsAdaptor.init
  opts = {:include_calendar => true}
  options.assert_valid_keys(opts.keys)
  opts.merge!(options)
  res = ['wice_grid']
  n = JsAdaptor.js_framework_specific_calendar_css_name
  res << n if n && opts[:include_calendar]
  res
end

#pagination_info(grid, allow_showing_all_records) ⇒ Object

:nodoc:


762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
# File 'lib/helpers/wice_grid_view_helpers.rb', line 762

def pagination_info(grid, allow_showing_all_records)  #:nodoc:
  collection = grid.resultset

  collection_total_entries = collection.total_entries
  collection_total_entries_str = collection_total_entries.to_s
  parameters = grid.get_state_as_parameter_value_pairs

  js = ''
  html = if (collection.total_pages < 2 && collection.length == 0)
    '0'
  else
    parameters << ["#{grid.name}[pp]", collection_total_entries_str]

    "#{collection.offset + 1}-#{collection.offset + collection.length} / #{collection_total_entries_str} " +
      if (! allow_showing_all_records) || collection_total_entries <= collection.length
        ''
      else
        res, js = show_all_link(collection_total_entries, parameters, grid.name)
        res
      end
  end +
  if grid.all_record_mode?
    res, js = back_to_pagination_link(parameters, grid.name)
    res
  else
    ''
  end

  [html, js]
end

#pagination_panel_content(grid, extra_request_parameters, allow_showing_all_records) ⇒ Object

:nodoc:


717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
# File 'lib/helpers/wice_grid_view_helpers.rb', line 717

def pagination_panel_content(grid, extra_request_parameters, allow_showing_all_records) #:nodoc:
  extra_request_parameters = extra_request_parameters.clone
  if grid.saved_query
    extra_request_parameters["#{grid.name}[q]"] = grid.saved_query.id
  end

  html, js = pagination_info(grid, allow_showing_all_records)

  [will_paginate(grid.resultset,
    :previous_label => WiceGridNlMessageProvider.get_message(:PREVIOUS_LABEL),
    :next_label     => WiceGridNlMessageProvider.get_message(:NEXT_LABEL),
    :param_name     => "#{grid.name}[page]",
    :params         => extra_request_parameters).to_s +
    (' <div class="pagination_status">' + html + '</div>').html_safe_if_necessary, js]
end

#prepare_result(rendering, grid, content, block) ⇒ Object

:nodoc:


178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
# File 'lib/helpers/wice_grid_view_helpers.rb', line 178

def prepare_result(rendering, grid, content, block) #:nodoc:
  if rendering.erb_mode
    # true in this case is a sign that grid_html has run in a normal mode, i.e. without detached filters
    if grid.output_buffer.nil? || grid.output_buffer == true
      content = content.to_s
      if Rails.respond_to?(:version) && Rails.version.to_f >= 2.2
        return concat(content)
      else
        return concat(content, block.binding)
      end
    else
      # this way we're sending an empty string and setting flag stubborn_output_mode of GridOutputBuffer to false
      return grid.output_buffer.to_s
    end
  else
    return content
  end
end

#reset_grid_javascript(grid) ⇒ Object

Returns javascript which resets the grid, clearing the state of filters. The parameter is a WiceGrid instance. Use it with button_to_function to create your Reset button.


669
670
671
672
673
674
# File 'lib/helpers/wice_grid_view_helpers.rb', line 669

def reset_grid_javascript(grid)
  unless grid.kind_of? WiceGrid
    raise WiceGridArgumentError.new("reset_grid_javascript: the parameter must be a WiceGrid instance.")
  end
  "#{grid.name}.reset()"
end

#reset_submit_buttons(options, grid, rendering) ⇒ Object

:nodoc:


622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
# File 'lib/helpers/wice_grid_view_helpers.rb', line 622

def reset_submit_buttons(options, grid, rendering)  #:nodoc:
  (if options[:hide_submit_button]
    ''
  else
    rendering.submit_button_present = true
    filter_tooltip = WiceGridNlMessageProvider.get_message(:FILTER_TOOLTIP)
    image_tag(Defaults::FILTER_ICON, :title => filter_tooltip, :alt => filter_tooltip, :class => 'submit clickable')
  end + ' ' +
  if options[:hide_reset_button]
    ''
  else
    rendering.reset_button_present = true
    filter_tooltip = WiceGridNlMessageProvider.get_message(:RESET_FILTER_TOOLTIP)
    image_tag(Defaults::RESET_ICON, :title => filter_tooltip, :alt => filter_tooltip, :class => 'reset clickable')
  end).html_safe_if_necessary
end

#saved_queries_list(grid_name, saved_query = nil, extra_parameters = nil) ⇒ Object

:nodoc:


50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
# File 'lib/helpers/wice_grid_serialized_queries_view_helpers.rb', line 50

def saved_queries_list(grid_name, saved_query = nil, extra_parameters = nil)  #:nodoc:
  
  link_title            = WiceGridNlMessageProvider.get_message(:SAVED_QUERY_LINK_TITLE)
  deletion_confirmation = WiceGridNlMessageProvider.get_message(:SAVED_QUERY_DELETION_CONFIRMATION)
  deletion_link_title   = WiceGridNlMessageProvider.get_message(:SAVED_QUERY_DELETION_LINK_TITLE)
  
  query_store_model = ::Wice::get_query_store_model
  currently_loaded_query_id = saved_query ? saved_query.id : nil
  with = extra_parameters.nil? ? nil : "'"  + {:extra => extra_parameters}.to_query + "'"

  %!<ul id="#{grid_name}_query_list" class="query_list"> ! +
  query_store_model.list(grid_name, controller).collect do |sq|
    link_opts = {:class => 'query_load_link', :title => "#{link_title} #{sq.name}"}
    link_opts[:class] += ' current' if saved_query == sq
    "<li>"+
    link_to_remote(image_tag(Defaults::DELETE_QUERY_ICON),
      {:url => delete_serialized_query_path(:grid_name => grid_name, :id => sq.id, :current => currently_loaded_query_id ),
        :confirm => deletion_confirmation, :with => with},
      {:title => "#{deletion_link_title} #{sq.name}"} )  + ' &nbsp; ' +
    link_to_function(h(sq.name),
      %/ if (typeof(#{grid_name}) != "undefined") #{grid_name}.load_query(#{sq.id}) /,
      link_opts) +
    if sq.respond_to? :description
      desc = sq.description
      desc.blank? ? '' : " <i>#{desc}</i>"
    else
      ''
    end +
    '</li>'
  end.join('') + '</ul>'
end

#saved_queries_panel(grid, opts = {}) ⇒ Object

View helper to render the list of saved queries and the form to create a new query. Parameters:

  • :extra_parameters - a hash of additional parameters to use when creating a new query object.

Read section “Adding Application Specific Logic to Saving/Restoring Queries” in README for more details.


9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
# File 'lib/helpers/wice_grid_serialized_queries_view_helpers.rb', line 9

def saved_queries_panel(grid, opts = {})
  unless grid.kind_of? WiceGrid
    raise WiceGridArgumentError.new("saved_queries_panel: the parameter must be a WiceGrid instance.")
  end

  options = {:extra_parameters => {}}
  opts.assert_valid_keys(options.keys)
  options.merge!(opts)

  grid_name = grid.name
  id_and_name = "#{grid_name}_saved_query_name"
  base_path_to_query_controller = create_serialized_query_url(:grid_name => grid_name)

  parameters = grid.get_state_as_parameter_value_pairs

  options[:extra_parameters].each do |k, v|
    parameters << [ CGI.unescape({:extra => {k => ''}}.to_query.sub(/=$/,'')) , v.to_s ]
  end
  parameters <<  ['authenticity_token', form_authenticity_token]

  (%! <div class="wice_grid_query_panel"><h3>#{WiceGridNlMessageProvider.get_message(:SAVED_QUERY_PANEL_TITLE)}</h3>! +
    saved_queries_list(grid_name, grid.saved_query, options[:extra_parameters]) +
    %!<div id="#{grid_name}_notification_messages"  onmouseover="#{Wice::JsAdaptor.fade_this}"></div>! +
    if block_given?
      view, ids = yield
      view
    else
      ''
    end +
    '<div class="wg-saved-query-input-controls">'+
    text_field_tag(id_and_name,  '', :size => 20, :onkeydown=>'', :id => id_and_name) +
    button_to_function(WiceGridNlMessageProvider.get_message(:SAVE_QUERY_BUTTON_LABEL),  "#{grid_name}_save_query()" ) +  
    '</div></div>' +
    javascript_tag do
      JsAdaptor.call_to_save_query_and_key_event_initialization_for_saving_queries(
        id_and_name, grid_name, base_path_to_query_controller, parameters.to_json, ids.to_json
      )
    end
    ).html_safe
end

#scaffolded_grid(grid_obj, opts = {}) ⇒ Object

secret but stupid weapon - takes an ActiveRecord and using reflection tries to build all the column clauses by itself. WiceGrid is not a scaffolding solution, I hate scaffolding and how certain idiots associate scaffolding with Rails, so I do not document this method to avoid contributing to this misunderstanding.


28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
# File 'lib/helpers/wice_grid_misc_view_helpers.rb', line 28

def scaffolded_grid(grid_obj, opts = {}) #:nodoc:
  Wice::JsAdaptor.init
  unless grid_obj.kind_of? WiceGrid
    raise WiceGridArgumentError.new("scaffolded_grid: the parameter must be a WiceGrid instance.")
  end

  # debug grid.klass.column_names
  columns = grid_obj.klass.column_names
  if opts[:reject_attributes].is_a? Proc
    columns = columns.reject{|c| opts[:reject_attributes].call(c)}
    opts.delete(:reject_attributes)
  elsif
    columns = columns.reject{|c| c =~ opts[:reject_attributes]}
    opts.delete(:reject_attributes)
  end
  grid(grid_obj, opts) do |g|
    columns.each do |column_name|
      g.column :column_name => column_name.humanize, :attribute_name => column_name  do |ar|
        ar.send(column_name)
      end
    end
  end
end

:nodoc:


734
735
736
737
738
739
740
741
742
743
744
745
746
747
# File 'lib/helpers/wice_grid_view_helpers.rb', line 734

def show_all_link(collection_total_entries, parameters, grid_name) #:nodoc:

  message = WiceGridNlMessageProvider.get_message(:ALL_QUERIES_WARNING)
  confirmation = collection_total_entries > Defaults::START_SHOWING_WARNING_FROM ? "if (confirm('#{message}'))" : ''

  js =  JsAdaptor.show_all_link_initialization(grid_name, confirmation, parameters.to_json)

  tooltip = WiceGridNlMessageProvider.get_message(:SHOW_ALL_RECORDS_TOOLTIP)
  html = %/<span class="show_all_link"><a href="#" title="#{tooltip}">/ +
    WiceGridNlMessageProvider.get_message(:SHOW_ALL_RECORDS_LABEL) +
    '</a></span>'

  [html, js]
end

#submit_grid_javascript(grid) ⇒ Object

Returns javascript which applies current filters. The parameter is a WiceGrid instance. Use it with button_to_function to create your Submit button.


659
660
661
662
663
664
# File 'lib/helpers/wice_grid_view_helpers.rb', line 659

def submit_grid_javascript(grid)
  unless grid.kind_of? WiceGrid
    raise WiceGridArgumentError.new("submit_grid_javascript: the parameter must be a WiceGrid instance.")
  end
  "#{grid.name}.process()"
end