voluntary 0.2.2 → 0.2.3
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/CHANGELOG.md +88 -0
- data/README.rdoc +2 -2
- data/app/assets/javascripts/voluntary/application.js +3 -0
- data/app/assets/javascripts/voluntary/base.js.coffee +47 -28
- data/app/assets/javascripts/voluntary/lib/jquery.multisortable.js +254 -0
- data/app/assets/stylesheets/voluntary/application.css +2 -0
- data/app/assets/stylesheets/voluntary/base.css.sass +7 -1
- data/app/assets/stylesheets/voluntary/bootstrap_and_overrides.css.sass +5 -1
- data/app/controllers/concerns/voluntary/v1/base_controller.rb +6 -1
- data/app/controllers/voluntary/api/v1/base_controller.rb +11 -0
- data/app/helpers/voluntary/show_helper.rb +2 -2
- data/app/models/concerns/likeable.rb +11 -0
- data/app/models/user.rb +4 -0
- data/app/views/layouts/application.html.erb +7 -1
- data/app/views/shared/_modal_javascript_response.js.erb +31 -0
- data/app/views/shared/layouts/twitter_bootstrap/_control_group.html.erb +11 -0
- data/app/views/shared/layouts/twitter_bootstrap/_modal.html.erb +12 -0
- data/app/views/shared/layouts/twitter_bootstrap/control_group/_boolean.html.erb +17 -0
- data/app/views/shared/resource/_actions.html.erb +4 -2
- data/config/locales/general/en.yml +14 -2
- data/config/routes/api.rb +6 -0
- data/config/routes.rb +3 -1
- data/lib/generators/voluntary/install/templates/app/views/layouts/application.html.erb +7 -1
- data/lib/generators/voluntary/product_dummy/product_dummy_generator.rb +0 -1
- data/lib/generators/voluntary/product_dummy/templates/app/views/layouts/application.html.erb +7 -1
- data/lib/voluntary/version.rb +1 -1
- data/lib/voluntary.rb +3 -1
- metadata +90 -84
- data/app/controllers/voluntary/api/v1/api_controller.rb +0 -9
data/CHANGELOG.md
ADDED
|
@@ -0,0 +1,88 @@
|
|
|
1
|
+
## unreleased ##
|
|
2
|
+
|
|
3
|
+
## 0.2.3 (March 15, 2015) ##
|
|
4
|
+
|
|
5
|
+
* #16 Implements scope liked_by for likeables.
|
|
6
|
+
* #45 Rewrite of API base controller and initialization of API V1 routes.
|
|
7
|
+
* Introduces Likeable.likes_or_dislikes_for.
|
|
8
|
+
* Introduces new window function jquery_ui_tabs_initialization.
|
|
9
|
+
* #37 Integrates selectize plugin. Used at new tournament form of competition product.
|
|
10
|
+
* Make .remote_modal_link click handler work with other elements than links through data attribute url.
|
|
11
|
+
* Disables closing of modal on pressing escape key.
|
|
12
|
+
* Introduces modal JavaScript response partial. See protip https://coderwall.com/p/eu9sqa/multi-step-form-wizard-responses-for-ajax-modals-and-html-requests
|
|
13
|
+
* Option to yield sidebar in application layout.
|
|
14
|
+
* Introduces User#best_available_name.
|
|
15
|
+
* #26 Add event handler for toggleable checkboxes.
|
|
16
|
+
* Sets GitHub ribbon to voluntary repository in application layout which can be overridden in each product through controller method voluntary_application_repository_path.
|
|
17
|
+
* #20 #23 #32 #33 #34 Adds JavaScript Plugin CompetitiveList used at music metadata enrichment music year in review top albums and songs.
|
|
18
|
+
* Adds jquery.multisortable.js used at music metadata enrichment music year in review top albums and songs.
|
|
19
|
+
* #19 Adds Twitter Bootstrap datetime picker.
|
|
20
|
+
* Implements shared twitter bootstrap layout 'boolean control group'.
|
|
21
|
+
* Sets width of #bootstrap_modal to 800px.
|
|
22
|
+
* Implements shared twitter bootstrap layout partials 'control_group' ...
|
|
23
|
+
* Implements new option :namespace for Voluntary::ShowHelper#show_actions.
|
|
24
|
+
|
|
25
|
+
## 0.2.2 (February 5, 2015) ##
|
|
26
|
+
|
|
27
|
+
* #17 Show progress spinner gif for Ajax tabs.
|
|
28
|
+
* Implements option to render custom breadcrumbs.
|
|
29
|
+
* Makes stylesheets and javascripts of application layout variable.
|
|
30
|
+
* Adds new view helper name_with_apostrophe.
|
|
31
|
+
* Yield page title and search in application layout.
|
|
32
|
+
* Disable scrolling in modal windows because of autocomplete lists cut off before.
|
|
33
|
+
* Sets global font size from 10px to 12px.
|
|
34
|
+
* Fixes ui tab paging links. Implements remote links and remote modal link handler.
|
|
35
|
+
* #14 last.fm authentication.
|
|
36
|
+
* #13 Facebook authentication.
|
|
37
|
+
* #12 Google authentication.
|
|
38
|
+
|
|
39
|
+
## 0.2.1 (January 6, 2015) ##
|
|
40
|
+
|
|
41
|
+
* Small changes not worth mentioning.
|
|
42
|
+
|
|
43
|
+
## 0.2.0 (March 22, 2014) ##
|
|
44
|
+
|
|
45
|
+
* Rails 4 upgrade.
|
|
46
|
+
* Adds new resource organization.
|
|
47
|
+
* after initialize callback for authorization ability.rb
|
|
48
|
+
* after_resource_has_many callback for main navigation
|
|
49
|
+
* Several bugfixes and small features.
|
|
50
|
+
|
|
51
|
+
## 0.1.0 (October 13, 2013) ##
|
|
52
|
+
|
|
53
|
+
* voluntary_translation support with new model column.
|
|
54
|
+
|
|
55
|
+
## 0.1.0.rc4 (September 9, 2013) ##
|
|
56
|
+
|
|
57
|
+
* Select product in /workflow/user/products/:product_id/areas/:id
|
|
58
|
+
|
|
59
|
+
## 0.1.0.rc3 (September 6, 2013) ##
|
|
60
|
+
|
|
61
|
+
* Fixes invalid user update form by initializing presenter.
|
|
62
|
+
|
|
63
|
+
## 0.1.0.rc2 (July 31, 2013) ##
|
|
64
|
+
|
|
65
|
+
* Support nesting of areas. #1
|
|
66
|
+
|
|
67
|
+
## 0.1.0.rc1 (June 7, 2013) ##
|
|
68
|
+
|
|
69
|
+
* Updates twitter bootstrap and jquery ui.
|
|
70
|
+
* Removes rails_info dependency.
|
|
71
|
+
* Paints navigation black and more responsive.
|
|
72
|
+
* Allow mixin of cancan authorization abilities in products and client applications.
|
|
73
|
+
* Several small bug fixes and cleanup.
|
|
74
|
+
* Removes "twitter" (auth) dependencies
|
|
75
|
+
|
|
76
|
+
## 0.0.3 (November 19, 2012) ##
|
|
77
|
+
|
|
78
|
+
* Adds vendor_extensions to gem specification's directories.
|
|
79
|
+
|
|
80
|
+
## 0.0.2 (November 19, 2012) ##
|
|
81
|
+
|
|
82
|
+
* Fixes some bugs regarding integration of product engines.
|
|
83
|
+
|
|
84
|
+
* Adds product dummy generator.
|
|
85
|
+
|
|
86
|
+
## 0.0.1 (November 11, 2012) ##
|
|
87
|
+
|
|
88
|
+
* Initial version.
|
data/README.rdoc
CHANGED
|
@@ -12,7 +12,7 @@ Run this in your console:
|
|
|
12
12
|
|
|
13
13
|
rvm --create use 1.9.3@your_crowdsourcing_platform_name
|
|
14
14
|
gem update bundler
|
|
15
|
-
gem install rails -v
|
|
15
|
+
gem install rails -v 4.0.13 --no-rdoc --no-ri
|
|
16
16
|
rails new your_crowdsourcing_platform_name
|
|
17
17
|
cd your_crowdsourcing_platform_name
|
|
18
18
|
|
|
@@ -74,9 +74,9 @@ Run this in your console:
|
|
|
74
74
|
bundle install
|
|
75
75
|
# change config/boot.rb to require bundler like here: https://github.com/volontariat/voluntary_scholarship/blob/master/dummy/config/boot.rb
|
|
76
76
|
# change database names to #{product_name}_#{environment} and customize user credentials in config/database.yml
|
|
77
|
-
# add gitignore file from voluntary: https://github.com/volontariat/voluntary/blob/master/.gitignore
|
|
78
77
|
bundle exec rake db:create:all && bundle exec rails g voluntary:product_dummy # confirm all overwrite questions except of Gemfile
|
|
79
78
|
cd ..
|
|
79
|
+
# add gitignore file from voluntary: https://github.com/volontariat/voluntary/blob/master/.gitignore
|
|
80
80
|
rails g migration add_product_name_product
|
|
81
81
|
# fill migration file with template: https://github.com/volontariat/voluntary_scholarship/blob/master/db/migrate/20140306201232_add_scholarship_product.rb
|
|
82
82
|
cd dummy
|
|
@@ -5,33 +5,37 @@ $(document).ready ->
|
|
|
5
5
|
|
|
6
6
|
$( '.accordions' ).each (k, v) ->
|
|
7
7
|
$(v).accordion({ autoHeight: false });
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
$(v)
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
ui.newTab.find('.
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
ui
|
|
8
|
+
|
|
9
|
+
window.jquery_ui_tabs_initialization = ->
|
|
10
|
+
$('.tabs').each (k, v) ->
|
|
11
|
+
$(v).tabs
|
|
12
|
+
autoHeight: false
|
|
13
|
+
beforeActivate: (event, ui) ->
|
|
14
|
+
unless ui.newTab.find('a').attr('href').indexOf('#') == 0
|
|
15
|
+
ui.newTab.find('.ajax_spinner').show()
|
|
16
|
+
ui.newPanel.empty()
|
|
17
|
+
|
|
18
|
+
beforeLoad: (event, ui) ->
|
|
19
|
+
ui.jqXHR.error ->
|
|
20
|
+
unless ui.tab.find('a').attr('href').indexOf('#') == 0
|
|
21
|
+
ui.tab.find('.ajax_spinner').hide()
|
|
22
|
+
|
|
23
|
+
json = null
|
|
24
|
+
|
|
25
|
+
try
|
|
26
|
+
json = jQuery.parseJSON(ui.jqXHR.responseText)
|
|
27
|
+
catch e
|
|
28
|
+
|
|
29
|
+
error = if json && json['error'] then json['error'] else 'Something went wrong'
|
|
30
|
+
|
|
31
|
+
ui.panel.html error
|
|
32
|
+
|
|
33
|
+
load: (event, ui) ->
|
|
19
34
|
unless ui.tab.find('a').attr('href').indexOf('#') == 0
|
|
20
35
|
ui.tab.find('.ajax_spinner').hide()
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
try
|
|
25
|
-
json = jQuery.parseJSON(ui.jqXHR.responseText)
|
|
26
|
-
catch e
|
|
27
|
-
|
|
28
|
-
error = if json && json['error'] then json['error'] else 'Something went wrong'
|
|
29
|
-
|
|
30
|
-
ui.panel.html error
|
|
31
|
-
|
|
32
|
-
load: (event, ui) ->
|
|
33
|
-
unless ui.tab.find('a').attr('href').indexOf('#') == 0
|
|
34
|
-
ui.tab.find('.ajax_spinner').hide()
|
|
36
|
+
window.jquery_ui_tabs_initialization()
|
|
37
|
+
|
|
38
|
+
window.jquery_ui_tabs_initialization()
|
|
35
39
|
|
|
36
40
|
$(document).on "click", ".ui-tabs-panel .pagination a", (event) ->
|
|
37
41
|
event.preventDefault()
|
|
@@ -82,6 +86,8 @@ $(document).ready ->
|
|
|
82
86
|
$( ".datepicker" ).each (k, v) ->
|
|
83
87
|
$(v).datepicker({ dateFormat: "yy-mm-dd", changeYear: true, yearRange: "c-100:c+10" });
|
|
84
88
|
|
|
89
|
+
$('.datetime_picker').datetimepicker()
|
|
90
|
+
|
|
85
91
|
$(document.body).on "click", ".remote_links", (event) ->
|
|
86
92
|
$this = $(this)
|
|
87
93
|
|
|
@@ -93,13 +99,26 @@ $(document).ready ->
|
|
|
93
99
|
$(document.body).on "click", ".remote_modal_link", (event) ->
|
|
94
100
|
$this = $(this)
|
|
95
101
|
|
|
96
|
-
|
|
102
|
+
url = if $this.data('url') then $this.data('url') else $this.attr('href')
|
|
103
|
+
|
|
104
|
+
$.ajax(url: url, type: "GET", dataType: "html").success (data) ->
|
|
97
105
|
$('#bootstrap_modal').html(data)
|
|
98
|
-
$('#bootstrap_modal').modal(
|
|
106
|
+
$('#bootstrap_modal').modal(show: true, keyboard: false)
|
|
99
107
|
|
|
100
108
|
event.preventDefault()
|
|
101
109
|
|
|
102
110
|
$(document.body).on "click", "#close_bootstrap_modal_button", (event) ->
|
|
103
111
|
$('#bootstrap_modal').modal('hide')
|
|
104
112
|
event.preventDefault()
|
|
105
|
-
|
|
113
|
+
|
|
114
|
+
$(document.body).on "click", "#toggle_checkboxes_checkbox", (event) ->
|
|
115
|
+
if $('.toggleable_checkbox:checked').length == 0
|
|
116
|
+
$('.toggleable_checkbox').prop('checked', true)
|
|
117
|
+
else
|
|
118
|
+
$('.toggleable_checkbox').prop('checked', false)
|
|
119
|
+
|
|
120
|
+
$('.bootstrap_tooltip').tooltip()
|
|
121
|
+
|
|
122
|
+
$('.selectize_select').selectize
|
|
123
|
+
create: true,
|
|
124
|
+
sortField: 'text'
|
|
@@ -0,0 +1,254 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* jquery.multisortable.js - v0.2
|
|
3
|
+
* https://github.com/shvetsgroup/jquery.multisortable
|
|
4
|
+
*
|
|
5
|
+
* Author: Ethan Atlakson, Jay Hayes, Gabriel Such, Alexander Shvets
|
|
6
|
+
* Last Revision 3/16/2012
|
|
7
|
+
* multi-selectable, multi-sortable jQuery plugin
|
|
8
|
+
*/
|
|
9
|
+
|
|
10
|
+
!function($) {
|
|
11
|
+
|
|
12
|
+
$.fn.multiselectable = function(options) {
|
|
13
|
+
if (!options) {
|
|
14
|
+
options = {}
|
|
15
|
+
}
|
|
16
|
+
options = $.extend({}, $.fn.multiselectable.defaults, options);
|
|
17
|
+
|
|
18
|
+
function mouseDown(e) {
|
|
19
|
+
var item = $(this),
|
|
20
|
+
parent = item.parent(),
|
|
21
|
+
myIndex = item.index();
|
|
22
|
+
|
|
23
|
+
var prev = parent.find('.multiselectable-previous');
|
|
24
|
+
// If no previous selection found, start selecting from first selected item.
|
|
25
|
+
prev = prev.length ? prev : $(parent.find('.' + options.selectedClass)[0]).addClass('multiselectable-previous');
|
|
26
|
+
var prevIndex = prev.index();
|
|
27
|
+
|
|
28
|
+
if (e.ctrlKey || e.metaKey) {
|
|
29
|
+
if (item.hasClass(options.selectedClass)) {
|
|
30
|
+
item.removeClass(options.selectedClass).removeClass('multiselectable-previous')
|
|
31
|
+
if (item.not('.child').length) {
|
|
32
|
+
item.nextUntil(':not(.child)').removeClass(options.selectedClass);
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
else {
|
|
36
|
+
parent.find('.multiselectable-previous').removeClass('multiselectable-previous');
|
|
37
|
+
item.addClass(options.selectedClass).addClass('multiselectable-previous')
|
|
38
|
+
if (item.not('.child').length) {
|
|
39
|
+
item.nextUntil(':not(.child)').addClass(options.selectedClass);
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
if (e.shiftKey) {
|
|
45
|
+
var last_shift_range = parent.find('.multiselectable-shift');
|
|
46
|
+
last_shift_range.removeClass(options.selectedClass).removeClass('multiselectable-shift');
|
|
47
|
+
|
|
48
|
+
var shift_range;
|
|
49
|
+
if (prevIndex < myIndex) {
|
|
50
|
+
shift_range = item.prevUntil('.multiselectable-previous').add(prev).add(item);
|
|
51
|
+
}
|
|
52
|
+
else if (prevIndex > myIndex) {
|
|
53
|
+
shift_range = item.nextUntil('.multiselectable-previous').add(prev).add(item);
|
|
54
|
+
}
|
|
55
|
+
shift_range.addClass(options.selectedClass).addClass('multiselectable-shift');
|
|
56
|
+
}
|
|
57
|
+
else {
|
|
58
|
+
parent.find('.multiselectable-shift').removeClass('multiselectable-shift');
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
if (!e.ctrlKey && !e.metaKey && !e.shiftKey) {
|
|
62
|
+
parent.find('.multiselectable-previous').removeClass('multiselectable-previous');
|
|
63
|
+
if (!item.hasClass(options.selectedClass)) {
|
|
64
|
+
parent.find('.' + options.selectedClass).removeClass(options.selectedClass);
|
|
65
|
+
item.addClass(options.selectedClass).addClass('multiselectable-previous');
|
|
66
|
+
if (item.not('.child').length) {
|
|
67
|
+
item.nextUntil(':not(.child)').addClass(options.selectedClass);
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
options.mousedown(e, item);
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
function click(e) {
|
|
76
|
+
if ( $(this).is('.ui-draggable-dragging') ) {
|
|
77
|
+
return;
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
var item = $(this), parent = item.parent();
|
|
81
|
+
|
|
82
|
+
// If item wasn't draged and is not multiselected, it should reset selection for other items.
|
|
83
|
+
if (!e.ctrlKey && !e.metaKey && !e.shiftKey) {
|
|
84
|
+
parent.find('.multiselectable-previous').removeClass('multiselectable-previous');
|
|
85
|
+
parent.find('.' + options.selectedClass).removeClass(options.selectedClass);
|
|
86
|
+
item.addClass(options.selectedClass).addClass('multiselectable-previous');
|
|
87
|
+
if (item.not('.child').length) {
|
|
88
|
+
item.nextUntil(':not(.child)').addClass(options.selectedClass);
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
options.click(e, item);
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
return this.each(function() {
|
|
96
|
+
var list = $(this);
|
|
97
|
+
|
|
98
|
+
if (!list.data('multiselectable')) {
|
|
99
|
+
list.data('multiselectable', true)
|
|
100
|
+
.delegate(options.items, 'mousedown', mouseDown)
|
|
101
|
+
.delegate(options.items, 'click', click)
|
|
102
|
+
.disableSelection();
|
|
103
|
+
}
|
|
104
|
+
})
|
|
105
|
+
};
|
|
106
|
+
|
|
107
|
+
$.fn.multiselectable.defaults = {
|
|
108
|
+
click: function(event, elem) {},
|
|
109
|
+
mousedown: function(event, elem) {},
|
|
110
|
+
selectedClass: 'selected',
|
|
111
|
+
items: 'li'
|
|
112
|
+
};
|
|
113
|
+
|
|
114
|
+
|
|
115
|
+
$.fn.multisortable = function(options) {
|
|
116
|
+
if (!options) {
|
|
117
|
+
options = {}
|
|
118
|
+
}
|
|
119
|
+
var settings = $.extend({}, $.fn.multisortable.defaults, options);
|
|
120
|
+
|
|
121
|
+
function regroup(item, list) {
|
|
122
|
+
if (list.find('.' + settings.selectedClass).length > 0) {
|
|
123
|
+
var myIndex = item.data('i');
|
|
124
|
+
|
|
125
|
+
var itemsBefore = list.find('.' + settings.selectedClass).filter(function() {
|
|
126
|
+
return $(this).data('i') < myIndex
|
|
127
|
+
}).css({
|
|
128
|
+
position: '',
|
|
129
|
+
width: '',
|
|
130
|
+
left: '',
|
|
131
|
+
top: '',
|
|
132
|
+
zIndex: ''
|
|
133
|
+
});
|
|
134
|
+
|
|
135
|
+
item.before(itemsBefore);
|
|
136
|
+
|
|
137
|
+
var itemsAfter = list.find('.' + settings.selectedClass).filter(function() {
|
|
138
|
+
return $(this).data('i') > myIndex
|
|
139
|
+
}).css({
|
|
140
|
+
position: '',
|
|
141
|
+
width: '',
|
|
142
|
+
left: '',
|
|
143
|
+
top: '',
|
|
144
|
+
zIndex: ''
|
|
145
|
+
});
|
|
146
|
+
|
|
147
|
+
item.after(itemsAfter);
|
|
148
|
+
|
|
149
|
+
setTimeout(function() {
|
|
150
|
+
itemsAfter.add(itemsBefore).addClass(settings.selectedClass);
|
|
151
|
+
}, 0);
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
return this.each(function() {
|
|
156
|
+
var list = $(this);
|
|
157
|
+
|
|
158
|
+
//enable multi-selection
|
|
159
|
+
list.multiselectable({
|
|
160
|
+
selectedClass: settings.selectedClass,
|
|
161
|
+
click: settings.click,
|
|
162
|
+
items: settings.items,
|
|
163
|
+
mousedown: settings.mousedown
|
|
164
|
+
});
|
|
165
|
+
|
|
166
|
+
//enable sorting
|
|
167
|
+
options.cancel = settings.items + ':not(.' + settings.selectedClass + ')';
|
|
168
|
+
options.placeholder = settings.placeholder;
|
|
169
|
+
options.start = function(event, ui) {
|
|
170
|
+
if (ui.item.hasClass(settings.selectedClass)) {
|
|
171
|
+
var parent = ui.item.parent();
|
|
172
|
+
|
|
173
|
+
//assign indexes to all selected items
|
|
174
|
+
parent.find('.' + settings.selectedClass).each(function(i) {
|
|
175
|
+
$(this).data('i', i);
|
|
176
|
+
});
|
|
177
|
+
|
|
178
|
+
// adjust placeholder size to be size of items
|
|
179
|
+
var height = parent.find('.' + settings.selectedClass).length * ui.item.outerHeight();
|
|
180
|
+
ui.placeholder.height(height);
|
|
181
|
+
}
|
|
182
|
+
|
|
183
|
+
settings.start(event, ui);
|
|
184
|
+
};
|
|
185
|
+
|
|
186
|
+
options.stop = function(event, ui) {
|
|
187
|
+
regroup(ui.item, ui.item.parent());
|
|
188
|
+
settings.stop(event, ui);
|
|
189
|
+
};
|
|
190
|
+
|
|
191
|
+
options.sort = function(event, ui) {
|
|
192
|
+
var parent = ui.item.parent(),
|
|
193
|
+
myIndex = ui.item.data('i'),
|
|
194
|
+
top = parseInt(ui.item.css('top').replace('px', '')),
|
|
195
|
+
left = parseInt(ui.item.css('left').replace('px', ''));
|
|
196
|
+
|
|
197
|
+
// fix to keep compatibility using prototype.js and jquery together
|
|
198
|
+
$.fn.reverse = Array.prototype._reverse || Array.prototype.reverse
|
|
199
|
+
|
|
200
|
+
var height = 0;
|
|
201
|
+
$('.' + settings.selectedClass, parent).filter(function() {
|
|
202
|
+
return $(this).data('i') < myIndex;
|
|
203
|
+
}).reverse().each(function() {
|
|
204
|
+
height += $(this).outerHeight();
|
|
205
|
+
$(this).css({
|
|
206
|
+
left: left,
|
|
207
|
+
top: top - height,
|
|
208
|
+
position: 'absolute',
|
|
209
|
+
zIndex: 1000,
|
|
210
|
+
width: ui.item.width()
|
|
211
|
+
})
|
|
212
|
+
});
|
|
213
|
+
|
|
214
|
+
height = ui.item.outerHeight();
|
|
215
|
+
$('.' + settings.selectedClass, parent).filter(function() {
|
|
216
|
+
return $(this).data('i') > myIndex;
|
|
217
|
+
}).each(function() {
|
|
218
|
+
var item = $(this);
|
|
219
|
+
item.css({
|
|
220
|
+
left: left,
|
|
221
|
+
top: top + height,
|
|
222
|
+
position: 'absolute',
|
|
223
|
+
zIndex: 1000,
|
|
224
|
+
width: ui.item.width()
|
|
225
|
+
});
|
|
226
|
+
|
|
227
|
+
height += item.outerHeight();
|
|
228
|
+
});
|
|
229
|
+
|
|
230
|
+
settings.sort(event, ui);
|
|
231
|
+
};
|
|
232
|
+
|
|
233
|
+
options.receive = function(event, ui) {
|
|
234
|
+
regroup(ui.item, ui.sender);
|
|
235
|
+
settings.receive(event, ui);
|
|
236
|
+
};
|
|
237
|
+
|
|
238
|
+
list.sortable(options).disableSelection();
|
|
239
|
+
})
|
|
240
|
+
};
|
|
241
|
+
|
|
242
|
+
$.fn.multisortable.defaults = {
|
|
243
|
+
start: function(event, ui) {},
|
|
244
|
+
stop: function(event, ui) {},
|
|
245
|
+
sort: function(event, ui) {},
|
|
246
|
+
receive: function(event, ui) {},
|
|
247
|
+
click: function(event, elem) {},
|
|
248
|
+
mousedown: function(event, elem) {},
|
|
249
|
+
selectedClass: 'selected',
|
|
250
|
+
placeholder: 'placeholder',
|
|
251
|
+
items: 'li'
|
|
252
|
+
};
|
|
253
|
+
|
|
254
|
+
}(jQuery);
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
@import "twitter/bootstrap/responsive"
|
|
2
|
+
@import 'bootstrap-datetimepicker'
|
|
2
3
|
|
|
3
4
|
.list-striped
|
|
4
5
|
li:nth-child(odd)
|
|
@@ -11,4 +12,7 @@
|
|
|
11
12
|
overflow-y: visible
|
|
12
13
|
|
|
13
14
|
.scrollable-modal-body
|
|
14
|
-
overflow-y: auto
|
|
15
|
+
overflow-y: auto
|
|
16
|
+
|
|
17
|
+
#bootstrap_modal
|
|
18
|
+
width: 800px !important
|
|
@@ -8,7 +8,8 @@ module Voluntary
|
|
|
8
8
|
rescue_from ActiveRecord::RecordNotFound, with: :not_found
|
|
9
9
|
rescue_from Mongoid::Errors::DocumentNotFound, with: :not_found
|
|
10
10
|
|
|
11
|
-
helper_method :parent, :application_navigation, :navigation_product_path, :navigation_product_name, :voluntary_application_stylesheets
|
|
11
|
+
helper_method :parent, :application_navigation, :navigation_product_path, :navigation_product_name, :voluntary_application_stylesheets
|
|
12
|
+
helper_method :voluntary_application_javascripts, :voluntary_application_repository_path
|
|
12
13
|
end
|
|
13
14
|
|
|
14
15
|
def voluntary_application_stylesheets
|
|
@@ -18,6 +19,10 @@ module Voluntary
|
|
|
18
19
|
def voluntary_application_javascripts
|
|
19
20
|
['voluntary/application', 'application']
|
|
20
21
|
end
|
|
22
|
+
|
|
23
|
+
def voluntary_application_repository_path
|
|
24
|
+
'volontariat/voluntary'
|
|
25
|
+
end
|
|
21
26
|
|
|
22
27
|
def parent
|
|
23
28
|
@parent
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
module Voluntary
|
|
2
|
+
module Api
|
|
3
|
+
module V1
|
|
4
|
+
class BaseController < ActionController::Base #ActionController::Metal
|
|
5
|
+
#include ActionController::Rendering # enables rendering
|
|
6
|
+
#include ActionController::MimeResponds # enables serving different content types like :xml or :json
|
|
7
|
+
#include AbstractController::Callbacks # callbacks for your authentication logic
|
|
8
|
+
end
|
|
9
|
+
end
|
|
10
|
+
end
|
|
11
|
+
end
|
|
@@ -53,11 +53,11 @@ module Voluntary
|
|
|
53
53
|
end
|
|
54
54
|
end
|
|
55
55
|
|
|
56
|
-
def show_actions
|
|
56
|
+
def show_actions(options = {})
|
|
57
57
|
result = content_tag :dt, raw(' ')
|
|
58
58
|
result += content_tag :dd, render(
|
|
59
59
|
partial: 'shared/resource/actions', locals: {
|
|
60
|
-
type: root_model_class_name(resource).tableize, resource: resource
|
|
60
|
+
type: root_model_class_name(resource).tableize, resource: resource, namespace: options[:namespace]
|
|
61
61
|
}
|
|
62
62
|
)
|
|
63
63
|
|
|
@@ -8,9 +8,20 @@ module Likeable
|
|
|
8
8
|
has_many :likers, class_name: 'User', through: :likes, source: :user
|
|
9
9
|
has_many :dislikes, -> { where(positive: false) }, class_name: 'Like', dependent: :delete_all, as: :target
|
|
10
10
|
has_many :dislikers, class_name: 'User', through: :dislikes, source: :user
|
|
11
|
+
|
|
12
|
+
scope :liked_by, ->(user_id) do
|
|
13
|
+
select('music_videos.*, likes.created_at AS liked_at').joins('RIGHT JOIN likes ON likes.positive = 1 AND likes.target_type = "MusicVideo" AND likes.target_id = music_videos.id').
|
|
14
|
+
where('likes.user_id = ? AND music_videos.id IS NOT NULL', user_id)
|
|
15
|
+
end
|
|
11
16
|
end
|
|
12
17
|
|
|
13
18
|
def update_likes_counter
|
|
14
19
|
self.class.where(id: self.id).update_all likes_count: self.likes.count, dislikes_count: self.dislikes.count
|
|
15
20
|
end
|
|
21
|
+
|
|
22
|
+
module ClassMethods
|
|
23
|
+
def likes_or_dislikes_for(user, ids)
|
|
24
|
+
user.likes_or_dislikes.for_targets(name, ids).index_by(&:target_id)
|
|
25
|
+
end
|
|
26
|
+
end
|
|
16
27
|
end
|
data/app/models/user.rb
CHANGED
|
@@ -13,6 +13,10 @@
|
|
|
13
13
|
|
|
14
14
|
<%= render 'layouts/shared/navigation' %>
|
|
15
15
|
|
|
16
|
+
<% if voluntary_application_repository_path.present? %>
|
|
17
|
+
<a href="https://github.com/<%= voluntary_application_repository_path %>"><img style="position: absolute; top: 41px; right: 0; border: 0; z-index: 100;" src="https://camo.githubusercontent.com/365986a132ccd6a44c23a9169022c0b5c890c387/68747470733a2f2f73332e616d617a6f6e6177732e636f6d2f6769746875622f726962626f6e732f666f726b6d655f72696768745f7265645f6161303030302e706e67" alt="Fork me on GitHub" data-canonical-src="https://s3.amazonaws.com/github/ribbons/forkme_right_red_aa0000.png"></a>
|
|
18
|
+
<% end %>
|
|
19
|
+
|
|
16
20
|
<section id="dialog">
|
|
17
21
|
<img alt="Ajax-loader-small" class="hide " id="dialog_body_spinner" src="<%=image_path('voluntary/spinner.gif')%>"/>
|
|
18
22
|
<div id="dialog_body"/>
|
|
@@ -27,7 +31,7 @@
|
|
|
27
31
|
</div>
|
|
28
32
|
<% end %>
|
|
29
33
|
<div class="row-fluid">
|
|
30
|
-
<% if sidenav(@sidenav_links_count).present? || content_for?(:search) %>
|
|
34
|
+
<% if sidenav(@sidenav_links_count).present? || content_for?(:search) || content_for?(:sidebar) %>
|
|
31
35
|
<div class="span9">
|
|
32
36
|
<% if content_for?(:breadcrumbs) %>
|
|
33
37
|
<div class="nav">
|
|
@@ -43,6 +47,8 @@
|
|
|
43
47
|
<%= yield :search %>
|
|
44
48
|
|
|
45
49
|
<%= sidenav(@sidenav_links_count) %>
|
|
50
|
+
|
|
51
|
+
<%= yield :sidebar %>
|
|
46
52
|
</div>
|
|
47
53
|
<% else %>
|
|
48
54
|
<div class="span12">
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
<% namespace ||= nil %>
|
|
2
|
+
<% message = flash[:notice].present? ? flash[:notice].clone : nil %>
|
|
3
|
+
<% flash.delete(:notice) %>
|
|
4
|
+
<% message = flash[:alert].present? ? flash[:alert].clone : message %>
|
|
5
|
+
<% flash.delete(:alert) %>
|
|
6
|
+
<% ajax_data ||= {} %>
|
|
7
|
+
<% ajax_method ||= :get %>
|
|
8
|
+
|
|
9
|
+
<% if @path.present? %>
|
|
10
|
+
$.ajax({ url: "<%= @path %>", data: <%= raw ajax_data.to_json %>, type: "<%= ajax_method.to_s.upcase %>", dataType: "script"}).done(function(data) {
|
|
11
|
+
eval(data);
|
|
12
|
+
<%= message.present? ? raw('alert("' + message + '");') : '' %>
|
|
13
|
+
})
|
|
14
|
+
.fail(function(data) {
|
|
15
|
+
<%= message.present? ? raw('alert("' + message + '");') : '' %>
|
|
16
|
+
alert("Failed to load <%= @path %>!");
|
|
17
|
+
});
|
|
18
|
+
<% elsif @template.present? %>
|
|
19
|
+
$("#bootstrap_modal").html("<%= escape_javascript(
|
|
20
|
+
render(
|
|
21
|
+
partial: 'shared/layouts/twitter_bootstrap/modal',
|
|
22
|
+
locals: {
|
|
23
|
+
title: title,
|
|
24
|
+
body: render(template: "#{namespace}#{@template}.html")
|
|
25
|
+
}
|
|
26
|
+
)
|
|
27
|
+
) %>");
|
|
28
|
+
<%= message.present? ? raw('alert("' + message + '");') : '' %>
|
|
29
|
+
<% elsif message.present? %>
|
|
30
|
+
<%= message.present? ? raw('alert("' + message + '");') : '' %>
|
|
31
|
+
<% end %>
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
<% id ||= field.match(/id="([^"]*)"/)[1] %>
|
|
2
|
+
<% required ||= false %>
|
|
3
|
+
<% required_class = required ? ' required' : ' optional' %>
|
|
4
|
+
<div class="control-group string<%= required_class %> <%= id %>">
|
|
5
|
+
<label for="<%= id %>" class="string<%= required_class %> control-label">
|
|
6
|
+
<% if required %><abbr title="required">*</abbr><% end %> <%= label %>
|
|
7
|
+
</label>
|
|
8
|
+
<div class="controls">
|
|
9
|
+
<%= field %>
|
|
10
|
+
</div>
|
|
11
|
+
</div>
|