active_scaffold-sequel 0.7.1 → 0.8.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (36) hide show
  1. data/app/assets/javascripts/active_scaffold.js.erb +12 -14
  2. data/app/assets/javascripts/jquery/active_scaffold.js +610 -348
  3. data/app/assets/javascripts/jquery/date_picker_bridge.js.erb +37 -19
  4. data/app/assets/javascripts/jquery/draggable_lists.js +28 -27
  5. data/app/assets/javascripts/jquery/jquery.editinplace.js +145 -137
  6. data/app/assets/javascripts/jquery/tiny_mce_bridge.js +1 -1
  7. data/app/assets/stylesheets/{active_scaffold.css.scss → active_scaffold.scss} +0 -0
  8. data/app/assets/stylesheets/{active_scaffold_colors.css.scss → active_scaffold_colors.scss} +0 -0
  9. data/app/assets/stylesheets/{active_scaffold_images.css.scss → active_scaffold_images.scss} +0 -0
  10. data/frontends/default/views/_list.html.erb +1 -1
  11. data/frontends/default/views/_list_record.html.erb +2 -1
  12. data/frontends/default/views/_search.html.erb +1 -10
  13. data/frontends/default/views/add_existing.js.erb +0 -3
  14. data/lib/active_scaffold.rb +0 -12
  15. data/lib/active_scaffold/actions/list.rb +8 -3
  16. data/lib/active_scaffold/bridges/carrierwave/form_ui.rb +3 -8
  17. data/lib/active_scaffold/bridges/date_picker.rb +2 -3
  18. data/lib/active_scaffold/bridges/dragonfly/form_ui.rb +3 -7
  19. data/lib/active_scaffold/bridges/tiny_mce.rb +1 -5
  20. data/lib/active_scaffold/bridges/tiny_mce/helpers.rb +1 -5
  21. data/lib/active_scaffold/extensions/action_view_rendering.rb +1 -6
  22. data/lib/active_scaffold/extensions/routing_mapper.rb +1 -1
  23. data/lib/active_scaffold/helpers/controller_helpers.rb +2 -2
  24. data/lib/active_scaffold/helpers/form_column_helpers.rb +3 -10
  25. data/lib/active_scaffold/version.rb +2 -2
  26. data/vendor/assets/javascripts/getprototypeof.js +12 -0
  27. data/vendor/assets/javascripts/jquery-ui-timepicker-addon.js +1882 -1276
  28. metadata +71 -65
  29. checksums.yaml +0 -7
  30. data/app/assets/javascripts/prototype/active_scaffold.js +0 -1103
  31. data/app/assets/javascripts/prototype/dhtml_history.js +0 -870
  32. data/app/assets/javascripts/prototype/form_enhancements.js +0 -117
  33. data/app/assets/javascripts/prototype/rico_corner.js +0 -370
  34. data/app/assets/javascripts/prototype/tiny_mce_bridge.js +0 -7
  35. data/lib/active_scaffold/bridges/calendar_date_select.rb +0 -24
  36. data/lib/active_scaffold/bridges/calendar_date_select/as_cds_bridge.rb +0 -67
@@ -1,19 +1,17 @@
1
- <% case ActiveScaffold.js_framework %>
2
- <% when :jquery %>
3
- <% require_asset "jquery-ui" %>
4
- <% require_asset "jquery-ui-timepicker-addon" %>
1
+ <% require_asset "getprototypeof" %>
2
+ <% require_asset "jquery-ui/core" %>
3
+ <% require_asset "jquery-ui/effect" %>
4
+ <% require_asset "jquery-ui/sortable" %>
5
+ <% require_asset "jquery-ui/draggable" %>
6
+ <% require_asset "jquery-ui/droppable" %>
7
+ <% if ActiveScaffold::Bridges[:date_picker] %>
8
+ <% require_asset "jquery-ui/datepicker" %>
9
+ <% require_asset "jquery-ui-timepicker-addon" %>
10
+ <% require_asset "jquery/date_picker_bridge" %>
11
+ <% end %>
12
+ <% require_asset "jquery/draggable_lists" %>
5
13
  <% require_asset "jquery/active_scaffold" %>
6
14
  <% require_asset "jquery/jquery.editinplace" %>
7
- <% require_asset "jquery/date_picker_bridge" %>
8
- <% require_asset "jquery/draggable_lists" %>
9
- <% when :prototype %>
10
- <% require_asset "effects" %>
11
- <% require_asset "controls" %>
12
- <% require_asset "prototype/active_scaffold" %>
13
- <% require_asset "prototype/dhtml_history" %>
14
- <% require_asset "prototype/form_enhancements" %>
15
- <% require_asset "prototype/rico_corner" %>
16
- <% end %>
17
15
  ActiveScaffold.config = <%= ActiveScaffold.js_config.to_json %>;
18
16
  <% ActiveScaffold.javascripts.each {|js| require_asset js} %>
19
17
  <% ActiveScaffold::Bridges.all_javascripts.each {|js| require_asset js} %>
@@ -1,32 +1,76 @@
1
- jQuery(document).ready(function() {
2
- jQuery('form.as_form').live('ajax:beforeSend', function(event) {
1
+ jQuery(document).ready(function($) {
2
+ /* It should not be needed, latest chrome is caching by itself
3
+ if (ActiveScaffold.config.conditional_get) jQuery.ajaxSettings.ifModified = true;
4
+ jQuery(document).on('ajax:beforeSend', function(event, xhr, settings){
5
+ xhr.cacheUrl = settings.url;
6
+ });
7
+ jQuery(document).on('ajax:success', function(event, data, status, xhr){
8
+ var etag=xhr.getResponseHeader("etag");
9
+ if (etag && xhr.status==304) {
10
+ var key = etag + xhr.cacheUrl;
11
+ xhr.responseText=jQuery(document).data(key);
12
+ var conv = jQuery(document).data('type-'+key);
13
+ if (conv) conv(xhr.responseText);
14
+ }
15
+ });
16
+ jQuery(document).ajaxComplete(function(event, xhr, settings){
17
+ var etag=xhr.getResponseHeader("etag");
18
+ if (etag && settings.ifModified && xhr.responseText) {
19
+ var key = etag + xhr.cacheUrl;
20
+ jQuery(document).data(key, xhr.responseText);
21
+ var contentType = xhr.getResponseHeader('Content-Type');
22
+ for(s in settings.contents) {
23
+ if (settings.contents[s].test(contentType)) {
24
+ var conv = settings.converters['text '+s];
25
+ if (typeof conv == 'function') jQuery(document).data('type-'+key, conv);
26
+ break;
27
+ }
28
+ }
29
+ }
30
+ });
31
+ */
32
+ if (/1\.[2-7]\..*/.test(jQuery().jquery)) {
33
+ var error = 'ActiveScaffold requires jquery 1.8.0 or greater, please use jquery-rails 2.1.x gem or greater';
34
+ if (typeof console != 'undefined') console.error(error);
35
+ else alert(error);
36
+ }
37
+
38
+ jQuery(document).on('focus', ':input', function() { ActiveScaffold.last_focus = this; });
39
+ jQuery(document).on('blur', ':input', function(e) { ActiveScaffold.last_focus = e.relatedTarget; });
40
+ jQuery(document).click(function(event) {
41
+ jQuery('.action_group.dyn > ul').hide(); // only hide so action links loading still work
42
+ });
43
+ jQuery(document).on('ajax:beforeSend', 'form.as_form', function(event) {
3
44
  var as_form = jQuery(this).closest("form");
4
- if (as_form && as_form.attr('data-loading') == 'true') {
45
+ if (as_form.data('loading') == true) {
5
46
  ActiveScaffold.disable_form(as_form);
6
47
  }
7
48
  return true;
8
49
  });
9
-
10
- jQuery('form.as_form').live('ajax:complete', function(event) {
50
+
51
+ jQuery(document).on('ajax:complete', 'form.as_form', function(event) {
11
52
  var as_form = jQuery(this).closest("form");
12
- if (as_form && as_form.attr('data-loading') == 'true') {
53
+ if (as_form.data('loading') == true) {
13
54
  ActiveScaffold.enable_form(as_form);
14
55
  }
15
56
  });
16
- jQuery('form.as_form').live('ajax:error', function(event, xhr, status, error) {
57
+ jQuery(document).on('ajax:complete', 'form.live', function(event) {
58
+ ActiveScaffold.focus_first_element_of_form(jQuery(this).closest("form"));
59
+ });
60
+ jQuery(document).on('ajax:error', 'form.as_form', function(event, xhr, status, error) {
17
61
  var as_div = jQuery(this).closest("div.active-scaffold");
18
- if (as_div) {
19
- ActiveScaffold.report_500_response(as_div)
62
+ if (as_div.length) {
63
+ ActiveScaffold.report_500_response(as_div, xhr);
20
64
  }
21
65
  });
22
- jQuery('form.as_form.as_remote_upload').live('submit', function(event) {
66
+ jQuery(document).on('submit', 'form.as_form:not([data-remote])', function(event) {
23
67
  var as_form = jQuery(this).closest("form");
24
- if (as_form && as_form.attr('data-loading') == 'true') {
68
+ if (as_form.data('loading') == true) {
25
69
  setTimeout("ActiveScaffold.disable_form('" + as_form.attr('id') + "')", 10);
26
70
  }
27
71
  return true;
28
72
  });
29
- jQuery('a.as_action').live('ajax:before', function(event) {
73
+ jQuery(document).on('ajax:before', 'a.as_action', function(event) {
30
74
  var action_link = ActiveScaffold.ActionLink.get(jQuery(this));
31
75
  if (action_link) {
32
76
  if (action_link.is_disabled()) {
@@ -38,170 +82,210 @@ jQuery(document).ready(function() {
38
82
  }
39
83
  return true;
40
84
  });
41
- jQuery('a.as_action.marked_records_action').live('ajax:before', function(event) {
42
- var action_link = jQuery(this);
43
- var marked_records = 'marked_records=' + ActiveScaffold.marked_records.join('%2C');
44
- var regexp = /(\?|&)marked_records=[^&]*/g;
45
- var match;
46
- if (action_link.search[0] == '?') {
47
- match = regexp.exec(action_link.search);
48
- if (match) {
49
- action_link.search = action_link.search.slice(0, match.index) + match[1] + marked_records + action_link.search.slice(regexp.lastIndex, action_link.search.length);
50
- } else {
51
- action_link.search = action_link.search + '&' + marked_records;
52
- }
53
- } else {
54
- action_link.search = '?' + marked_records;
55
- }
56
- return true;
57
- });
58
- jQuery('a.as_action.marked_records_action').live('ajax:complete', function(event) {
59
- var action_link = jQuery(this);
60
- ActiveScaffold.mark_records(action_link.readAttribute('data-tbody_id'), false);
61
- ActiveScaffold.marked_records = [];
62
- return true;
63
- });
64
- jQuery('a.as_action').live('ajax:success', function(event, response) {
85
+ jQuery(document).on('ajax:success', 'a.as_action', function(event, response) {
65
86
  var action_link = ActiveScaffold.ActionLink.get(jQuery(this));
66
87
  if (action_link) {
67
88
  if (action_link.position) {
68
89
  action_link.insert(response);
69
90
  if (action_link.hide_target) action_link.target.hide();
70
91
  } else {
92
+ if (action_link.tag.hasClass('toggle')) {
93
+ action_link.tag.closest('.action_group,.actions').find('.toggle.active').removeClass('active');
94
+ action_link.tag.addClass('active');
95
+ }
71
96
  action_link.enable();
72
97
  }
73
98
  jQuery(this).trigger('as:action_success', action_link);
99
+ if (action_link.loading_indicator) action_link.loading_indicator.css('visibility','hidden');
74
100
  }
75
101
  return true;
76
102
  });
77
- jQuery('a.as_action').live('ajax:complete', function(event) {
103
+ jQuery(document).on('ajax:error', 'a.as_action', function(event, xhr, status, error) {
78
104
  var action_link = ActiveScaffold.ActionLink.get(jQuery(this));
79
105
  if (action_link) {
80
- if (action_link.loading_indicator) action_link.loading_indicator.css('visibility','hidden');
106
+ ActiveScaffold.report_500_response(action_link.scaffold_id(), xhr);
107
+ action_link.enable();
81
108
  }
82
109
  return true;
83
110
  });
84
- jQuery('a.as_action').live('ajax:error', function(event, xhr, status, error) {
85
- var action_link = ActiveScaffold.ActionLink.get(jQuery(this));
86
- if (action_link) {
87
- ActiveScaffold.report_500_response(action_link.scaffold_id());
88
- action_link.enable();
111
+ jQuery(document).on('ajax:before', 'a.as_action.marked_records_action', function(event) {
112
+ var action_link = jQuery(this);
113
+ var marked_records = 'marked_records=' + ActiveScaffold.marked_records.join('%2C');
114
+ var regexp = /(\?|&)marked_records=[^&]*/g;
115
+ var match;
116
+ var search = action_link.prop('search');
117
+ if (search[0] == '?') {
118
+ match = regexp.exec(search);
119
+ if (match) {
120
+ action_link.prop('search', search.slice(0, match.index) + match[1] + marked_records + search.slice(regexp.lastIndex, search.length));
121
+ } else {
122
+ action_link.prop('search', search + '&' + marked_records);
123
+ }
124
+ } else {
125
+ action_link.prop('search', '?' + marked_records);
89
126
  }
90
127
  return true;
91
128
  });
92
- jQuery('a.as_cancel').live('ajax:before', function(event) {
129
+ jQuery(document).on('ajax:complete', 'a.as_action.marked_records_action', function(event) {
130
+ var action_link = jQuery(this);
131
+ ActiveScaffold.mark_records(action_link.attr('data-tbody_id'), false);
132
+ ActiveScaffold.marked_records = [];
133
+ return true;
134
+ });
135
+ jQuery(document).on('ajax:before', 'a.as_cancel', function(event) {
93
136
  var as_cancel = jQuery(this);
94
- var action_link = ActiveScaffold.find_action_link(as_cancel);
95
-
137
+ var action_link = ActiveScaffold.find_action_link(as_cancel);
138
+
96
139
  if (action_link) {
97
140
  var cancel_url = as_cancel.attr('href');
98
- var refresh_data = as_cancel.attr('data-refresh');
99
- if (refresh_data !== 'true' || !cancel_url) {
141
+ var refresh_data = action_link.tag.data('cancel-refresh') || as_cancel.data('refresh');
142
+ if (!refresh_data || !cancel_url) {
100
143
  action_link.close();
101
144
  return false;
102
145
  }
103
146
  }
104
147
  return true;
105
148
  });
106
- jQuery('a.as_cancel').live('ajax:success', function(event, response) {
107
- var action_link = ActiveScaffold.find_action_link(jQuery(this));
108
-
109
- if (action_link) {
110
- if (action_link.position) {
111
- action_link.close(response);
112
- } else {
113
- response.evalResponse();
114
- }
149
+ jQuery(document).on('ajax:success', 'a.as_cancel', function(event) {
150
+ var link = jQuery(this), action_link = ActiveScaffold.find_action_link(link);
151
+
152
+ if (action_link && action_link.position) {
153
+ action_link.close();
154
+ } else if (link.hasClass('reset')) {
155
+ var form = link.closest('form');
156
+ if (form.is('.search')) form.find(':input:visible:not([type=submit])').val('');
157
+ else form.trigger('reset');
115
158
  }
116
159
  return true;
117
160
  });
118
- jQuery('a.as_cancel').live('ajax:error', function(event, xhr, status, error) {
161
+ jQuery(document).on('ajax:error', 'a.as_cancel', function(event, xhr, status, error) {
119
162
  var action_link = ActiveScaffold.find_action_link(jQuery(this));
120
163
  if (action_link) {
121
- ActiveScaffold.report_500_response(action_link.scaffold_id());
164
+ ActiveScaffold.report_500_response(action_link.scaffold_id(), xhr);
122
165
  }
123
166
  return true;
124
167
  });
125
- jQuery('a.as_sort').live('ajax:before', function(event) {
168
+ jQuery(document).on('ajax:before', 'a.as_sort', function(event) {
126
169
  var as_sort = jQuery(this);
127
- var history_controller_id = as_sort.attr('data-page-history');
170
+ var history_controller_id = as_sort.data('page-history');
128
171
  if (history_controller_id) addActiveScaffoldPageToHistory(as_sort.attr('href'), history_controller_id);
129
172
  as_sort.closest('th').addClass('loading');
130
173
  return true;
131
174
  });
132
- jQuery('a.as_sort').live('ajax:error', function(event, xhr, status, error) {
175
+ jQuery(document).on('ajax:error', 'a.as_sort', function(event, xhr, status, error) {
133
176
  var as_scaffold = jQuery(this).closest('.active-scaffold');
134
- ActiveScaffold.report_500_response(as_scaffold);
177
+ ActiveScaffold.report_500_response(as_scaffold, xhr);
178
+ jQuery(this).closest('th').removeClass('loading');
135
179
  return true;
136
180
  });
137
- jQuery('span.mark_record_field,span.mark_heading,span.in_place_editor_field').live('hover', function(event) {
138
- jQuery(this).data(); // $ 1.4.2 workaround
139
- if (event.type == 'mouseenter') {
140
- if (typeof(jQuery(this).data('editInPlace')) === 'undefined') jQuery(this).addClass("hover");
141
- }
142
- if (event.type == 'mouseleave') {
143
- if (typeof(jQuery(this).data('editInPlace')) === 'undefined') jQuery(this).removeClass("hover");
144
- }
145
- return true;
146
- });
147
- jQuery('span.mark_record_field').live('click', function(event) {
148
- ActiveScaffold.mark_span(jQuery(this));
181
+ jQuery(document).on('click', 'span.mark_record_field', function(event) {
182
+ ActiveScaffold.mark_span(this);
149
183
  });
150
- jQuery('span.mark_heading').live('click', function(event) {
184
+ jQuery(document).on('click', 'span.mark_heading', function(event) {
151
185
  var span = jQuery(this);
152
- var checkbox = span.find('input[type="checkbox"]').first();
186
+ var checkbox = span.find('input[type="checkbox"]').eq(0);
153
187
  var tbody_id = span.attr('data-tbody_id');
154
- if (checkbox.checked) {
188
+ if (checkbox.prop('checked')) {
155
189
  ActiveScaffold.mark_records(tbody_id, true);
156
190
  } else {
157
191
  ActiveScaffold.mark_records(tbody_id, false);
158
192
  }
159
193
  });
160
- jQuery('span.in_place_editor_field').live('click', function(event) {
161
- ActiveScaffold.in_place_editor_field_clicked(jQuery(this));
194
+ jQuery(document).on('mouseenter mouseleave', 'span.mark_record_field,span.mark_heading,td.in_place_editor_field', function(event) {
195
+ var td = jQuery(this), span = td.find('span.in_place_editor_field');
196
+ if (event.type == 'mouseenter') {
197
+ if (td.hasClass('empty') || typeof(span.data('editInPlace')) === 'undefined') td.find('span').addClass("hover");
198
+ }
199
+ if (event.type == 'mouseleave') {
200
+ if (td.hasClass('empty') || typeof(span.data('editInPlace')) === 'undefined') td.find('span').removeClass("hover");
201
+ }
202
+ return true;
203
+ });
204
+ jQuery(document).on('click', 'td.in_place_editor_field, th.as_marked-column_heading', function(event) {
205
+ var span = jQuery(this).find('span.in_place_editor_field');
206
+ span.data('addEmptyOnCancel', jQuery(this).hasClass('empty'));
207
+ jQuery(this).removeClass('empty');
208
+ if (span.data('editInPlace')) span.trigger('click.editInPlace');
209
+ else ActiveScaffold.in_place_editor_field_clicked(span);
162
210
  });
163
- jQuery('a.as_paginate').live('ajax:before',function(event) {
211
+ jQuery(document).on('ajax:before', 'a.as_paginate',function(event) {
164
212
  var as_paginate = jQuery(this);
165
- var history_controller_id = as_paginate.attr('data-page-history');
213
+ var history_controller_id = as_paginate.data('page-history');
166
214
  if (history_controller_id) addActiveScaffoldPageToHistory(as_paginate.attr('href'), history_controller_id);
167
215
  as_paginate.prevAll('img.loading-indicator').css('visibility','visible');
168
216
  return true;
169
217
  });
170
- jQuery('a.as_paginate').live('ajax:error', function(event, xhr, status, error) {
218
+ jQuery(document).on('ajax:error', 'a.as_paginate', function(event, xhr, status, error) {
171
219
  var as_scaffold = jQuery(this).closest('.active-scaffold');
172
- ActiveScaffold.report_500_response(as_scaffold);
220
+ ActiveScaffold.report_500_response(as_scaffold, xhr);
173
221
  return true;
174
222
  });
175
- jQuery('a.as_paginate').live('ajax:complete', function(event) {
223
+ jQuery(document).on('ajax:complete', 'a.as_paginate', function(event) {
176
224
  jQuery(this).prevAll('img.loading-indicator').css('visibility','hidden');
177
225
  return true;
178
226
  });
179
- jQuery('a.as_add_existing, a.as_replace_existing').live('ajax:before', function(event) {
180
- var id = jQuery(this).prev().val();
227
+ jQuery(document).on('ajax:before', 'a.as_add_existing, a.as_replace_existing', function(event) {
228
+ var prev = jQuery(this).prev();
229
+ if (!prev.is(':input')) prev = prev.find(':input');
230
+ var id = prev.val();
181
231
  if (id) {
182
232
  if (!jQuery(this).data('href')) jQuery(this).data('href', jQuery(this).attr('href'));
183
233
  jQuery(this).attr('href', jQuery(this).data('href').replace('--ID--', id));
184
234
  return true;
185
235
  } else return false;
186
236
  });
187
- jQuery('input.update_form:not(.recordselect), textarea.update_form, select.update_form').live('change', function(event) {
237
+ jQuery(document).on('ajax:complete', '.action_group.dyn > ul a', function(event) {
238
+ var action_link = ActiveScaffold.find_action_link(event.target);
239
+ if (action_link.loading_indicator) action_link.loading_indicator.css('visibility','hidden');
240
+ jQuery(event.target).closest('.action_group.dyn > ul').remove();
241
+ });
242
+
243
+ jQuery(document).on('change', 'input.update_form:not(.recordselect), textarea.update_form, select.update_form, .checkbox-list.update_form input:checkbox', function(event) {
188
244
  var element = jQuery(this);
189
- var value = element.is("input:checkbox:not(:checked)") ? null : element.val();
190
- ActiveScaffold.update_column(element, element.attr('data-update_url'), element.attr('data-update_send_form'), element.attr('id'), value);
245
+ var form_element = element.closest('.checkbox-list');
246
+ var value, additional_params;
247
+ if (form_element.is(".checkbox-list")) {
248
+ value = form_element.find(':checked').map(function(item){return $(this).val();}).toArray();
249
+ additional_params = (element.is(':checked') ? '_added=' : '_removed=') + element.val();
250
+ } else {
251
+ value = element.is("input:checkbox:not(:checked)") ? null : element.val();
252
+ form_element = element;
253
+ }
254
+ ActiveScaffold.update_column(form_element, form_element.data('update_url'), form_element.data('update_send_form'), element.attr('id'), value, additional_params);
191
255
  return true;
192
256
  });
193
- jQuery('input.recordselect.update_form').live('recordselect:change', function(event, id, label) {
257
+ jQuery(document).on('click', 'a.refresh-link', function(event) {
258
+ event.preventDefault();
194
259
  var element = jQuery(this);
195
- ActiveScaffold.update_column(element, element.attr('data-update_url'), element.attr('data-update_send_form'), element.attr('id'), id);
260
+ var form_element = element.prev();
261
+ var value;
262
+ if (form_element.is(".checkbox-list")) {
263
+ value = form_element.find(':checked').map(function(item){return $(this).val();}).toArray();
264
+ form_element = form_element.parent().find("input:checkbox"); // parent is needed for draggable-list, checked list may be empty
265
+ } else value = form_element.is("input:checkbox:not(:checked)") ? null : form_element.val();
266
+ ActiveScaffold.update_column(form_element, element.attr('href'), element.data('update_send_form'), form_element.attr('id'), value);
267
+ });
268
+ jQuery(document).on('click', 'a.visibility-toggle', function(e) {
269
+ var link = jQuery(this), toggable = jQuery('#' + link.data('toggable'));
270
+ e.preventDefault();
271
+ toggable.toggle();
272
+ link.html((toggable.is(':hidden')) ? link.data('show') : link.data('hide'));
273
+ return false;
274
+ });
275
+ jQuery(document).on('recordselect:change', 'input.recordselect.update_form', function(event, id, label) {
276
+ var element = jQuery(this);
277
+ ActiveScaffold.update_column(element, element.data('update_url'), element.data('update_send_form'), element.attr('id'), id);
196
278
  return true;
197
279
  });
198
-
199
- jQuery('select.as_search_range_option').live('change', function(event) {
200
- ActiveScaffold[jQuery(this).val() == 'BETWEEN' ? 'show' : 'hide'](jQuery(this).parent().find('.as_search_range_between'));
280
+
281
+ jQuery(document).on('change', 'select.as_search_range_option', function(event) {
282
+ var element = jQuery(this);
283
+ ActiveScaffold[element.val() == 'BETWEEN' ? 'show' : 'hide'](element.closest('dd').find('.as_search_range_between'));
284
+ ActiveScaffold[(element.val() == 'null' || element.val() == 'not_null') ? 'hide' : 'show'](element.attr('id').replace(/_opt/, '_numeric'));
201
285
  return true;
202
286
  });
203
-
204
- jQuery('select.as_search_range_option').live('change', function(event) {
287
+
288
+ jQuery(document).on('change', 'select.as_search_date_time_option', function(event) {
205
289
  var element = jQuery(this);
206
290
  ActiveScaffold[!(element.val() == 'PAST' || element.val() == 'FUTURE' || element.val() == 'RANGE') ? 'show' : 'hide'](element.attr('id').replace(/_opt/, '_numeric'));
207
291
  ActiveScaffold[(element.val() == 'PAST' || element.val() == 'FUTURE') ? 'show' : 'hide'](element.attr('id').replace(/_opt/, '_trend'));
@@ -209,18 +293,18 @@ jQuery(document).ready(function() {
209
293
  return true;
210
294
  });
211
295
 
212
- jQuery('select.as_update_date_operator').live('change', function(event) {
296
+ jQuery(document).on('change', 'select.as_update_date_operator', function(event) {
213
297
  ActiveScaffold[jQuery(this).val() == 'REPLACE' ? 'show' : 'hide'](jQuery(this).next());
214
298
  ActiveScaffold[jQuery(this).val() == 'REPLACE' ? 'hide' : 'show'](jQuery(this).next().next());
215
299
  return true;
216
300
  });
217
301
 
218
- jQuery('a[data-popup]').live('click', function(e) {
219
- window.open(jQuery(this).attr('href'));
220
- e.preventDefault();
302
+ jQuery(document).on('click', '.active-scaffold .sub-form a.destroy', function(event) {
303
+ event.preventDefault();
304
+ ActiveScaffold.delete_subform_record($(this).data('delete-id'));
221
305
  });
222
306
 
223
- jQuery('.hover_click').live("click", function(event) {
307
+ jQuery(document).on("click", '.hover_click', function(event) {
224
308
  var element = jQuery(this);
225
309
  var ul_element = element.children('ul').first();
226
310
  if (ul_element.is(':visible')) {
@@ -230,15 +314,42 @@ jQuery(document).ready(function() {
230
314
  }
231
315
  return false;
232
316
  });
233
- jQuery('.hover_click a.as_action').live('click', function(event) {
317
+ jQuery(document).on('click', '.hover_click a.as_action', function(event) {
234
318
  var element = jQuery(this).closest('.hover_click');
235
- if (element) {
319
+ if (element.length) {
236
320
  element.find('ul').hide();
237
321
  }
238
322
  return true;
239
323
  });
324
+
325
+ jQuery(document).on('click', '.message a.close', function(e) {
326
+ ActiveScaffold.hide(jQuery(this).closest('.message'));
327
+ e.preventDefault();
328
+ });
329
+
330
+ /* setup some elements on page/form load */
331
+ ActiveScaffold.load_embedded(document);
332
+ ActiveScaffold.enable_js_form_buttons(document);
333
+ ActiveScaffold.live_search(document);
334
+ ActiveScaffold.auto_paginate(document);
335
+ ActiveScaffold.draggable_lists('.draggable-lists', document);
336
+ if (ActiveScaffold.config.warn_changes) ActiveScaffold.setup_warn_changes();
337
+ jQuery(document).on('as:element_updated', function(e) {
338
+ ActiveScaffold.load_embedded(e.target);
339
+ ActiveScaffold.enable_js_form_buttons(e.target);
340
+ ActiveScaffold.live_search(e.target);
341
+ ActiveScaffold.draggable_lists('.draggable-lists', e.target);
342
+ });
343
+ jQuery(document).on('as:action_success', 'a.as_action', function(e, action_link) {
344
+ ActiveScaffold.load_embedded(action_link.adapter);
345
+ ActiveScaffold.enable_js_form_buttons(action_link.adapter);
346
+ ActiveScaffold.live_search(action_link.adapter);
347
+ ActiveScaffold.auto_paginate(action_link.adapter);
348
+ ActiveScaffold.draggable_lists('.draggable-lists', action_link.adapter);
349
+ });
240
350
  });
241
351
 
352
+
242
353
  /* Simple Inheritance
243
354
  http://ejohn.org/blog/simple-javascript-inheritance/
244
355
  */
@@ -247,17 +358,17 @@ jQuery(document).ready(function() {
247
358
 
248
359
  // The base Class implementation (does nothing)
249
360
  this.Class = function(){};
250
-
361
+
251
362
  // Create a new Class that inherits from this class
252
363
  Class.extend = function(prop) {
253
364
  var _super = this.prototype;
254
-
365
+
255
366
  // Instantiate a base class (but only create the instance,
256
367
  // don't run the init constructor)
257
368
  initializing = true;
258
369
  var prototype = new this();
259
370
  initializing = false;
260
-
371
+
261
372
  // Copy the properties over onto the new prototype
262
373
  for (var name in prop) {
263
374
  // Check if we're overwriting an existing function
@@ -266,38 +377,38 @@ jQuery(document).ready(function() {
266
377
  (function(name, fn){
267
378
  return function() {
268
379
  var tmp = this._super;
269
-
380
+
270
381
  // Add a new ._super() method that is the same method
271
382
  // but on the super-class
272
383
  this._super = _super[name];
273
-
384
+
274
385
  // The method only need to be bound temporarily, so we
275
386
  // remove it when we're done executing
276
- var ret = fn.apply(this, arguments);
387
+ var ret = fn.apply(this, arguments);
277
388
  this._super = tmp;
278
-
389
+
279
390
  return ret;
280
391
  };
281
392
  })(name, prop[name]) :
282
393
  prop[name];
283
394
  }
284
-
395
+
285
396
  // The dummy class constructor
286
397
  function Class() {
287
398
  // All construction is actually done in the init method
288
399
  if ( !initializing && this.init )
289
400
  this.init.apply(this, arguments);
290
401
  }
291
-
402
+
292
403
  // Populate our constructed prototype object
293
404
  Class.prototype = prototype;
294
-
405
+
295
406
  // Enforce the constructor to be what we expect
296
407
  Class.constructor = Class;
297
408
 
298
409
  // And make this class extendable
299
410
  Class.extend = arguments.callee;
300
-
411
+
301
412
  return Class;
302
413
  };
303
414
  })();
@@ -305,60 +416,38 @@ jQuery(document).ready(function() {
305
416
  /*
306
417
  $ delayed observer
307
418
  (c) 2007 - Maxime Haineault (max@centdessin.com)
308
-
419
+
309
420
  Special thanks to Stephen Goguen & Tane Piper.
310
-
421
+
311
422
  Slight modifications by Elliot Winkler
312
423
  */
313
424
 
314
- if (typeof(jQuery.fn.delayedObserver) === 'undefined') {
315
- (function() {
316
- var delayedObserverStack = [];
317
- var observed;
318
-
319
- function delayedObserverCallback(stackPos) {
320
- observed = delayedObserverStack[stackPos];
321
- if (observed.timer) return;
322
-
323
- observed.timer = setTimeout(function(){
324
- observed.timer = null;
325
- observed.callback(observed.obj.val(), observed.obj);
326
- }, observed.delay * 1000);
327
-
328
- observed.oldVal = observed.obj.val();
329
- }
330
-
331
- // going by
332
- // <http://www.cambiaresearch.com/c4/702b8cd1-e5b0-42e6-83ac-25f0306e3e25/Javascript-Char-Codes-Key-Codes.aspx>
333
- // I think these codes only work when using keyup or keydown
334
- function isNonPrintableKey(event) {
335
- var code = event.keyCode;
336
- return (
337
- event.metaKey ||
338
- (code >= 9 && code <= 16) || (code >= 27 && code <= 40) || (code >= 91 && code <= 93) || (code >= 112 && code <= 145)
339
- );
340
- }
341
-
342
- jQuery.fn.extend({
343
- delayedObserver:function(delay, callback){
344
- $this = jQuery(this);
345
-
346
- delayedObserverStack.push({
347
- obj: $this, timer: null, delay: delay,
348
- oldVal: $this.val(), callback: callback
349
- });
350
-
351
- stackPos = delayedObserverStack.length-1;
352
-
353
- $this.keyup(function(event) {
354
- if (isNonPrintableKey(event)) return;
355
- observed = delayedObserverStack[stackPos];
356
- if (observed.obj.val() == observed.obj.oldVal) return;
357
- else delayedObserverCallback(stackPos);
358
- });
425
+ if (typeof(jQuery.fn.delayedObserver) === 'undefined') {
426
+ (function($){
427
+ $.extend($.fn, {
428
+ delayedObserver: function(callback, delay, options){
429
+ return this.each(function(){
430
+ var el = $(this);
431
+ var op = options || {};
432
+ el.data('oldval', el.val())
433
+ .data('delay', delay || 0.5)
434
+ .data('condition', op.condition || function() { return ($(this).data('oldval') == $(this).val()); })
435
+ .data('callback', callback)
436
+ [(op.event||'keyup')](function(){
437
+ if (el.data('condition').apply(el)) { return; }
438
+ else {
439
+ if (el.data('timer')) { clearTimeout(el.data('timer')); }
440
+ el.data('timer', setTimeout(function(){
441
+ var callback = el.data('callback')
442
+ if (callback) callback.apply(el);
443
+ }, el.data('delay') * 1000));
444
+ el.data('oldval', el.val());
445
+ }
446
+ });
447
+ });
359
448
  }
360
449
  });
361
- })();
450
+ })(jQuery);
362
451
  };
363
452
 
364
453
 
@@ -367,6 +456,34 @@ if (typeof(jQuery.fn.delayedObserver) === 'undefined') {
367
456
  */
368
457
 
369
458
  var ActiveScaffold = {
459
+ last_focus: null,
460
+ live_search: function(element) {
461
+ jQuery('form.search.live input[type=search]', element).delayedObserver(function() {
462
+ jQuery(this).parent().trigger("submit");
463
+ }, ActiveScaffold.config.live_search_delay || 0.5);
464
+ },
465
+ auto_paginate: function(element) {
466
+ var paginate_link = jQuery('.active-scaffold-pagination.auto-paginate a:first', element);
467
+ if (paginate_link.length) {
468
+ jQuery('.active-scaffold-pagination.auto-paginate', element).hide();
469
+ ActiveScaffold.auto_load_page(paginate_link.attr('href'), {auto_pagination: true});
470
+ }
471
+ },
472
+ auto_load_page: function(href, params) {
473
+ jQuery.get(href, params, null, 'script');
474
+ },
475
+ enable_js_form_buttons: function(element) {
476
+ jQuery('.as-js-button', element).show();
477
+ },
478
+ load_embedded: function(element) {
479
+ jQuery('.active-scaffold-component .load-embedded', element).each(function(index, item) {
480
+ item = jQuery(item);
481
+ item.closest('.active-scaffold-component').load(item.attr('href'), function() {
482
+ jQuery(this).trigger('as:element_updated');
483
+ });
484
+ });
485
+ },
486
+
370
487
  records_for: function(tbody_id) {
371
488
  if (typeof(tbody_id) == 'string') tbody_id = '#' + tbody_id;
372
489
  return jQuery(tbody_id).children('.record');
@@ -374,7 +491,7 @@ var ActiveScaffold = {
374
491
  stripe: function(tbody_id) {
375
492
  var even = false;
376
493
  var rows = this.records_for(tbody_id);
377
-
494
+
378
495
  rows.each(function (index, row_node) {
379
496
  row = jQuery(row_node);
380
497
  if (row_node.tagName != 'SCRIPT'
@@ -387,27 +504,30 @@ var ActiveScaffold = {
387
504
  else row.removeClass("even-record");
388
505
 
389
506
  even = !even;
390
- }
507
+ }
391
508
  });
392
509
  },
393
510
  hide_empty_message: function(tbody) {
394
511
  if (this.records_for(tbody).length != 0) {
395
- var empty_message_node = jQuery(tbody).parent().find('tbody.messages p.empty-message')
396
- if (empty_message_node) empty_message_node.hide();
512
+ jQuery(tbody).parent().find('tbody.messages p.empty-message').hide();
397
513
  }
398
514
  },
399
515
  reload_if_empty: function(tbody, url) {
400
516
  if (this.records_for(tbody).length == 0) {
401
- jQuery.getScript(url);
517
+ this.reload(url);
402
518
  }
403
519
  },
520
+ reload: function(url) {
521
+ jQuery.getScript(url);
522
+ },
404
523
  removeSortClasses: function(scaffold) {
405
524
  if (typeof(scaffold) == 'string') scaffold = '#' + scaffold;
406
525
  scaffold = jQuery(scaffold)
407
- scaffold.find('td.sorted').each(function(element) {
408
- element.removeClass("sorted");
526
+ scaffold.find('td.sorted').each(function(index, element) {
527
+ jQuery(element).removeClass("sorted");
409
528
  });
410
- scaffold.find('th.sorted').each(function(element) {
529
+ scaffold.find('th.sorted').each(function(index, element) {
530
+ element = jQuery(element);
411
531
  element.removeClass("sorted");
412
532
  element.removeClass("asc");
413
533
  element.removeClass("desc");
@@ -415,213 +535,279 @@ var ActiveScaffold = {
415
535
  },
416
536
  decrement_record_count: function(scaffold) {
417
537
  // decrement the last record count, firsts record count are in nested lists
418
- if (typeof(scaffold) == 'string') scaffold = '#' + scaffold;
419
- scaffold = jQuery(scaffold)
538
+ if (typeof(scaffold) == 'string') scaffold = '#' + scaffold;
539
+ scaffold = jQuery(scaffold);
420
540
  count = scaffold.find('span.active-scaffold-records').last();
421
541
  if (count) count.html(parseInt(count.html(), 10) - 1);
422
542
  },
423
543
  increment_record_count: function(scaffold) {
424
544
  // increment the last record count, firsts record count are in nested lists
425
545
  if (typeof(scaffold) == 'string') scaffold = '#' + scaffold;
426
- scaffold = jQuery(scaffold)
546
+ scaffold = jQuery(scaffold);
427
547
  count = scaffold.find('span.active-scaffold-records').last();
428
548
  if (count) count.html(parseInt(count.html(), 10) + 1);
429
549
  },
430
550
  update_row: function(row, html) {
431
551
  var even_row = false;
432
552
  var replaced = null;
433
- if (typeof(row) == 'string') row = '#' + row;
553
+ if (typeof(row) == 'string') row = '#' + row;
434
554
  row = jQuery(row);
435
555
  if (row.hasClass('even-record')) even_row = true;
436
556
 
437
557
  replaced = this.replace(row, html);
438
- if (even_row === true) replaced.addClass('even-record');
439
- ActiveScaffold.highlight(replaced);
558
+ if (replaced) {
559
+ if (even_row === true) replaced.addClass('even-record');
560
+ ActiveScaffold.highlight(replaced);
561
+ }
440
562
  },
441
-
563
+
442
564
  replace: function(element, html) {
443
- if (typeof(element) == 'string') element = '#' + element;
565
+ if (typeof(element) == 'string') element = '#' + element;
566
+ element = jQuery(element);
567
+ var new_element = typeof(html) == 'string' ? jQuery.parseHTML(jQuery.trim(html), true) : html;
568
+ new_element = jQuery(new_element);
569
+ if (element.length) {
570
+ element.replaceWith(new_element);
571
+ new_element.trigger('as:element_updated');
572
+ return new_element;
573
+ } else return null;
574
+ },
575
+
576
+ replace_html: function(element, html) {
577
+ if (typeof(element) == 'string') element = '#' + element;
444
578
  element = jQuery(element);
445
- element.replaceWith(html);
446
- if (element.attr('id')) {
447
- element = jQuery('#' + element.attr('id'));
579
+ if (element.length) {
580
+ element.html(html);
581
+ element.trigger('as:element_updated');
448
582
  }
449
583
  return element;
450
584
  },
451
-
452
- replace_html: function(element, html) {
453
- if (typeof(element) == 'string') element = '#' + element;
585
+
586
+ append: function(element, html) {
587
+ if (typeof(element) == 'string') element = '#' + element;
454
588
  element = jQuery(element);
455
- element.html(html);
589
+ element.append(html);
590
+ element.trigger('as:element_updated');
456
591
  return element;
457
592
  },
458
-
459
- remove: function(element) {
460
- if (typeof(element) == 'string') element = '#' + element;
461
- jQuery(element).remove();
593
+
594
+ remove: function(element, callback) {
595
+ if (typeof(element) == 'string') element = '#' + element;
596
+ jQuery(element).trigger('as:element_removed').remove();
597
+ if (callback) callback();
598
+ },
599
+
600
+ update_inplace_edit: function(element, value, empty) {
601
+ if (typeof(element) == 'string') element = '#' + element;
602
+ this.replace_html(jQuery(element), value);
603
+ jQuery(element).closest('td')[empty ? 'addClass' : 'removeClass']('empty');
462
604
  },
463
-
605
+
464
606
  hide: function(element) {
465
607
  if (typeof(element) == 'string') element = '#' + element;
466
608
  jQuery(element).hide();
467
609
  },
468
-
610
+
469
611
  show: function(element) {
470
612
  if (typeof(element) == 'string') element = '#' + element;
471
613
  jQuery(element).show();
472
614
  },
473
-
615
+
474
616
  reset_form: function(element) {
475
617
  if (typeof(element) == 'string') element = '#' + element;
476
618
  jQuery(element).get(0).reset();
477
619
  },
478
-
479
- disable_form: function(as_form) {
620
+
621
+ disable_form: function(as_form, skip_loading_indicator) {
480
622
  if (typeof(as_form) == 'string') as_form = '#' + as_form;
481
623
  as_form = jQuery(as_form)
482
624
  var loading_indicator = jQuery('#' + as_form.attr('id').replace(/-form$/, '-loading-indicator'));
483
- if (loading_indicator) loading_indicator.css('visibility','visible');
625
+ if (!skip_loading_indicator && loading_indicator) loading_indicator.css('visibility','visible');
484
626
  jQuery('input[type=submit]', as_form).attr('disabled', 'disabled');
485
- as_form[0].disabled_fields = jQuery("input:enabled,select:enabled,textarea:enabled", as_form).attr('disabled', 'disabled');
627
+ jQuery('.sub-form a.destroy', as_form).addClass('disabled');
628
+ if (jQuery.fn.droppable) jQuery('.draggable-list', as_form).sortable('disable');
629
+ // data-remote-disabled attr instead of set data because is used to in selector later
630
+ jQuery("input:enabled,select:enabled,textarea:enabled", as_form).attr('disabled', 'disabled').attr('data-remove-disabled', true);
486
631
  },
487
-
488
- enable_form: function(as_form) {
632
+
633
+ enable_form: function(as_form, skip_loading_indicator) {
489
634
  if (typeof(as_form) == 'string') as_form = '#' + as_form;
490
635
  as_form = jQuery(as_form)
491
636
  var loading_indicator = jQuery('#' + as_form.attr('id').replace(/-form$/, '-loading-indicator'));
492
- if (loading_indicator) loading_indicator.css('visibility','hidden');
637
+ if (!skip_loading_indicator && loading_indicator) loading_indicator.css('visibility','hidden');
493
638
  jQuery('input[type=submit]', as_form).removeAttr('disabled');
494
- as_form[0].disabled_fields.removeAttr('disabled');
495
- },
496
-
497
- focus_first_element_of_form: function(form_element) {
639
+ jQuery('.sub-form a.destroy.disabled', as_form).removeClass('disabled');
640
+ if (jQuery.fn.droppable) jQuery('.draggable-list', as_form).sortable('enable');
641
+ jQuery("input[data-remove-disabled],select[data-remove-disabled],textarea[data-remove-disabled]", as_form).removeAttr('disabled data-remove-disabled');
642
+ },
643
+
644
+ focus_first_element_of_form: function(form_element, form_selector) {
498
645
  if (typeof(form_element) == 'string') form_element = '#' + form_element;
499
- jQuery(form_element + ":first *:input[type!=hidden]:first").focus();
646
+ if (typeof(form_selector) == 'undefined') form_selector = jQuery(form_element).is('form') ? '' : 'form ';
647
+ jQuery(form_selector + ":input:visible:first", jQuery(form_element)).focus();
500
648
  },
501
-
649
+
502
650
  create_record_row: function(active_scaffold_id, html, options) {
503
651
  if (typeof(active_scaffold_id) == 'string') active_scaffold_id = '#' + active_scaffold_id;
504
- tbody = jQuery(active_scaffold_id).find('tbody.records');
505
-
652
+ tbody = jQuery(active_scaffold_id).find('tbody.records').first();
653
+ var new_row;
654
+
506
655
  if (options.insert_at == 'top') {
507
656
  tbody.prepend(html);
508
- var new_row = tbody.children('tr.record:first-child');
657
+ new_row = tbody.children('tr.record:first-child');
509
658
  } else if (options.insert_at == 'bottom') {
510
659
  var rows = tbody.children('tr.record, tr.inline-adapter');
511
- var new_row = null;
512
660
  if (rows.length > 0) {
513
661
  new_row = rows.last().after(html).next();
514
662
  } else {
515
663
  new_row = tbody.append(html).children().last();
516
664
  }
665
+ } else if (typeof options.insert_at == 'object') {
666
+ var insert_method, get_method, row, id;
667
+ if (options.insert_at.after) {
668
+ insert_method = 'after';
669
+ get_method = 'next';
670
+ } else {
671
+ insert_method = 'before';
672
+ get_method = 'prev';
673
+ }
674
+ if (id = options.insert_at[insert_method]) row = tbody.children('#' + id);
675
+ if (row && row.length) {
676
+ new_row = row[insert_method](html)[get_method]();
677
+ }
517
678
  }
518
679
  this.stripe(tbody);
519
680
  this.hide_empty_message(tbody);
520
681
  this.increment_record_count(tbody.closest('div.active-scaffold'));
521
- ActiveScaffold.highlight(new_row);
682
+ this.highlight(new_row);
683
+ new_row.trigger('as:element_created');
684
+ },
685
+
686
+ create_record_row_from_url: function(action_link, url, options) {
687
+ jQuery.get(url, function(row) {
688
+ ActiveScaffold.create_record_row(action_link.scaffold(), row, options);
689
+ action_link.close();
690
+ });
522
691
  },
523
-
692
+
524
693
  delete_record_row: function(row, page_reload_url) {
525
694
  if (typeof(row) == 'string') row = '#' + row;
526
695
  row = jQuery(row);
527
696
  var tbody = row.closest('tbody.records');
528
-
529
- var current_action_node = row.find('td.actions a.disabled').first();
530
- if (current_action_node) {
531
- var action_link = ActiveScaffold.ActionLink.get(current_action_node);
532
- if (action_link) {
533
- action_link.close_previous_adapter();
534
- }
535
- }
536
-
537
- row.remove();
538
- this.stripe(tbody);
539
- this.decrement_record_count(tbody.closest('div.active-scaffold'));
540
- this.reload_if_empty(tbody, page_reload_url);
697
+
698
+ row.find('a.disabled').each(function() {;
699
+ var action_link = ActiveScaffold.ActionLink.get(this);
700
+ if (action_link) action_link.close();
701
+ });
702
+
703
+ ActiveScaffold.remove(row, function() {
704
+ ActiveScaffold.stripe(tbody);
705
+ ActiveScaffold.decrement_record_count(tbody.closest('div.active-scaffold'));
706
+ if (page_reload_url) ActiveScaffold.reload_if_empty(tbody, page_reload_url);
707
+ });
541
708
  },
542
709
 
543
710
  delete_subform_record: function(record) {
544
711
  if (typeof(record) == 'string') record = '#' + record;
545
- record = jQuery(record);
546
- var errors = record.prev();
547
- if (errors.hasClass('association-record-errors')) {
548
- this.remove(errors);
549
- }
550
- var associated = jQuery(record).next();
712
+ record = jQuery(record).closest('.sub-form-record');
551
713
  this.remove(record);
552
- while (associated.hasClass('associated-record')) {
553
- record = associated;
554
- associated = jQuery(record).next();
555
- this.remove(record);
556
- }
557
714
  },
558
715
 
559
- report_500_response: function(active_scaffold_id) {
560
- server_error = jQuery(active_scaffold_id).find('td.messages-container p.server-error');
561
- if (!jQuery(server_error).is(':visible')) {
716
+ report_500_response: function(active_scaffold_id, xhr) {
717
+ var server_error = jQuery(active_scaffold_id).find('td.messages-container p.server-error').first();
718
+ if (server_error.is(':visible')) {
719
+ ActiveScaffold.highlight(server_error);
720
+ } else {
562
721
  server_error.show();
563
722
  }
723
+ if (xhr) server_error.find('.error-500')[xhr.status < 500 ? 'hide' : 'show']();
724
+ ActiveScaffold.scroll_to(server_error, ActiveScaffold.config.scroll_on_close == 'checkInViewport');
564
725
  },
565
-
726
+
566
727
  find_action_link: function(element) {
567
728
  if (typeof(element) == 'string') element = '#' + element;
568
- var as_adapter = jQuery(element).closest('.as_adapter');
569
- return ActiveScaffold.ActionLink.get(as_adapter);
729
+ element = jQuery(element);
730
+ return ActiveScaffold.ActionLink.get(element.is('.actions a') ? element : element.closest('.as_adapter'));
570
731
  },
571
-
572
- scroll_to: function(element) {
732
+
733
+ display_dynamic_action_group: function(link, html) {
734
+ var container;
735
+ if (typeof(link) == 'string') link = jQuery('#' + link);
736
+ if (link.closest('td.actions').length) {
737
+ container = link.closest('td').addClass('action_group dyn');
738
+ } else {
739
+ if (link.parent('div.actions').length) link.wrap(jQuery('<div>'));
740
+ container = link.parent().addClass('action_group dyn');
741
+ }
742
+ container.find('> ul').remove();
743
+ container.append(html);
744
+ },
745
+
746
+ scroll_to: function(element, checkInViewport) {
747
+ if (typeof checkInViewport == 'undefined') checkInViewport = true;
573
748
  if (typeof(element) == 'string') element = '#' + element;
574
- var form_offset = jQuery(element).offset(),
575
- destination = form_offset.top;
576
- jQuery(document).scrollTop(destination);
749
+ var form_offset = jQuery(element).offset().top;
750
+ if (checkInViewport) {
751
+ var docViewTop = jQuery(window).scrollTop(),
752
+ docViewBottom = docViewTop + jQuery(window).height();
753
+ // If it's in viewport , don't scroll;
754
+ if (form_offset + jQuery(element).height() <= docViewBottom && form_offset >= docViewTop) return;
755
+ }
756
+
757
+ jQuery(document).scrollTop(form_offset);
577
758
  },
578
-
759
+
579
760
  process_checkbox_inplace_edit: function(checkbox, options) {
580
- var checked = checkbox.is(':checked');
761
+ var checked = checkbox.is(':checked'), td = checkbox.closest('td');
581
762
  if (checked === true) options['params'] += '&value=1';
582
763
  jQuery.ajax({
583
764
  url: options.url,
584
765
  type: "POST",
585
766
  data: options['params'],
586
767
  dataType: options.ajax_data_type,
587
- after: function(request){
768
+ beforeSend: function(request, settings) {
769
+ if (options.beforeSend) options.beforeSend.call(checkbox, request, settings);
588
770
  checkbox.attr('disabled', 'disabled');
771
+ td.closest('tr').find('td.actions .loading-indicator').css('visibility','visible');
589
772
  },
590
773
  complete: function(request){
591
774
  checkbox.removeAttr('disabled');
775
+ },
776
+ success: function(request){
777
+ td.closest('tr').find('td.actions .loading-indicator').css('visibility','hidden');
592
778
  }
593
779
  });
594
780
  },
595
-
781
+
596
782
  read_inplace_edit_heading_attributes: function(column_heading, options) {
597
- if (column_heading.attr('data-ie_cancel_text')) options.cancel_button = '<button class="inplace_cancel">' + column_heading.attr('data-ie_cancel_text') + "</button>";
598
- if (column_heading.attr('data-ie_loading_text')) options.loading_text = column_heading.attr('data-ie_loading_text');
599
- if (column_heading.attr('data-ie_saving_text')) options.saving_text = column_heading.attr('data-ie_saving_text');
600
- if (column_heading.attr('data-ie_save_text')) options.save_button = '<button class="inplace_save">' + column_heading.attr('data-ie_save_text') + "</button>";
601
- if (column_heading.attr('data-ie_rows')) options.textarea_rows = column_heading.attr('data-ie_rows');
602
- if (column_heading.attr('data-ie_cols')) options.textarea_cols = column_heading.attr('data-ie_cols');
603
- if (column_heading.attr('data-ie_size')) options.text_size = column_heading.attr('data-ie_size');
604
- },
605
-
783
+ if (column_heading.data('ie-cancel-text')) options.cancel_button = '<button class="inplace_cancel">' + column_heading.data('ie-cancel-text') + "</button>";
784
+ if (column_heading.data('ie-loading-text')) options.loading_text = column_heading.data('ie-loading-text');
785
+ if (column_heading.data('ie-saving-text')) options.saving_text = column_heading.data('ie-saving-text');
786
+ if (column_heading.data('ie-save-text')) options.save_button = '<button class="inplace_save">' + column_heading.data('ie-save-text') + "</button>";
787
+ if (column_heading.data('ie-rows')) options.textarea_rows = column_heading.data('ie-rows');
788
+ if (column_heading.data('ie-cols')) options.textarea_cols = column_heading.data('ie-cols');
789
+ if (column_heading.data('ie-size')) options.text_size = column_heading.data('ie-size');
790
+ },
791
+
606
792
  create_inplace_editor: function(span, options) {
607
793
  span.removeClass('hover');
608
794
  span.editInPlace(options);
609
795
  span.trigger('click.editInPlace');
610
796
  },
611
-
797
+
612
798
  highlight: function(element) {
613
799
  if (typeof(element) == 'string') element = jQuery('#' + element);
614
800
  if (typeof(element.effect) == 'function') {
615
- element.effect("highlight", {}, 3000);
801
+ element.effect("highlight", jQuery.extend({}, ActiveScaffold.config.highlight), 3000);
616
802
  }
617
803
  },
618
-
804
+
619
805
  create_visibility_toggle: function(element, options) {
620
806
  if (typeof(element) == 'string') element = '#' + element;
621
807
  var toggable = jQuery(element);
622
808
  var toggler = toggable.prev();
623
809
  var initial_label = (options.default_visible === true) ? options.hide_label : options.show_label;
624
-
810
+
625
811
  toggler.append(' (<a class="visibility-toggle" href="#">' + initial_label + '</a>)');
626
812
  toggler.children('a').click(function() {
627
813
  toggable.toggle();
@@ -629,34 +815,42 @@ var ActiveScaffold = {
629
815
  return false;
630
816
  });
631
817
  },
632
-
818
+
633
819
  create_associated_record_form: function(element, content, options) {
634
820
  if (typeof(element) == 'string') element = '#' + element;
635
821
  var element = jQuery(element);
822
+ content = jQuery(content);
636
823
  if (options.singular == false) {
637
824
  if (!(options.id && jQuery('#' + options.id).size() > 0)) {
638
- element.append(content);
825
+ var tfoot = element.children('tfoot');
826
+ if (tfoot.length) tfoot.before(content);
827
+ else element.append(content);
639
828
  }
640
829
  } else {
641
- var current = jQuery('#' + element.attr('id') + ' .association-record')
830
+ var current = jQuery('#' + element.attr('id') + ' .sub-form-record')
642
831
  if (current[0]) {
643
832
  this.replace(current[0], content);
644
833
  } else {
645
834
  element.prepend(content);
646
835
  }
647
836
  }
837
+ ActiveScaffold.focus_first_element_of_form(content, '');
838
+ content.trigger('as:element_created');
648
839
  },
649
-
840
+
650
841
  render_form_field: function(source, content, options) {
651
842
  if (typeof(source) == 'string') source = '#' + source;
652
843
  var source = jQuery(source);
653
- var element = source.closest('.association-record');
844
+ var element = source.closest('.sub-form-record'), selector = '';
654
845
  if (element.length == 0) {
655
846
  element = source.closest('form > ol.form');
847
+ selector = 'li';
656
848
  }
657
- element = element.find('.' + options.field_class + ":first");
849
+ // find without entering new subforms
850
+ selector = options.is_subform ? '' : selector + ':not(.sub-form) ';
851
+ element = element.find(selector + '.' + options.field_class).first();
658
852
 
659
- if (element) {
853
+ if (element.length) {
660
854
  if (options.is_subform == false) {
661
855
  this.replace(element.closest('dl'), content);
662
856
  } else {
@@ -664,35 +858,21 @@ var ActiveScaffold = {
664
858
  }
665
859
  }
666
860
  },
667
-
668
- sortable: function(element, controller, options, url_params) {
669
- if (typeof(element) == 'string') element = '#' + element;
670
- var element = jQuery(element);
671
- var sortable_options = {};
672
- if (options.update === true) {
673
- url_params.authenticity_token = jQuery('meta[name=csrf-param]').attr('content');
674
- sortable_options.update = function(event, ui) {
675
- var url = controller + '/' + options.action + '?'
676
- url += jQuery(this).sortable('serialize',{key: encodeURIComponent(jQuery(this).attr('id') + '[]'), expression:/^[^_-](?:[A-Za-z0-9_-]*)-(.*)-row$/});
677
- jQuery.post(url.append_params(url_params));
678
- }
679
- }
680
- element.sortable(sortable_options);
681
- },
682
861
 
683
862
  record_select_onselect: function(edit_associated_url, active_scaffold_id, id){
684
863
  jQuery.ajax({
685
- url: edit_associated_url.split('--ID--').join(id),
864
+ url: edit_associated_url.replace('--ID--', id),
686
865
  error: function(xhr, textStatus, errorThrown){
687
- ActiveScaffold.report_500_response(active_scaffold_id)
866
+ ActiveScaffold.report_500_response(active_scaffold_id, xhr)
688
867
  }
689
868
  });
690
869
  },
691
870
 
692
871
  mark_span: function(span, mark_flag) {
693
- var record_id = span.attr('data-ie_id');
694
- var checkbox = span.find('input[type="checkbox"]').first();
695
- if (mark_flag == false || (typeof(mark_flag) == 'undefined' && !checkbox.checked)) {
872
+ var element = jQuery(span);
873
+ var record_id = element.attr('data-ie_id');
874
+ var checkbox = element.find('input[type="checkbox"]').eq(0);
875
+ if (mark_flag == false || (typeof(mark_flag) == 'undefined' && !checkbox.prop('checked'))) {
696
876
  ActiveScaffold.unmark_record(record_id);
697
877
  } else {
698
878
  ActiveScaffold.mark_record(record_id);
@@ -701,11 +881,11 @@ var ActiveScaffold = {
701
881
  },
702
882
 
703
883
  mark_records: function(tbody_id, mark_flag) {
704
- var spans = $('#' + tbody_id + ' > tr.record td.marked-column span.mark_record_field');
884
+ var spans = jQuery('#' + tbody_id + ' > tr.record td.marked-column span.mark_record_field');
705
885
  var checkbox;
706
886
  for (var i = 0; i < spans.length; i++) {
707
887
  checkbox = ActiveScaffold.mark_span(spans[i], mark_flag);
708
- checkbox.checked = mark_flag;
888
+ checkbox.prop('checked', mark_flag);
709
889
  }
710
890
  },
711
891
 
@@ -724,12 +904,21 @@ var ActiveScaffold = {
724
904
  },
725
905
 
726
906
  in_place_editor_field_clicked: function(span) {
727
- span.data(); // $ 1.4.2 workaround
907
+ // test editor is open
728
908
  if (typeof(span.data('editInPlace')) === 'undefined') {
729
909
  var options = {show_buttons: true,
730
910
  hover_class: 'hover',
731
911
  element_id: 'editor_id',
732
912
  ajax_data_type: "script",
913
+ delegate: {
914
+ willCloseEditInPlace: function(span, options) {
915
+ if (span.data('addEmptyOnCancel')) span.closest('td').addClass('empty');
916
+ span.closest('tr').find('td.actions .loading-indicator').css('visibility','visible');
917
+ },
918
+ didCloseEditInPlace: function(span, options) {
919
+ span.closest('tr').find('td.actions .loading-indicator').css('visibility','hidden');
920
+ }
921
+ },
733
922
  update_value: 'value'},
734
923
  csrf_param = jQuery('meta[name=csrf-param]').first(),
735
924
  csrf_token = jQuery('meta[name=csrf-token]').first(),
@@ -737,7 +926,7 @@ var ActiveScaffold = {
737
926
  column_heading = null;
738
927
 
739
928
  if(!(my_parent.is('td') || my_parent.is('th'))){
740
- my_parent = span.parents('td').eq(0);
929
+ my_parent = span.parents('td').eq(0);
741
930
  }
742
931
 
743
932
  if (my_parent.is('td')) {
@@ -747,25 +936,25 @@ var ActiveScaffold = {
747
936
  column_heading = my_parent;
748
937
  }
749
938
 
750
- var render_url = column_heading.attr('data-ie_render_url'),
751
- mode = column_heading.attr('data-ie_mode'),
752
- record_id = span.attr('data-ie_id');
939
+ var render_url = column_heading.data('ie-render-url'),
940
+ mode = column_heading.data('ie-mode'),
941
+ record_id = span.data('ie-id') || '';
753
942
 
754
943
  ActiveScaffold.read_inplace_edit_heading_attributes(column_heading, options);
755
944
 
756
- if (span.attr('data-ie_url')) {
757
- options.url = span.attr('data-ie_url').replace(/__id__/, record_id);
945
+ if (span.data('ie-url')) {
946
+ options.url = span.data('ie-url').replace(/__id__/, record_id);
758
947
  } else {
759
- options.url = column_heading.attr('data-ie_url').replace(/__id__/, record_id);
948
+ options.url = column_heading.data('ie-url').replace(/__id__/, record_id);
760
949
  }
761
950
 
762
951
  if (csrf_param) options['params'] = csrf_param.attr('content') + '=' + csrf_token.attr('content');
763
952
 
764
- if (span.closest('div.active-scaffold').attr('data-eid')) {
953
+ if (span.closest('div.active-scaffold').data('eid')) {
765
954
  if (options['params'].length > 0) {
766
955
  options['params'] += "&";
767
956
  }
768
- options['params'] += ("eid=" + span.closest('div.active-scaffold').attr('data-eid'));
957
+ options['params'] += ("eid=" + span.closest('div.active-scaffold').data('eid'));
769
958
  }
770
959
 
771
960
  if (mode === 'clone') {
@@ -776,9 +965,29 @@ var ActiveScaffold = {
776
965
 
777
966
  if (render_url) {
778
967
  var plural = false;
779
- if (column_heading.attr('data-ie_plural')) plural = true;
968
+ if (column_heading.data('ie-plural')) plural = true;
780
969
  options.field_type = 'remote';
781
970
  options.editor_url = render_url.replace(/__id__/, record_id)
971
+ if (!options.delegate) options.delegate = {}
972
+ options.delegate.didOpenEditInPlace = function(dom) { dom.trigger('as:element_updated'); }
973
+ }
974
+ var actions, forms;
975
+ options.beforeSend = function(xhr, settings) {
976
+ switch (span.data('ie-update')) {
977
+ case 'update_row':
978
+ actions = span.closest('tr').find('.actions a:not(.disabled)').addClass('disabled');
979
+ break;
980
+ case 'update_table':
981
+ var table = span.closest('.as_content');
982
+ actions = table.find('.actions a:not(.disabled)').addClass('disabled');
983
+ forms = table.find('.as_form');
984
+ ActiveScaffold.disable_form(forms);
985
+ break;
986
+ }
987
+ }
988
+ options.error = options.success = function() {
989
+ if (actions) actions.removeClass('disabled');
990
+ if (forms) ActiveScaffold.enable_form(forms);
782
991
  }
783
992
  if (mode === 'inline_checkbox') {
784
993
  ActiveScaffold.process_checkbox_inplace_edit(span.find('input:checkbox'), options);
@@ -787,18 +996,21 @@ var ActiveScaffold = {
787
996
  }
788
997
  }
789
998
  },
790
-
791
- update_column: function(element, url, send_form, source_id, val) {
999
+
1000
+ update_column: function(element, url, send_form, source_id, val, additional_params) {
792
1001
  if (!element) element = jQuery('#' + source_id);
793
1002
  var as_form = element.closest('form.as_form');
794
1003
  var params = null;
795
1004
 
796
1005
  if (send_form) {
797
- var selector;
1006
+ var selector, base = as_form;
1007
+ if (send_form == 'row') base = element.closest('.association-record, form');
798
1008
  if (selector = element.data('update_send_form_selector'))
799
- params = as_form.find(selector).serialize();
800
- else params = as_form.serialize();
801
- params += '&' + jQuery.param({"source_id": source_id});
1009
+ params = base.find(selector).serialize();
1010
+ else if (base != as_form) params = base.find(':input').serialize();
1011
+ else params = base.serialize();
1012
+ params += '&_method=&' + jQuery.param({"source_id": source_id});
1013
+ if (additional_params) params += '&' + additional_params;
802
1014
  } else {
803
1015
  params = {value: val};
804
1016
  params.source_id = source_id;
@@ -807,25 +1019,54 @@ var ActiveScaffold = {
807
1019
  jQuery.ajax({
808
1020
  url: url,
809
1021
  data: params,
810
- beforeSend: function(event) {
1022
+ type: 'post',
1023
+ beforeSend: function(xhr, settings) {
811
1024
  element.nextAll('img.loading-indicator').css('visibility','visible');
812
1025
  ActiveScaffold.disable_form(as_form);
1026
+ if ($.rails.fire(element, 'ajax:beforeSend', [xhr, settings])) {
1027
+ element.trigger('ajax:send', xhr);
1028
+ } else {
1029
+ return false;
1030
+ }
813
1031
  },
814
- complete: function(event) {
1032
+ success: function(data, status, xhr) {
1033
+ as_form.find('#'+element.attr('id')).trigger('ajax:success', [data, status, xhr]);
1034
+ },
1035
+ complete: function(xhr, status) {
1036
+ element = as_form.find('#'+element.attr('id'));
815
1037
  element.nextAll('img.loading-indicator').css('visibility','hidden');
816
- ActiveScaffold.enable_form(as_form);
1038
+ element.trigger('ajax:complete', [xhr, status]);
1039
+ if (ActiveScaffold.last_focus) jQuery(ActiveScaffold.last_focus).focus().select();
817
1040
  },
818
1041
  error: function (xhr, status, error) {
1042
+ element = as_form.find('#'+element.attr('id'));
819
1043
  var as_div = element.closest("div.active-scaffold");
820
- if (as_div) {
821
- ActiveScaffold.report_500_response(as_div);
822
- }
1044
+ if (as_div) ActiveScaffold.report_500_response(as_div, xhr);
1045
+ element.trigger('ajax:error', [xhr, status, error]);
823
1046
  }
824
1047
  });
825
1048
  },
826
-
827
- draggable_lists: function(element) {
828
- jQuery('#' + element).draggable_lists();
1049
+
1050
+ draggable_lists: function(selector_or_elements, parent) {
1051
+ var elements;
1052
+ if (!jQuery.fn.draggableLists) return;
1053
+ if (typeof(selector_or_elements) == 'string') elements = jQuery(selector_or_elements, parent);
1054
+ else elements = jQuery(selector_or_elements);
1055
+ elements.draggableLists();
1056
+ },
1057
+
1058
+ setup_warn_changes: function() {
1059
+ var need_confirm = false;
1060
+ var unload_message = $('meta[name=unload-message]').attr('content') || ActiveScaffold.config.unload_message || "This page contains unsaved data that will be lost if you leave this page.";
1061
+ $(document).on('change input', '.active-scaffold form:not(.search) input, .active-scaffold form:not(.search) textarea, .active-scaffold form:not(.search) select', function() {
1062
+ $(this).closest('form').addClass('need-confirm');
1063
+ });
1064
+ $(document).on('click', '.active-scaffold .as_cancel:not([data-remote])', function() {
1065
+ $(this).closest('form').removeClass('need-confirm');
1066
+ });
1067
+ window.onbeforeunload = function() {
1068
+ if ($('form.need-confirm').length) return unload_message;
1069
+ }
829
1070
  }
830
1071
  }
831
1072
 
@@ -854,8 +1095,8 @@ String.prototype.append_params = function(params) {
854
1095
  for(var key in params) {
855
1096
  if (key) url += (key + '=' + params[key] + '&');
856
1097
  }
857
-
858
- // the loop leaves a comma dangling at the end of string, chop it off
1098
+
1099
+ // the loop leaves a comma dangling at the end of string, chop it off
859
1100
  url = url.substring(0, url.length-1);
860
1101
  return url;
861
1102
  };
@@ -870,7 +1111,7 @@ ActiveScaffold.Actions.Abstract = Class.extend({
870
1111
  this.target = jQuery(target);
871
1112
  this.loading_indicator = jQuery(loading_indicator);
872
1113
  this.options = options;
873
- var _this = this;
1114
+ var _this = this;
874
1115
  this.links = jQuery.map(links, function(link) {
875
1116
  var my_link = _this.instantiate_link(link);
876
1117
  return my_link;
@@ -894,19 +1135,19 @@ ActiveScaffold.ActionLink = {
894
1135
  element.data(); // $ 1.4.2 workaround
895
1136
  if (typeof(element.data('action_link')) === 'undefined' && !element.hasClass('as_adapter')) {
896
1137
  var parent = element.closest('.actions');
897
- if (parent.length === 0) {
1138
+ if (parent.length === 0 || parent.is('td')) {
898
1139
  // maybe an column action_link
899
- parent = element.parent();
1140
+ parent = element.closest('tr.record');
900
1141
  }
901
- if (parent && parent.is('td')) {
1142
+ if (parent.is('tr')) {
902
1143
  // record action
903
- parent = parent.closest('tr.record');
904
1144
  var target = parent.find('a.as_action');
905
1145
  var loading_indicator = parent.find('td.actions .loading-indicator');
1146
+ if (!loading_indicator.length) loading_indicator = element.parent().find('.loading-indicator');
906
1147
  new ActiveScaffold.Actions.Record(target, parent, loading_indicator);
907
1148
  } else if (parent && parent.is('div')) {
908
1149
  //table action
909
- new ActiveScaffold.Actions.Table(parent.find('a.as_action'), parent.closest('div.active-scaffold').find('tbody.before-header'), parent.find('.loading-indicator'));
1150
+ new ActiveScaffold.Actions.Table(parent.find('a.as_action'), parent.closest('div.active-scaffold').find('tbody.before-header').first(), parent.find('.loading-indicator').first());
910
1151
  }
911
1152
  element = jQuery(element);
912
1153
  }
@@ -920,29 +1161,34 @@ ActiveScaffold.ActionLink.Abstract = Class.extend({
920
1161
  init: function(a, target, loading_indicator) {
921
1162
  this.tag = jQuery(a);
922
1163
  this.url = this.tag.attr('href');
923
- this.method = this.tag.attr('data-method') || 'get';
1164
+ this.method = this.tag.data('method') || 'get';
924
1165
  this.target = target;
925
1166
  this.loading_indicator = loading_indicator;
926
1167
  this.hide_target = false;
927
- this.position = this.tag.attr('data-position');
928
- this.action = this.tag.attr('data-action');
1168
+ this.position = this.tag.data('position');
1169
+ this.action = this.tag.data('action');
929
1170
 
930
1171
  this.tag.data('action_link', this);
931
1172
  return this;
932
1173
  },
933
1174
 
934
1175
  open: function(event) {
1176
+ this.tag.click();
935
1177
  },
936
-
1178
+
937
1179
  insert: function(content) {
938
1180
  throw 'unimplemented'
939
1181
  },
940
1182
 
941
1183
  close: function() {
942
- this.enable();
943
- this.adapter.remove();
944
- if (this.hide_target) this.target.show();
945
- if (ActiveScaffold.config.scroll_on_close) ActiveScaffold.scroll_to(this.target);
1184
+ if (this.adapter) {
1185
+ var link = this;
1186
+ ActiveScaffold.remove(this.adapter, function() {
1187
+ link.enable();
1188
+ if (link.hide_target) link.target.show();
1189
+ if (ActiveScaffold.config.scroll_on_close) ActiveScaffold.scroll_to(link.target.attr('id'), ActiveScaffold.config.scroll_on_close == 'checkInViewport');
1190
+ });
1191
+ }
946
1192
  },
947
1193
 
948
1194
  reload: function() {
@@ -976,7 +1222,7 @@ ActiveScaffold.ActionLink.Abstract = Class.extend({
976
1222
  scaffold: function() {
977
1223
  return this.tag.closest('div.active-scaffold');
978
1224
  },
979
-
1225
+
980
1226
  update_flash_messages: function(messages) {
981
1227
  message_node = jQuery(this.scaffold_id().replace(/-active-scaffold/, '-messages'));
982
1228
  if (message_node) message_node.html(messages);
@@ -985,7 +1231,10 @@ ActiveScaffold.ActionLink.Abstract = Class.extend({
985
1231
  this.adapter = element;
986
1232
  this.adapter.addClass('as_adapter');
987
1233
  this.adapter.data('action_link', this);
988
- if (this.refresh_url) jQuery('.as_cancel[data-refresh=true]', this.adapter).attr('href', this.refresh_url);
1234
+ if (this.refresh_url) jQuery('.as_cancel', this.adapter).attr('href', this.refresh_url);
1235
+ },
1236
+ keep_open: function() {
1237
+ return this.tag.data('keep-open');
989
1238
  }
990
1239
  });
991
1240
 
@@ -995,9 +1244,9 @@ ActiveScaffold.ActionLink.Abstract = Class.extend({
995
1244
  ActiveScaffold.Actions.Record = ActiveScaffold.Actions.Abstract.extend({
996
1245
  instantiate_link: function(link) {
997
1246
  var l = new ActiveScaffold.ActionLink.Record(link, this.target, this.loading_indicator);
998
- var refresh = this.target.attr('data-refresh');
999
- if (refresh) l.refresh_url = refresh;
1000
-
1247
+ var refresh = this.target.data('refresh');
1248
+ if (refresh) l.refresh_url = this.target.closest('.records').data('refresh-record').replace('--ID--', refresh);
1249
+
1001
1250
  if (l.position) {
1002
1251
  l.url = l.url.append_params({adapter: '_list_inline_adapter'});
1003
1252
  l.tag.attr('href', l.url);
@@ -1011,9 +1260,8 @@ ActiveScaffold.ActionLink.Record = ActiveScaffold.ActionLink.Abstract.extend({
1011
1260
  close_previous_adapter: function() {
1012
1261
  var _this = this;
1013
1262
  jQuery.each(this.set.links, function(index, item) {
1014
- if (item.url != _this.url && item.is_disabled() && item.adapter) {
1015
- item.enable();
1016
- item.adapter.remove();
1263
+ if (item.url != _this.url && item.is_disabled() && !item.keep_open() && item.adapter) {
1264
+ ActiveScaffold.remove(item.adapter, function () { item.enable(); });
1017
1265
  }
1018
1266
  });
1019
1267
  },
@@ -1026,6 +1274,11 @@ ActiveScaffold.ActionLink.Record = ActiveScaffold.ActionLink.Abstract.extend({
1026
1274
  this.hide_target = true;
1027
1275
  }
1028
1276
 
1277
+ var colspan = this.target.children().length;
1278
+ if (content && this.position) {
1279
+ content = jQuery(content);
1280
+ content.find('.inline-adapter-cell:first').attr('colspan', colspan);
1281
+ }
1029
1282
  if (this.position == 'after') {
1030
1283
  this.target.after(content);
1031
1284
  this.set_adapter(this.target.next());
@@ -1037,14 +1290,22 @@ ActiveScaffold.ActionLink.Record = ActiveScaffold.ActionLink.Abstract.extend({
1037
1290
  else {
1038
1291
  return false;
1039
1292
  }
1293
+ ActiveScaffold.focus_first_element_of_form(this.adapter);
1040
1294
  ActiveScaffold.highlight(this.adapter.find('td'));
1041
1295
  },
1042
1296
 
1043
- close: function(refreshed_content) {
1044
- if (refreshed_content) {
1045
- ActiveScaffold.update_row(this.target, refreshed_content);
1046
- }
1297
+ close: function(refreshed_content_or_reload) {
1047
1298
  this._super();
1299
+ if (refreshed_content_or_reload) {
1300
+ if (typeof refreshed_content_or_reload == 'string') {
1301
+ ActiveScaffold.update_row(this.target, refreshed_content_or_reload);
1302
+ } else if (this.refresh_url) {
1303
+ var target = this.target;
1304
+ jQuery.get(this.refresh_url, function(e, status, response) {
1305
+ ActiveScaffold.update_row(target, response.responseText);
1306
+ });
1307
+ }
1308
+ }
1048
1309
  },
1049
1310
 
1050
1311
  enable: function() {
@@ -1062,7 +1323,7 @@ ActiveScaffold.ActionLink.Record = ActiveScaffold.ActionLink.Abstract.extend({
1062
1323
  item.tag.addClass('disabled');
1063
1324
  });
1064
1325
  },
1065
-
1326
+
1066
1327
  set_opened: function() {
1067
1328
  if (this.position == 'after') {
1068
1329
  this.set_adapter(this.target.next());
@@ -1097,6 +1358,7 @@ ActiveScaffold.ActionLink.Table = ActiveScaffold.ActionLink.Abstract.extend({
1097
1358
  else {
1098
1359
  throw 'Unknown position "' + this.position + '"'
1099
1360
  }
1361
+ ActiveScaffold.focus_first_element_of_form(this.adapter);
1100
1362
  ActiveScaffold.highlight(this.adapter.find('td').first().children());
1101
1363
  }
1102
1364
  });