active_scaffold-sequel 0.5.1 → 0.6.0
Sign up to get free protection for your applications and to get access to all the features.
- 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
|