active_scaffold-sequel 0.5.1 → 0.6.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/app/assets/javascripts/jquery/active_scaffold.js +67 -22
- data/app/assets/javascripts/prototype/active_scaffold.js +76 -25
- data/doc/README.mark +30 -0
- data/frontends/default/views/update_column.js.erb +14 -16
- data/lib/active_scaffold/actions/core.rb +1 -4
- data/lib/active_scaffold/actions/delete.rb +0 -1
- data/lib/active_scaffold/actions/mark.rb +4 -62
- data/lib/active_scaffold/actions/update.rb +17 -9
- data/lib/active_scaffold/config/list.rb +0 -7
- data/lib/active_scaffold/config/mark.rb +1 -10
- data/lib/active_scaffold/data_structures/columns.rb +8 -4
- data/lib/active_scaffold/helpers/list_column_helpers.rb +12 -17
- data/lib/active_scaffold/helpers/view_helpers.rb +3 -0
- data/lib/active_scaffold/marked_model.rb +4 -29
- data/lib/active_scaffold/version.rb +2 -2
- metadata +177 -155
- data/frontends/default/views/on_mark_all.js.erb +0 -12
@@ -38,6 +38,29 @@ jQuery(document).ready(function() {
|
|
38
38
|
}
|
39
39
|
return true;
|
40
40
|
});
|
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
|
+
});
|
41
64
|
jQuery('a.as_action').live('ajax:success', function(event, response) {
|
42
65
|
var action_link = ActiveScaffold.ActionLink.get(jQuery(this));
|
43
66
|
if (action_link) {
|
@@ -111,7 +134,7 @@ jQuery(document).ready(function() {
|
|
111
134
|
ActiveScaffold.report_500_response(as_scaffold);
|
112
135
|
return true;
|
113
136
|
});
|
114
|
-
jQuery('span.in_place_editor_field').live('hover', function(event) {
|
137
|
+
jQuery('span.mark_record_field,span.mark_heading,span.in_place_editor_field').live('hover', function(event) {
|
115
138
|
jQuery(this).data(); // $ 1.4.2 workaround
|
116
139
|
if (event.type == 'mouseenter') {
|
117
140
|
if (typeof(jQuery(this).data('editInPlace')) === 'undefined') jQuery(this).addClass("hover");
|
@@ -121,6 +144,19 @@ jQuery(document).ready(function() {
|
|
121
144
|
}
|
122
145
|
return true;
|
123
146
|
});
|
147
|
+
jQuery('span.mark_record_field').live('click', function(event) {
|
148
|
+
ActiveScaffold.mark_span(jQuery(this));
|
149
|
+
});
|
150
|
+
jQuery('span.mark_heading').live('click', function(event) {
|
151
|
+
var span = jQuery(this);
|
152
|
+
var checkbox = span.find('input[type="checkbox"]').first();
|
153
|
+
var tbody_id = span.attr('data-tbody_id');
|
154
|
+
if (checkbox.checked) {
|
155
|
+
ActiveScaffold.mark_records(tbody_id, true);
|
156
|
+
} else {
|
157
|
+
ActiveScaffold.mark_records(tbody_id, false);
|
158
|
+
}
|
159
|
+
});
|
124
160
|
jQuery('span.in_place_editor_field').live('click', function(event) {
|
125
161
|
ActiveScaffold.in_place_editor_field_clicked(jQuery(this));
|
126
162
|
});
|
@@ -653,28 +689,37 @@ var ActiveScaffold = {
|
|
653
689
|
});
|
654
690
|
},
|
655
691
|
|
656
|
-
|
657
|
-
|
658
|
-
|
659
|
-
|
660
|
-
|
661
|
-
|
662
|
-
|
663
|
-
|
664
|
-
|
665
|
-
|
666
|
-
|
667
|
-
|
668
|
-
|
669
|
-
|
670
|
-
|
671
|
-
|
672
|
-
|
673
|
-
|
674
|
-
|
675
|
-
|
692
|
+
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)) {
|
696
|
+
ActiveScaffold.unmark_record(record_id);
|
697
|
+
} else {
|
698
|
+
ActiveScaffold.mark_record(record_id);
|
699
|
+
}
|
700
|
+
return checkbox;
|
701
|
+
},
|
702
|
+
|
703
|
+
mark_records: function(tbody_id, mark_flag) {
|
704
|
+
var spans = $('#' + tbody_id + ' > tr.record td.marked-column span.mark_record_field');
|
705
|
+
var checkbox;
|
706
|
+
for (var i = 0; i < spans.length; i++) {
|
707
|
+
checkbox = ActiveScaffold.mark_span(spans[i], mark_flag);
|
708
|
+
checkbox.checked = mark_flag;
|
709
|
+
}
|
710
|
+
},
|
711
|
+
|
712
|
+
marked_records: [],
|
713
|
+
|
714
|
+
mark_record: function(record_id) {
|
715
|
+
ActiveScaffold.marked_records.push(record_id);
|
716
|
+
},
|
717
|
+
|
718
|
+
unmark_record: function(record_id) {
|
719
|
+
for (var i = ActiveScaffold.marked_records.length - 1; i >= 0; i--) {
|
720
|
+
if (ActiveScaffold.marked_records[i] == record_id) {
|
721
|
+
ActiveScaffold.marked_records.splice(i, 1);
|
676
722
|
}
|
677
|
-
mark_all_checkbox.attr('value', ('' + !options.checked));
|
678
723
|
}
|
679
724
|
},
|
680
725
|
|
@@ -61,6 +61,29 @@ document.observe("dom:loaded", function() {
|
|
61
61
|
}
|
62
62
|
return true;
|
63
63
|
});
|
64
|
+
document.on('ajax:before', 'a.as_action.marked_records_action', function(event) {
|
65
|
+
var action_link = event.findElement();
|
66
|
+
var marked_records = 'marked_records=' + ActiveScaffold.marked_records.join('%2C');
|
67
|
+
var regexp = /(\?|&)marked_records=[^&]*/g;
|
68
|
+
var match;
|
69
|
+
if (action_link.search[0] == '?') {
|
70
|
+
match = regexp.exec(action_link.search);
|
71
|
+
if (match) {
|
72
|
+
action_link.search = action_link.search.slice(0, match.index) + match[1] + marked_records + action_link.search.slice(regexp.lastIndex, action_link.search.length);
|
73
|
+
} else {
|
74
|
+
action_link.search = action_link.search + '&' + marked_records;
|
75
|
+
}
|
76
|
+
} else {
|
77
|
+
action_link.search = '?' + marked_records;
|
78
|
+
}
|
79
|
+
return true;
|
80
|
+
});
|
81
|
+
document.on('ajax:complete', 'a.as_action.marked_records_action', function(event) {
|
82
|
+
var action_link = event.findElement();
|
83
|
+
ActiveScaffold.mark_records(action_link.readAttribute('data-tbody_id'), false);
|
84
|
+
ActiveScaffold.marked_records = [];
|
85
|
+
return true;
|
86
|
+
});
|
64
87
|
document.on('ajax:success', 'a.as_action', function(event) {
|
65
88
|
var action_link = ActiveScaffold.ActionLink.get(event.findElement());
|
66
89
|
if (action_link && event.memo && event.memo.request) {
|
@@ -135,15 +158,28 @@ document.observe("dom:loaded", function() {
|
|
135
158
|
ActiveScaffold.report_500_response(as_scaffold);
|
136
159
|
return true;
|
137
160
|
});
|
138
|
-
document.on('mouseover', 'span.in_place_editor_field', function(event) {
|
161
|
+
document.on('mouseover', 'span.mark_record_field,span.mark_heading,span.in_place_editor_field', function(event) {
|
139
162
|
event.findElement().addClassName('hover');
|
140
163
|
});
|
141
|
-
document.on('mouseout', 'span.in_place_editor_field', function(event) {
|
164
|
+
document.on('mouseout', 'span.mark_record_field,span.mark_heading,span.in_place_editor_field', function(event) {
|
142
165
|
event.findElement().removeClassName('hover');
|
143
166
|
});
|
167
|
+
document.on('click', 'span.mark_record_field', function(event) {
|
168
|
+
ActiveScaffold.mark_span(event.findElement('span.mark_record_field'));
|
169
|
+
});
|
170
|
+
document.on('click', 'span.mark_heading', function(event) {
|
171
|
+
var span = event.findElement('span.mark_heading');
|
172
|
+
var checkbox = span.down('input[type="checkbox"]');
|
173
|
+
var tbody_id = span.readAttribute('data-tbody_id');
|
174
|
+
if (checkbox.checked) {
|
175
|
+
ActiveScaffold.mark_records(tbody_id, true);
|
176
|
+
} else {
|
177
|
+
ActiveScaffold.mark_records(tbody_id, false);
|
178
|
+
}
|
179
|
+
});
|
144
180
|
document.on('click', 'span.in_place_editor_field', function(event) {
|
145
181
|
var span = event.findElement('span.in_place_editor_field');
|
146
|
-
|
182
|
+
|
147
183
|
if (typeof(span.inplace_edit) === 'undefined') {
|
148
184
|
var options = {htmlResponse: false,
|
149
185
|
onEnterHover: null,
|
@@ -159,14 +195,14 @@ document.observe("dom:loaded", function() {
|
|
159
195
|
if(!(my_parent.nodeName.toLowerCase() === 'td' || my_parent.nodeName.toLowerCase() === 'th')){
|
160
196
|
my_parent = span.up('td');
|
161
197
|
}
|
162
|
-
|
198
|
+
|
163
199
|
if (my_parent.nodeName.toLowerCase() === 'td') {
|
164
200
|
var heading_selector = '.' + span.up().readAttribute('class').split(' ')[0] + '_heading';
|
165
201
|
column_heading = span.up('.active-scaffold').down(heading_selector);
|
166
202
|
} else if (my_parent.nodeName.toLowerCase() === 'th') {
|
167
203
|
column_heading = my_parent;
|
168
204
|
}
|
169
|
-
|
205
|
+
|
170
206
|
var render_url = column_heading.readAttribute('data-ie_render_url'),
|
171
207
|
mode = column_heading.readAttribute('data-ie_mode'),
|
172
208
|
record_id = span.readAttribute('data-ie_id');
|
@@ -188,7 +224,7 @@ document.observe("dom:loaded", function() {
|
|
188
224
|
}
|
189
225
|
options['params'] += ("eid=" + span.up('div.active-scaffold').readAttribute('data-eid'));
|
190
226
|
}
|
191
|
-
|
227
|
+
|
192
228
|
if (mode === 'clone') {
|
193
229
|
options.nodeIdSuffix = record_id;
|
194
230
|
options.inplacePatternSelector = '#' + column_heading.readAttribute('id') + ' .as_inplace_pattern';
|
@@ -583,26 +619,41 @@ var ActiveScaffold = {
|
|
583
619
|
);
|
584
620
|
},
|
585
621
|
|
586
|
-
|
587
|
-
|
588
|
-
var
|
589
|
-
|
590
|
-
|
591
|
-
|
592
|
-
|
593
|
-
|
594
|
-
|
595
|
-
|
596
|
-
|
597
|
-
}
|
598
|
-
|
599
|
-
|
600
|
-
|
601
|
-
|
602
|
-
|
603
|
-
|
622
|
+
mark_span: function(span, mark_flag) {
|
623
|
+
var record_id = span.readAttribute('data-ie_id');
|
624
|
+
var checkbox = span.down('input[type="checkbox"]');
|
625
|
+
/*
|
626
|
+
when the "mark_flag" is "undefined", the "checked" attribute is already set to the new value,
|
627
|
+
when the "mark_flag" is defined (this function is called by the "mark_records" function), the "checked" attribute is still set to the old value
|
628
|
+
*/
|
629
|
+
if (mark_flag == false || (typeof(mark_flag) == 'undefined' && !checkbox.checked)) {
|
630
|
+
ActiveScaffold.unmark_record(record_id);
|
631
|
+
} else {
|
632
|
+
ActiveScaffold.mark_record(record_id);
|
633
|
+
}
|
634
|
+
return checkbox;
|
635
|
+
},
|
636
|
+
|
637
|
+
mark_records: function(tbody_id, mark_flag) {
|
638
|
+
var spans = $$('#' + tbody_id + ' > tr.record td.marked-column span.mark_record_field');
|
639
|
+
var checkbox;
|
640
|
+
for (var i = 0; i < spans.length; i++) {
|
641
|
+
checkbox = ActiveScaffold.mark_span(spans[i], mark_flag);
|
642
|
+
checkbox.checked = mark_flag;
|
643
|
+
}
|
644
|
+
},
|
645
|
+
|
646
|
+
marked_records: [],
|
647
|
+
|
648
|
+
mark_record: function(record_id) {
|
649
|
+
ActiveScaffold.marked_records.push(record_id);
|
650
|
+
},
|
651
|
+
|
652
|
+
unmark_record: function(record_id) {
|
653
|
+
for (var i = ActiveScaffold.marked_records.length - 1; i >= 0; i--) {
|
654
|
+
if (ActiveScaffold.marked_records[i] == record_id) {
|
655
|
+
ActiveScaffold.marked_records.splice(i, 1);
|
604
656
|
}
|
605
|
-
mark_all_checkbox.writeAttribute('value', ('' + !options.checked));
|
606
657
|
}
|
607
658
|
},
|
608
659
|
|
data/doc/README.mark
ADDED
@@ -0,0 +1,30 @@
|
|
1
|
+
#########
|
2
|
+
# HOWTO #
|
3
|
+
#########
|
4
|
+
|
5
|
+
1) add the :mark action
|
6
|
+
2) use css class "marked_records_action" for actions working with marked records
|
7
|
+
3) use the controller method "marked_records" to retrieve the IDs of marked records
|
8
|
+
|
9
|
+
########################################
|
10
|
+
# Example code for Comments controller #
|
11
|
+
########################################
|
12
|
+
|
13
|
+
config.actions.add :mark
|
14
|
+
config.action_links.add('delete_selected', :label => 'Delete selected comments', :type => :collection, :method => :post,
|
15
|
+
:position => false, :html_options => {:class => 'marked_records_action'})
|
16
|
+
|
17
|
+
...
|
18
|
+
|
19
|
+
def delete_selected
|
20
|
+
record_ids = marked_records
|
21
|
+
Comment.where(:id => record_ids).all.each do |comment|
|
22
|
+
comment.deleted = true
|
23
|
+
comment.save(:columns => [:deleted], :validate => false)
|
24
|
+
end
|
25
|
+
render :update do |page|
|
26
|
+
record_ids.each do |record_id|
|
27
|
+
page.remove(element_row_id(:action => 'list', :id => record_id))
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
@@ -1,16 +1,14 @@
|
|
1
|
-
<% @column_span_id ||= element_cell_id(:id => @record.id.to_s, :action => 'update_column', :name =>
|
2
|
-
<% unless controller.send :successful
|
3
|
-
alert('<%= escape_javascript(@record.errors.full_messages.join("\n"))%>');
|
4
|
-
<% @record.reload
|
5
|
-
<% end
|
6
|
-
<% column
|
7
|
-
|
8
|
-
|
9
|
-
<%
|
10
|
-
|
11
|
-
|
12
|
-
<%
|
13
|
-
|
14
|
-
|
15
|
-
<% end%>
|
16
|
-
|
1
|
+
<% @column_span_id ||= element_cell_id(:id => @record.id.to_s, :action => 'update_column', :name => @column.name) -%>
|
2
|
+
<% unless controller.send :successful? -%>
|
3
|
+
alert('<%= escape_javascript(@record.errors.full_messages.join("\n")) %>');
|
4
|
+
<% @record.reload -%>
|
5
|
+
<% end -%>
|
6
|
+
<% if @column.inplace_edit -%>
|
7
|
+
ActiveScaffold.replace_html('<%= @column_span_id %>','<%= escape_javascript(get_column_value(@record, @column)) %>');
|
8
|
+
<% else -%>
|
9
|
+
<% formatted_value = get_column_value(@record, @column)%>
|
10
|
+
ActiveScaffold.replace_html('<%= @column_span_id %>','<%= escape_javascript(formatted_value) %>');
|
11
|
+
<% end -%>
|
12
|
+
<% if @column.calculation? %>
|
13
|
+
ActiveScaffold.replace_html('<%= active_scaffold_calculations_id(@column) %>', '<%= escape_javascript(render_column_calculation(@column)) %>');
|
14
|
+
<% end -%>
|
@@ -71,13 +71,10 @@ module ActiveScaffold::Actions
|
|
71
71
|
end
|
72
72
|
end
|
73
73
|
|
74
|
-
def marked_records
|
75
|
-
active_scaffold_session_storage[:marked_records] ||= Set.new
|
76
|
-
end
|
77
|
-
|
78
74
|
def default_formats
|
79
75
|
[:html, :js, :json, :xml, :yaml]
|
80
76
|
end
|
77
|
+
|
81
78
|
# Returns true if the client accepts one of the MIME types passed to it
|
82
79
|
# ex: accepts? :html, :xml
|
83
80
|
def accepts?(*types)
|
@@ -52,7 +52,6 @@ module ActiveScaffold::Actions
|
|
52
52
|
@record ||= destroy_find_record
|
53
53
|
begin
|
54
54
|
self.successful = @record.destroy
|
55
|
-
marked_records.delete @record.id.to_s if successful?
|
56
55
|
rescue
|
57
56
|
flash[:warning] = as_(:cant_destroy_record, :record => @record.to_label)
|
58
57
|
self.successful = false
|
@@ -1,75 +1,17 @@
|
|
1
1
|
module ActiveScaffold::Actions
|
2
2
|
module Mark
|
3
|
-
|
4
3
|
def self.included(base)
|
5
|
-
base.before_filter :mark_authorized?, :only => :mark
|
6
|
-
#base.prepend_before_filter :assign_marked_records_to_model
|
7
4
|
base.helper_method :marked_records
|
8
5
|
end
|
9
6
|
|
10
|
-
def mark_all
|
11
|
-
if mark_all? || mark_all_scope_forced?
|
12
|
-
do_mark_all
|
13
|
-
else
|
14
|
-
do_unmark
|
15
|
-
end
|
16
|
-
respond_to_action(:mark_all)
|
17
|
-
end
|
18
7
|
protected
|
19
8
|
|
20
|
-
def
|
21
|
-
|
22
|
-
|
23
|
-
end
|
24
|
-
|
25
|
-
def mark_all_respond_to_js
|
26
|
-
do_list
|
27
|
-
render :action => 'on_mark_all', :locals => {:mark_all => mark_all?}
|
28
|
-
end
|
29
|
-
|
30
|
-
# We need to give the ActiveRecord classes a handle to currently marked records. We don't want to just pass the object,
|
31
|
-
# because the object may change. So we give ActiveRecord a proc that ties to the
|
32
|
-
# marked_records_method on this ApplicationController.
|
33
|
-
def assign_marked_records_to_model
|
34
|
-
active_scaffold_config.model.marked_records = marked_records
|
35
|
-
end
|
36
|
-
|
37
|
-
def mark?
|
38
|
-
params[:value] == 'true'
|
39
|
-
end
|
40
|
-
|
41
|
-
def mark_all?
|
42
|
-
@mark_all ||= [true, 'true', 1, '1', 'T', 't'].include?(params[:value].class == String ? params[:value].downcase : params[:value])
|
43
|
-
end
|
44
|
-
|
45
|
-
def mark_all_scope_forced?
|
46
|
-
!params[:mark_target].nil? && params[:mark_target]=='scope'
|
47
|
-
end
|
48
|
-
|
49
|
-
def do_mark_all
|
50
|
-
if active_scaffold_config.mark.mark_all_mode == :page && !mark_all_scope_forced? then
|
51
|
-
each_record_in_page {|record| marked_records << record.id}
|
52
|
-
else
|
53
|
-
each_record_in_scope {|record| marked_records << record.id}
|
54
|
-
end
|
55
|
-
end
|
56
|
-
|
57
|
-
def do_demark_all
|
58
|
-
if active_scaffold_config.mark.mark_all_mode == :page then
|
59
|
-
each_record_in_page {|record| marked_records.delete(record.id)}
|
9
|
+
def marked_records
|
10
|
+
if params[:marked_records]
|
11
|
+
params[:marked_records].split(',').collect {|x| Integer(x)}.uniq
|
60
12
|
else
|
61
|
-
|
13
|
+
[]
|
62
14
|
end
|
63
15
|
end
|
64
|
-
|
65
|
-
# The default security delegates to ModelPermissions.
|
66
|
-
# You may override the method to customize.
|
67
|
-
def mark_authorized?
|
68
|
-
authorized_for?(:crud_type => :read)
|
69
|
-
end
|
70
|
-
|
71
|
-
def mark_all_formats
|
72
|
-
(default_formats + active_scaffold_config.formats).uniq
|
73
|
-
end
|
74
16
|
end
|
75
17
|
end
|
@@ -97,17 +97,25 @@ module ActiveScaffold::Actions
|
|
97
97
|
end
|
98
98
|
|
99
99
|
def do_update_column
|
100
|
-
|
101
|
-
|
102
|
-
|
103
|
-
|
104
|
-
|
105
|
-
|
106
|
-
|
100
|
+
# delete from params so update :table won't break urls, also they shouldn't be used in sort links too
|
101
|
+
value = params.delete(:value)
|
102
|
+
column = params.delete(:column).to_sym
|
103
|
+
params.delete(:original_html)
|
104
|
+
params.delete(:original_value)
|
105
|
+
|
106
|
+
@record = find_if_allowed(params[:id], :read)
|
107
|
+
if @record.authorized_for?(:crud_type => :update, :column => column)
|
108
|
+
@column = active_scaffold_config.columns[column]
|
109
|
+
value ||= unless @column.column.nil? || @column.column.null
|
110
|
+
@column.column.default == true ? false : @column.column.default
|
111
|
+
end
|
112
|
+
unless @column.nil?
|
113
|
+
value = column_value_from_param_value(@record, @column, value)
|
114
|
+
value = [] if value.nil? && @column.form_ui && @column.plural_association?
|
107
115
|
end
|
108
|
-
@record.send("#{
|
116
|
+
@record.send("#{@column.name}=", value)
|
109
117
|
before_update_save(@record)
|
110
|
-
@record.save
|
118
|
+
self.successful = @record.save
|
111
119
|
after_update_save(@record)
|
112
120
|
end
|
113
121
|
end
|