caboose-cms 0.5.64 → 0.5.66
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +8 -8
- data/app/assets/javascripts/caboose/admin.js +1 -1
- data/app/assets/javascripts/caboose/admin_edit_order.js +724 -0
- data/app/assets/javascripts/caboose/cart2.js +4 -4
- data/app/assets/javascripts/caboose/model/index_table.js +122 -80
- data/app/assets/stylesheets/caboose/admin_main.css +8 -0
- data/app/controllers/caboose/application_controller.rb +1 -1
- data/app/controllers/caboose/block_type_sources_controller.rb +1 -1
- data/app/controllers/caboose/block_types_controller.rb +1 -1
- data/app/controllers/caboose/calendars_controller.rb +1 -1
- data/app/controllers/caboose/cart_controller.rb +8 -1
- data/app/controllers/caboose/checkout_controller.rb +17 -9
- data/app/controllers/caboose/line_items_controller.rb +135 -0
- data/app/controllers/caboose/order_packages_controller.rb +304 -0
- data/app/controllers/caboose/orders_controller.rb +31 -74
- data/app/controllers/caboose/pages_controller.rb +2 -1
- data/app/controllers/caboose/product_images_controller.rb +11 -0
- data/app/controllers/caboose/products_controller.rb +25 -8
- data/app/controllers/caboose/shipping_addresses_controller.rb +46 -0
- data/app/controllers/caboose/shipping_packages_controller.rb +125 -54
- data/app/controllers/caboose/sites_controller.rb +2 -79
- data/app/controllers/caboose/smtp_controller.rb +52 -0
- data/app/controllers/caboose/store_controller.rb +94 -0
- data/app/controllers/caboose/vendors_controller.rb +25 -4
- data/app/models/caboose/address.rb +1 -3
- data/app/models/caboose/caboose_plugin.rb +1 -1
- data/app/models/caboose/category.rb +18 -0
- data/app/models/caboose/core_plugin.rb +21 -19
- data/app/models/caboose/order.rb +12 -7
- data/app/models/caboose/order_package.rb +5 -2
- data/app/models/caboose/order_transaction.rb +25 -0
- data/app/models/caboose/page.rb +1 -1
- data/app/models/caboose/schema.rb +50 -22
- data/app/models/caboose/shipping_calculator.rb +26 -30
- data/app/models/caboose/shipping_package.rb +45 -5
- data/app/models/caboose/store_config.rb +18 -6
- data/app/models/caboose/tax_calculator.rb +6 -5
- data/app/views/caboose/blocks/admin_edit.html.erb +1 -1
- data/app/views/caboose/line_items/admin_new.html.erb +100 -0
- data/app/views/caboose/orders/admin_edit.html.erb +21 -247
- data/app/views/caboose/orders/admin_edit_old.html.erb +155 -0
- data/app/views/caboose/orders/admin_new.html.erb +8 -23
- data/app/views/caboose/products/#Untitled-1# +0 -0
- data/app/views/caboose/products/admin_edit_images.html.erb +20 -4
- data/app/views/caboose/products/admin_index.html.erb +9 -3
- data/app/views/caboose/products/admin_sort.html.erb +138 -142
- data/app/views/caboose/roles/index.html.erb +1 -1
- data/app/views/caboose/shipping_packages/admin_edit.html.erb +52 -137
- data/app/views/caboose/shipping_packages/admin_index.html.erb +56 -19
- data/app/views/caboose/sites/_admin_header.html.erb +3 -5
- data/app/views/caboose/sites/admin_edit.html.erb +5 -3
- data/app/views/caboose/smtp/admin_edit.html.erb +41 -0
- data/app/views/caboose/station/index.html.erb +1 -1
- data/app/views/caboose/store/admin_edit.html.erb +96 -0
- data/app/views/caboose/vendors/admin_edit.html.erb +7 -3
- data/app/views/layouts/caboose/_station.html.erb +1 -1
- data/config/routes.rb +67 -25
- data/lib/caboose/engine.rb +1 -1
- data/lib/caboose/version.rb +1 -1
- metadata +28 -5
- data/app/views/caboose/shipping_packages/admin_new.html.erb +0 -33
- data/app/views/caboose/sites/admin_edit_smtp_config.html.erb +0 -51
- data/app/views/caboose/sites/admin_edit_store_config.html.erb +0 -77
@@ -0,0 +1,155 @@
|
|
1
|
+
<%
|
2
|
+
sa = @order.shipping_address
|
3
|
+
shipping_address = sa.address1
|
4
|
+
shipping_address << "<br />#{sa.address2}" if sa.address2 && sa.address2.length > 0
|
5
|
+
shipping_address << "<br />#{sa.city}, #{sa.state} #{sa.zip}"
|
6
|
+
captured = @order.financial_status == 'captured'
|
7
|
+
%>
|
8
|
+
<input type='hidden' name='order_id' id='order_id' value='<%= @order.id %>' />
|
9
|
+
|
10
|
+
<h1>Edit Order #<%= @order.id %></h1>
|
11
|
+
|
12
|
+
<table class='data'>
|
13
|
+
<tr>
|
14
|
+
<th><%= if @order.customer.nil? then 'Guest' else 'Customer' end %></th>
|
15
|
+
<th>Shipping Address</th>
|
16
|
+
<th>Shipping Method</th>
|
17
|
+
<th>Order Status</th>
|
18
|
+
<th>Payment Status</th>
|
19
|
+
<th>Transaction ID</th>
|
20
|
+
</tr>
|
21
|
+
<tr>
|
22
|
+
<td valign='top'>
|
23
|
+
<%= "#{@order.shipping_address.first_name} #{@order.shipping_address.last_name}" %><br />
|
24
|
+
<% if @order.customer %>
|
25
|
+
<a href="mailto:<%= "#{@order.customer.email}" %>"><%= "#{@order.customer.email}" %></a><br />
|
26
|
+
<% elsif @order.email %>
|
27
|
+
<a href="mailto:<%= @order.email %>"><%= @order.email %></a>
|
28
|
+
<% end %>
|
29
|
+
<%= @order.customer ? @order.customer.phone : @order.shipping_address.phone %>
|
30
|
+
</td>
|
31
|
+
<td valign='top'>
|
32
|
+
<%= "#{@order.shipping_address.first_name} #{@order.shipping_address.last_name}" %><br />
|
33
|
+
<%= raw shipping_address %>
|
34
|
+
</td>
|
35
|
+
<td valign='top' align='center'>
|
36
|
+
<% if @order.shipping_service_code %>
|
37
|
+
<%= @order.shipping_carrier %> <%= @order.shipping_service_name %>
|
38
|
+
<% else %>
|
39
|
+
Multiple packages
|
40
|
+
<% end %>
|
41
|
+
</td>
|
42
|
+
<td valign='top'>
|
43
|
+
<div id='order_<%= @order.id %>_status'></div>
|
44
|
+
</td>
|
45
|
+
<td valign='top' align='center'>
|
46
|
+
<%= @order.financial_status %>
|
47
|
+
<% if @order.financial_status == 'authorized' %>
|
48
|
+
for<br /><%= number_to_currency(@order.auth_amount) %>
|
49
|
+
<% end %>
|
50
|
+
</td>
|
51
|
+
<td valign="top" align='center'><%= @order.transaction_id %></td>
|
52
|
+
</tr>
|
53
|
+
</table><br />
|
54
|
+
|
55
|
+
<table class='data' width='100%'>
|
56
|
+
<tr>
|
57
|
+
<th>Package</th>
|
58
|
+
<th>Item</th>
|
59
|
+
<th>Status</th>
|
60
|
+
<th>Unit Price</th>
|
61
|
+
<th>Quantity</th>
|
62
|
+
<th>Subtotal</th>
|
63
|
+
</tr>
|
64
|
+
<% @order.packages.each do |op| %>
|
65
|
+
<% op.line_items.each_with_index do |li, i| %>
|
66
|
+
<tr>
|
67
|
+
<% if i == 0 %>
|
68
|
+
<td rowspan="<%= op.line_items.count %>">
|
69
|
+
<div id='orderpackage_<%= op.id %>_shipping_method_id'></div>
|
70
|
+
<div id='orderpackage_<%= op.id %>_status'></div>
|
71
|
+
</td>
|
72
|
+
<% end %>
|
73
|
+
<td>
|
74
|
+
<% if li.variant.nil? || li.variant.product.nil? %>
|
75
|
+
<% if li.variant.nil? %>
|
76
|
+
Unknown variant
|
77
|
+
<% else %>
|
78
|
+
<%= li.variant.sku %>
|
79
|
+
<% end %>
|
80
|
+
<% else %>
|
81
|
+
<a href='/admin/products/<%= li.variant.product.id %>/variants?highlight=<%= li.variant.id %>'><%= li.variant.product.title %></a><br />
|
82
|
+
<%= li.variant.sku %><br />
|
83
|
+
<%= li.variant.title %>
|
84
|
+
<% end %>
|
85
|
+
</td>
|
86
|
+
<td ><div id='lineitem_<%= li.id %>_status' ></div></td>
|
87
|
+
<td align='right'><%= number_to_currency(li.variant.price) %></td>
|
88
|
+
<td align='right'><% if captured %><%= li.quantity %><% else %><div id='lineitem_<%= li.id %>_quantity'></div><% end %></td>
|
89
|
+
<td align='right' id='li_<%= li.id %>_subtotal'><%= number_to_currency(li.price) %></td>
|
90
|
+
</tr>
|
91
|
+
<% end %>
|
92
|
+
<% end %>
|
93
|
+
<% @order.line_items.each do |li| %>
|
94
|
+
<% next if li.order_package_id %>
|
95
|
+
<tr>
|
96
|
+
<td><div id='assign_to_package'>Unpackaged! <a href='#' onclick="assign_to_package_form(<%= li.id %>);">Assign to package</a></div></td>
|
97
|
+
<td>
|
98
|
+
<% if li.variant.nil? || li.variant.product.nil? %>
|
99
|
+
<% if li.variant.nil? %>Unknown variant<% else %><%= li.variant.sku %><% end %>
|
100
|
+
<% else %>
|
101
|
+
<a href='/admin/products/<%= li.variant.product.id %>/variants?highlight=<%= li.variant.id %>'><%= li.variant.product.title %></a><br />
|
102
|
+
<%= li.variant.sku %><br />
|
103
|
+
<%= li.variant.title %>
|
104
|
+
<% end %>
|
105
|
+
</td>
|
106
|
+
<td ><div id='lineitem_<%= li.id %>_status' ></div></td>
|
107
|
+
<td align='right'><%= number_to_currency(li.variant.price) %></td>
|
108
|
+
<td align='right'><% if captured %><%= li.quantity %><% else %><div id='lineitem_<%= li.id %>_quantity'></div><% end %></td>
|
109
|
+
<td align='right' id='li_<%= li.id %>_subtotal'><%= number_to_currency(li.price) %></td>
|
110
|
+
</tr>
|
111
|
+
<% end %>
|
112
|
+
<tr><td colspan='5' align='right'>Subtotal </td><td align='right' id='subtotal' ><%= number_to_currency(@order.subtotal ) %></td></tr>
|
113
|
+
<tr><td colspan='5' align='right'>Tax </td><td align='right' id='tax' ><%= number_to_currency(@order.tax ) %></td></tr>
|
114
|
+
<tr><td colspan='5' align='right'><%= @order.shipping_service_code ? @order.shipping_service_code : '' %> Shipping & Handling </td><td align='right' id='shipping'><%= number_to_currency(@order.shipping + @order.handling) %></td></tr>
|
115
|
+
<tr>
|
116
|
+
<td colspan='5' align='right'>Discount</td>
|
117
|
+
<td align='right'>
|
118
|
+
<% if captured && @order.discounts.any? %>
|
119
|
+
<%= number_to_currency(@order.amount_discounted || 0) %>
|
120
|
+
<% elsif @order.discounts.any? %>
|
121
|
+
<%= number_to_currency(@order.discounts.first.amount_current) %>
|
122
|
+
<% else %>
|
123
|
+
$0.00
|
124
|
+
<% end %>
|
125
|
+
</td>
|
126
|
+
</tr>
|
127
|
+
<tr><td colspan='5' align='right'>Total </td><td align='right' id='total' ><%= number_to_currency(@order.total ) %></td></tr>
|
128
|
+
</table>
|
129
|
+
<div id='message'></div>
|
130
|
+
|
131
|
+
<p>
|
132
|
+
<input type='button' value='< Back' onclick="window.location='/admin/orders';" />
|
133
|
+
<% if @order.financial_status == 'authorized' %>
|
134
|
+
<input type='button' value='Capture Funds' onclick="capture_funds(<%= @order.id %>);" />
|
135
|
+
<input type='button' value='Void' onclick="void_order(<%= @order.id %>);" />
|
136
|
+
<% end %>
|
137
|
+
<% if @order.financial_status == 'captured' %>
|
138
|
+
<input type='button' value='Refund' onclick="refund_order(<%= @order.id %>);" />
|
139
|
+
<% end %>
|
140
|
+
<input type='button' value='Resend Confirmation' onclick="resend_confirmation(<%= @order.id %>)" />
|
141
|
+
<input type='button' value='Print Order' onclick="print_order(<%= @order.id %>);" />
|
142
|
+
|
143
|
+
<% str = Caboose.plugin_hook('admin_edit_order_buttons', "", @order) %>
|
144
|
+
<% if str %><%= raw str %><% end %>
|
145
|
+
</p>
|
146
|
+
|
147
|
+
<% content_for :caboose_js do %>
|
148
|
+
<%= javascript_include_tag 'caboose/model/all' %>
|
149
|
+
<%= javascript_include_tag 'caboose/admin_edit_order' %>
|
150
|
+
<script type='text/javascript'>
|
151
|
+
|
152
|
+
var controller = new OrderController({ order_id: <%= raw Caboose.json(@order.id) %> });
|
153
|
+
|
154
|
+
</script>
|
155
|
+
<% end %>
|
@@ -1,13 +1,6 @@
|
|
1
1
|
<h1>New Manual Order</h1>
|
2
2
|
|
3
|
-
<p
|
4
|
-
<option value=''>-- Select a product --</option>
|
5
|
-
<% @products.each do |p| %>
|
6
|
-
<option value='<%= p.id %>'><%= p.title %></option>
|
7
|
-
<% end %>
|
8
|
-
</select>
|
9
|
-
<span id='variant_id_container'></span>
|
10
|
-
</p>
|
3
|
+
<p>This will create a new order that you can populate and then send to the customer for payment.</p>
|
11
4
|
|
12
5
|
<p>
|
13
6
|
<input type='button' value='< Back' onclick="window.location='/admin/orders';" />
|
@@ -17,23 +10,15 @@
|
|
17
10
|
<% content_for :caboose_js do %>
|
18
11
|
<script type='text/javascript'>
|
19
12
|
|
20
|
-
|
21
|
-
$(window).load(function() {
|
22
|
-
modal = new CabooseModal('95%');
|
23
|
-
});
|
24
|
-
|
25
|
-
function populate_variants()
|
13
|
+
function create_order()
|
26
14
|
{
|
27
|
-
$('#
|
28
|
-
var product_id = $('#product_id').val();
|
15
|
+
$('#message').empty().append("<p class='loading'>Creating order...</p>");
|
29
16
|
$.ajax({
|
30
|
-
url: '/admin/
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
});
|
36
|
-
$('#variant_id_container').empty().append(select);
|
17
|
+
url: '/admin/orders',
|
18
|
+
type: 'post',
|
19
|
+
success: function(resp) {
|
20
|
+
if (resp.error) $('#message').html("<p class='note error'>" + resp.error + "</p>");
|
21
|
+
if (resp.redirect) window.location = resp.redirect;
|
37
22
|
}
|
38
23
|
});
|
39
24
|
}
|
File without changes
|
@@ -14,10 +14,12 @@ p = @product
|
|
14
14
|
|
15
15
|
<div id='images'>
|
16
16
|
<% if p.product_images.count > 0 %>
|
17
|
-
|
18
|
-
<%
|
19
|
-
|
20
|
-
|
17
|
+
<ul id='images_list' class='clearfix'>
|
18
|
+
<% p.product_images.reorder(:position).each do |img| %>
|
19
|
+
<% url = img.image.url(:tiny) %>
|
20
|
+
<li id='img_<%= img.id %>'><div id='img_<%= img.id %>_container'><a href="javascript:select_image(<%= img.id %>);"><img src='<%= url %>' width='75' /></a></div></li>
|
21
|
+
<% end %>
|
22
|
+
</ul>
|
21
23
|
<% else %>
|
22
24
|
<p>This product doesn't have any images yet.</p>
|
23
25
|
<% end %>
|
@@ -34,6 +36,8 @@ p = @product
|
|
34
36
|
#images div { display: inline-block; }
|
35
37
|
#images div img { border: #000 4px solid; }
|
36
38
|
#images div.selected img { border: #ff3333 4px solid; }
|
39
|
+
#images_list { list-style: none; margin: 0; padding: 0; }
|
40
|
+
#images_list li { list-style: none; margin: 0 10px 10px 0; padding: 0; float: left; }
|
37
41
|
</style>
|
38
42
|
<% end %>
|
39
43
|
<% content_for :caboose_js do %>
|
@@ -43,6 +47,18 @@ $(document).ready(function() {
|
|
43
47
|
<% if p.product_images.count > 0 %>
|
44
48
|
select_image(<%= p.product_images[0].id %>);
|
45
49
|
<% end %>
|
50
|
+
$('#images_list').sortable({
|
51
|
+
stop: function(e, ui) {
|
52
|
+
var arr = $('#images_list').sortable('toArray')
|
53
|
+
ids = $.map(arr, function(id, i) { return parseInt(id.replace('img_', '')); });
|
54
|
+
$.ajax({
|
55
|
+
url: '/admin/product-images/sort-order',
|
56
|
+
type: 'put',
|
57
|
+
data: { product_image_ids: ids },
|
58
|
+
success: function(resp) {}
|
59
|
+
});
|
60
|
+
}
|
61
|
+
});
|
46
62
|
});
|
47
63
|
|
48
64
|
variants = false;
|
@@ -7,9 +7,15 @@
|
|
7
7
|
</p>
|
8
8
|
|
9
9
|
<form action="/admin/products" method="get" id="search_form" style="margin: 0 0 12px">
|
10
|
-
<input type="text" name="search_like" placeholder="Title or Vendor Name" value="<%= params[:search_like] %>" style="width: 350px"
|
11
|
-
<
|
12
|
-
|
10
|
+
<p><input type="text" name="search_like" placeholder="Title or Vendor Name" value="<%= params[:search_like] %>" style="width: 350px" /></p>
|
11
|
+
<p><select type="text" name="category_id" placeholder="Category" value="<%= params[:search_like] %>" style="width: 350px">
|
12
|
+
<option value=''>-- Category --</option>
|
13
|
+
<% @category_options.each do |cat| %><option value="<%= cat[:value] %>"<% if cat[:value] == params[:category_id] %> selected='true'<% end %>><%= cat[:text] %></option><% end %>
|
14
|
+
</select></p>
|
15
|
+
<p>
|
16
|
+
<input type="submit" value="Search" />
|
17
|
+
<input type="button" value="Clear" onclick="window.location='/admin/products'" />
|
18
|
+
</p>
|
13
19
|
</form>
|
14
20
|
|
15
21
|
<div id='products'></div>
|
@@ -11,8 +11,7 @@
|
|
11
11
|
<input name="search" type="search" placeholder="Search for Products" />
|
12
12
|
|
13
13
|
<select class="filter" name="vendor">
|
14
|
-
<option value="">-- Filter by Vendor --</option>
|
15
|
-
|
14
|
+
<option value="">-- Filter by Vendor --</option>
|
16
15
|
<% @vendors.each do |vendor| %>
|
17
16
|
<option value="<%= vendor.id %>"><%= vendor.name %></option>
|
18
17
|
<% end %>
|
@@ -31,157 +30,154 @@
|
|
31
30
|
</section>
|
32
31
|
|
33
32
|
<% content_for :caboose_js do %>
|
34
|
-
|
35
|
-
|
33
|
+
<%= javascript_include_tag('underscore') %>
|
34
|
+
<script type='text/javascript'>
|
35
|
+
window.products = <%= @products.to_json.html_safe %>;
|
36
|
+
window.results = window.products; // Used to store filtered results
|
37
|
+
|
38
|
+
// Delay method
|
39
|
+
var delay = (function(){
|
40
|
+
var timer = 0;
|
41
|
+
return function(callback, ms){
|
42
|
+
clearTimeout (timer);
|
43
|
+
timer = setTimeout(callback, ms);
|
44
|
+
};
|
45
|
+
})();
|
46
|
+
|
47
|
+
// Filter
|
48
|
+
function filter(event) {
|
49
|
+
var $source = $('ul#source')
|
50
|
+
, $search = $('input[name=search]')
|
51
|
+
, search_string = $search.val() === $search.attr('placeholder') ? undefined : $search.val().trim().toUpperCase()
|
52
|
+
, vendor_id = $('select[name=vendor]').val();
|
36
53
|
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
var timer = 0;
|
45
|
-
return function(callback, ms){
|
46
|
-
clearTimeout (timer);
|
47
|
-
timer = setTimeout(callback, ms);
|
48
|
-
};
|
49
|
-
})();
|
50
|
-
|
51
|
-
// Filter
|
52
|
-
function filter(event) {
|
53
|
-
var $source = $('ul#source')
|
54
|
-
, $search = $('input[name=search]')
|
55
|
-
, search_string = $search.val() === $search.attr('placeholder') ? undefined : $search.val().trim().toUpperCase()
|
56
|
-
, vendor_id = $('select[name=vendor]').val();
|
57
|
-
|
58
|
-
$source.empty();
|
59
|
-
|
60
|
-
_.each(window.products, function(product) {
|
61
|
-
if (!search_string && !vendor_id
|
62
|
-
|| search_string && product.title.toUpperCase().indexOf(search_string) > -1
|
63
|
-
|| vendor_id && product.vendor_id == vendor_id) {
|
64
|
-
$source.append( $('<li/>').attr('data-id', product.id).text(product.title) );
|
65
|
-
}
|
66
|
-
});
|
54
|
+
$source.empty();
|
55
|
+
|
56
|
+
_.each(window.products, function(product) {
|
57
|
+
if (!search_string && !vendor_id
|
58
|
+
|| search_string && product.title.toUpperCase().indexOf(search_string) > -1
|
59
|
+
|| vendor_id && product.vendor_id == vendor_id) {
|
60
|
+
$source.append( $('<li/>').attr('data-id', product.id).text(product.title) );
|
67
61
|
}
|
68
|
-
|
69
|
-
|
62
|
+
});
|
63
|
+
}
|
64
|
+
|
65
|
+
function update(event) {
|
66
|
+
|
67
|
+
// Send the ordered array to the server to make it official
|
68
|
+
$.ajax({
|
69
|
+
type: 'put',
|
70
|
+
url: '/admin/products/update-sort-order',
|
71
|
+
data: { product_ids: $('ul#target').sortable('toArray', { attribute: 'data-id' }) }
|
72
|
+
});
|
73
|
+
}
|
74
|
+
|
75
|
+
$(document).ready(function() {
|
76
|
+
var selected_class = 'selected';
|
77
|
+
|
78
|
+
// Selection rules
|
79
|
+
$('ul.sortable').on('click', 'li', function(event) {
|
80
|
+
$element = $(this);
|
81
|
+
|
82
|
+
if (event.shiftKey && $last_element) {
|
83
|
+
if ($element.index() < $last_element.index()) {
|
84
|
+
$element.nextUntil($last_element).addClass(selected_class);
|
85
|
+
} else {
|
86
|
+
$element.prevUntil($last_element).addClass(selected_class);
|
87
|
+
}
|
70
88
|
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
89
|
+
$element.toggleClass(selected_class);
|
90
|
+
} else if (event.ctrlKey || event.metaKey) {
|
91
|
+
if ($element.hasClass(selected_class)) {
|
92
|
+
$element.removeClass(selected_class);
|
93
|
+
} else {
|
94
|
+
$element.addClass(selected_class);
|
95
|
+
}
|
96
|
+
} else {
|
97
|
+
$element.addClass(selected_class).siblings().removeClass(selected_class);
|
77
98
|
}
|
78
99
|
|
79
|
-
$
|
80
|
-
|
100
|
+
$last_element = $element;
|
101
|
+
});
|
102
|
+
|
103
|
+
// Setup sortable lists
|
104
|
+
$('ul#source').sortable({
|
105
|
+
delay: 150,
|
106
|
+
revert: 0,
|
107
|
+
connectWith: 'ul#target',
|
108
|
+
|
109
|
+
helper: function(event, item) {
|
81
110
|
|
82
|
-
//
|
83
|
-
|
84
|
-
$element = $(this);
|
85
|
-
|
86
|
-
if (event.shiftKey && $last_element) {
|
87
|
-
if ($element.index() < $last_element.index()) {
|
88
|
-
$element.nextUntil($last_element).addClass(selected_class);
|
89
|
-
} else {
|
90
|
-
$element.prevUntil($last_element).addClass(selected_class);
|
91
|
-
}
|
92
|
-
|
93
|
-
$element.toggleClass(selected_class);
|
94
|
-
} else if (event.ctrlKey || event.metaKey) {
|
95
|
-
if ($element.hasClass(selected_class)) {
|
96
|
-
$element.removeClass(selected_class);
|
97
|
-
} else {
|
98
|
-
$element.addClass(selected_class);
|
99
|
-
}
|
100
|
-
} else {
|
101
|
-
$element.addClass(selected_class).siblings().removeClass(selected_class);
|
102
|
-
}
|
103
|
-
|
104
|
-
$last_element = $element;
|
105
|
-
});
|
111
|
+
// If the user just clicked and immediately drug an element
|
112
|
+
if ( !item.hasClass(selected_class) ) item.addClass(selected_class).siblings().removeClass(selected_class);
|
106
113
|
|
107
|
-
//
|
108
|
-
|
109
|
-
|
110
|
-
revert: 0,
|
111
|
-
connectWith: 'ul#target',
|
112
|
-
|
113
|
-
helper: function(event, item) {
|
114
|
-
|
115
|
-
// If the user just clicked and immediately drug an element
|
116
|
-
if ( !item.hasClass(selected_class) ) item.addClass(selected_class).siblings().removeClass(selected_class);
|
117
|
-
|
118
|
-
// Grab the selected elements and create the helper
|
119
|
-
var elements = item.parent().children('.' + selected_class).clone()
|
120
|
-
, helper = $('<li/>');
|
121
|
-
|
122
|
-
// Add the elements to the item multidrag data attribute
|
123
|
-
item.data('multidrag', elements).siblings('.' + selected_class);
|
124
|
-
|
125
|
-
// Pass back the helper
|
126
|
-
return helper.append(elements);
|
127
|
-
},
|
128
|
-
|
129
|
-
start: function(event, ui) {
|
130
|
-
|
131
|
-
// Make sure the item stays visible on #source
|
132
|
-
$(ui.item).show();
|
133
|
-
|
134
|
-
// Clone the original item and note the previous one, to reappend after jquery ui takes it away
|
135
|
-
item_clone = $(ui.item).clone();
|
136
|
-
previous_item = $(ui.item).prev();
|
137
|
-
|
138
|
-
// Remove selected status from ul#target
|
139
|
-
$('ul#target li.selected').removeClass('selected');
|
140
|
-
},
|
114
|
+
// Grab the selected elements and create the helper
|
115
|
+
var elements = item.parent().children('.' + selected_class).clone()
|
116
|
+
, helper = $('<li/>');
|
141
117
|
|
142
|
-
|
143
|
-
|
144
|
-
|
145
|
-
|
146
|
-
|
147
|
-
|
148
|
-
|
149
|
-
|
150
|
-
|
151
|
-
|
152
|
-
|
153
|
-
|
154
|
-
|
155
|
-
|
156
|
-
|
157
|
-
|
158
|
-
|
159
|
-
|
160
|
-
|
161
|
-
|
162
|
-
|
163
|
-
previous_item.after(item_clone);
|
164
|
-
} else {
|
165
|
-
$('ul#source').prepend(item_clone);
|
166
|
-
}
|
167
|
-
|
168
|
-
// Update sort order
|
169
|
-
update(event, ui);
|
170
|
-
}
|
171
|
-
});
|
118
|
+
// Add the elements to the item multidrag data attribute
|
119
|
+
item.data('multidrag', elements).siblings('.' + selected_class);
|
120
|
+
|
121
|
+
// Pass back the helper
|
122
|
+
return helper.append(elements);
|
123
|
+
},
|
124
|
+
|
125
|
+
start: function(event, ui) {
|
126
|
+
|
127
|
+
// Make sure the item stays visible on #source
|
128
|
+
$(ui.item).show();
|
129
|
+
|
130
|
+
// Clone the original item and note the previous one, to reappend after jquery ui takes it away
|
131
|
+
item_clone = $(ui.item).clone();
|
132
|
+
previous_item = $(ui.item).prev();
|
133
|
+
|
134
|
+
// Remove selected status from ul#target
|
135
|
+
$('ul#target li.selected').removeClass('selected');
|
136
|
+
},
|
137
|
+
|
138
|
+
beforeStop: function(event, ui) {
|
172
139
|
|
173
|
-
|
174
|
-
$('ul#target').sortable({ stop: update });
|
140
|
+
if ($(ui.item).parent().attr('id') != 'source') {
|
175
141
|
|
176
|
-
|
177
|
-
|
142
|
+
// Remove duplicate items from old positions
|
143
|
+
ui.item.data('multidrag').each(function(index, element) {
|
144
|
+
var $element = $(element);
|
145
|
+
$('ul#target li[data-id=' + $element.attr('data-id') + ']').not('.selected').remove()
|
146
|
+
});
|
147
|
+
}
|
148
|
+
},
|
149
|
+
|
150
|
+
stop: function(event, ui) {
|
178
151
|
|
179
|
-
|
180
|
-
|
181
|
-
|
182
|
-
|
183
|
-
|
184
|
-
|
152
|
+
if ($(ui.item).parent().attr('id') == 'source') return false;
|
153
|
+
|
154
|
+
// Clear multidrag data
|
155
|
+
ui.item.after( ui.item.data('multidrag') ).remove();
|
156
|
+
|
157
|
+
// If the previous item is defined append the clone just after, otherwise prepend to #source
|
158
|
+
if (previous_item.length) {
|
159
|
+
previous_item.after(item_clone);
|
160
|
+
} else {
|
161
|
+
$('ul#source').prepend(item_clone);
|
162
|
+
}
|
163
|
+
|
164
|
+
// Update sort order
|
165
|
+
update(event, ui);
|
166
|
+
}
|
167
|
+
});
|
168
|
+
|
169
|
+
// Update sort order when done sorting
|
170
|
+
$('ul#target').sortable({ stop: update });
|
171
|
+
|
172
|
+
// Filter when the vendor select box change
|
173
|
+
$('select').on('change', filter);
|
174
|
+
|
175
|
+
// Filter, after a delay, when there is a keyup event in the search
|
176
|
+
$('input[type=search]').on('keyup', function(event) {
|
177
|
+
delay(function() { filter(event) }, 600);
|
178
|
+
});
|
179
|
+
});
|
180
|
+
</script>
|
185
181
|
<% end %>
|
186
182
|
|
187
183
|
<% content_for :caboose_css do %>
|