surveyor 0.22.0 → 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (144) hide show
  1. data/.gitignore +1 -0
  2. data/.rspec +1 -0
  3. data/CHANGELOG.md +83 -0
  4. data/Gemfile.rails_version +7 -1
  5. data/README.md +114 -16
  6. data/Rakefile +15 -9
  7. data/app/inputs/quiet_input.rb +5 -0
  8. data/app/inputs/surveyor_check_boxes_input.rb +35 -0
  9. data/app/inputs/surveyor_radio_input.rb +18 -0
  10. data/app/views/partials/_answer.html.haml +4 -4
  11. data/app/views/partials/_question.html.haml +7 -7
  12. data/app/views/partials/_question_group.html.haml +9 -8
  13. data/app/views/surveyor/export.json.rabl +28 -25
  14. data/app/views/surveyor/new.html.haml +8 -5
  15. data/app/views/surveyor/show.json.rabl +3 -2
  16. data/ci-exec.sh +13 -7
  17. data/cucumber.yml +3 -3
  18. data/doc/REPRESENTATIONS.md +34 -0
  19. data/doc/api_id_schema.json +7 -0
  20. data/doc/response_set_schema.json +54 -0
  21. data/doc/surveyor question combinations.png +0 -0
  22. data/doc/surveyor_timestamp_schema.json +9 -0
  23. data/features/ajax_submissions.feature +140 -0
  24. data/features/export_to_json.feature +182 -34
  25. data/features/no_duplicates.feature +110 -0
  26. data/features/show_survey.feature +1 -1
  27. data/features/step_definitions/parser_steps.rb +25 -2
  28. data/features/step_definitions/surveyor_steps.rb +145 -20
  29. data/features/step_definitions/ui_steps.rb +3 -0
  30. data/features/support/database_cleaner.rb +16 -0
  31. data/features/support/env.rb +21 -17
  32. data/features/support/simultaneous_ajax.rb +101 -0
  33. data/features/support/single_quit_selenium_driver.rb +23 -0
  34. data/features/support/slow_updates.rb +18 -0
  35. data/features/surveyor.feature +174 -44
  36. data/features/surveyor_dependencies.feature +80 -39
  37. data/features/surveyor_parser.feature +114 -20
  38. data/features/z_redcap_parser.feature +0 -1
  39. data/lib/{generators/surveyor/templates/public → assets}/images/surveyor/next.gif +0 -0
  40. data/lib/{generators/surveyor/templates/public → assets}/images/surveyor/prev.gif +0 -0
  41. data/lib/{generators/surveyor/templates/public/stylesheets/surveyor → assets/images}/ui-bg_glass_100_f6f6f6_1x400.png +0 -0
  42. data/lib/{generators/surveyor/templates/public/stylesheets/surveyor → assets/images}/ui-bg_glass_100_fdf5ce_1x400.png +0 -0
  43. data/lib/{generators/surveyor/templates/public/stylesheets/surveyor → assets/images}/ui-bg_glass_65_ffffff_1x400.png +0 -0
  44. data/lib/{generators/surveyor/templates/public/stylesheets/surveyor → assets/images}/ui-bg_gloss-wave_35_f6a828_500x100.png +0 -0
  45. data/lib/assets/images/ui-bg_highlight-soft_100_eeeeee_1x100.png +0 -0
  46. data/lib/{generators/surveyor/templates/public/stylesheets/surveyor → assets/images}/ui-bg_highlight-soft_75_ffe45c_1x100.png +0 -0
  47. data/lib/{generators/surveyor/templates/public/stylesheets/surveyor → assets/images}/ui-icons_ef8c08_256x240.png +0 -0
  48. data/lib/{generators/surveyor/templates/public/stylesheets/surveyor → assets/images}/ui-icons_ffffff_256x240.png +0 -0
  49. data/lib/{generators/surveyor/templates/public → assets}/javascripts/surveyor/jquery-ui-timepicker-addon.js +23 -23
  50. data/lib/{generators/surveyor/templates/public → assets}/javascripts/surveyor/jquery-ui.js +125 -125
  51. data/lib/assets/javascripts/surveyor/jquery.selectToUISlider.js +240 -0
  52. data/lib/{generators/surveyor/templates/public → assets}/javascripts/surveyor/jquery.surveyor.js +52 -57
  53. data/lib/{generators/surveyor/templates/public → assets}/javascripts/surveyor/jquery.tools.min.js +7 -7
  54. data/lib/{generators/surveyor/templates/public → assets}/stylesheets/surveyor/dateinput.css +13 -13
  55. data/lib/{generators/surveyor/templates/public → assets}/stylesheets/surveyor/jquery-ui-timepicker-addon.css +0 -0
  56. data/lib/{generators/surveyor/templates/public → assets}/stylesheets/surveyor/jquery-ui.custom.css +17 -17
  57. data/lib/{generators/surveyor/templates/public → assets}/stylesheets/surveyor/reset.css +1 -1
  58. data/lib/{generators/surveyor/templates/public → assets}/stylesheets/surveyor/results.css +0 -0
  59. data/lib/assets/stylesheets/surveyor/ui.slider.extras.css +110 -0
  60. data/lib/{generators/surveyor/templates/public/stylesheets/sass → assets/stylesheets}/surveyor.sass +15 -7
  61. data/lib/generators/surveyor/custom_generator.rb +3 -2
  62. data/lib/generators/surveyor/install_generator.rb +59 -17
  63. data/lib/generators/surveyor/templates/app/assets/javascripts/surveyor_all.js +5 -0
  64. data/lib/generators/surveyor/templates/app/assets/stylesheets/surveyor_all.css +9 -0
  65. data/lib/generators/surveyor/templates/app/controllers/surveyor_controller.rb +2 -1
  66. data/lib/generators/surveyor/templates/app/views/layouts/surveyor_custom.html.erb +1 -0
  67. data/lib/generators/surveyor/templates/config/locales/surveyor_es.yml +1 -0
  68. data/lib/generators/surveyor/templates/config/locales/surveyor_he.yml +1 -0
  69. data/lib/generators/surveyor/templates/db/migrate/add_api_id_to_question_groups.rb +1 -0
  70. data/lib/generators/surveyor/templates/db/migrate/add_api_ids.rb +1 -0
  71. data/lib/generators/surveyor/templates/db/migrate/add_api_ids_to_response_sets_and_responses.rb +1 -0
  72. data/lib/generators/surveyor/templates/db/migrate/add_correct_answer_id_to_questions.rb +1 -0
  73. data/lib/generators/surveyor/templates/db/migrate/add_default_value_to_answers.rb +1 -0
  74. data/lib/generators/surveyor/templates/db/migrate/add_display_order_to_surveys.rb +1 -0
  75. data/lib/generators/surveyor/templates/db/migrate/add_display_type_to_answers.rb +1 -0
  76. data/lib/generators/surveyor/templates/db/migrate/add_index_to_response_sets.rb +1 -0
  77. data/lib/generators/surveyor/templates/db/migrate/add_index_to_surveys.rb +1 -0
  78. data/lib/generators/surveyor/templates/db/migrate/add_section_id_to_responses.rb +1 -0
  79. data/lib/generators/surveyor/templates/db/migrate/add_unique_index_on_access_code_and_version_in_surveys.rb +10 -0
  80. data/lib/generators/surveyor/templates/db/migrate/add_unique_indicies.rb +3 -2
  81. data/lib/generators/surveyor/templates/db/migrate/add_version_to_surveys.rb +10 -0
  82. data/lib/generators/surveyor/templates/db/migrate/api_ids_must_be_unique.rb +23 -0
  83. data/lib/generators/surveyor/templates/db/migrate/create_answers.rb +6 -5
  84. data/lib/generators/surveyor/templates/db/migrate/create_dependencies.rb +2 -1
  85. data/lib/generators/surveyor/templates/db/migrate/create_dependency_conditions.rb +2 -1
  86. data/lib/generators/surveyor/templates/db/migrate/create_question_groups.rb +5 -4
  87. data/lib/generators/surveyor/templates/db/migrate/create_questions.rb +4 -3
  88. data/lib/generators/surveyor/templates/db/migrate/create_response_sets.rb +1 -0
  89. data/lib/generators/surveyor/templates/db/migrate/create_responses.rb +10 -9
  90. data/lib/generators/surveyor/templates/db/migrate/create_survey_sections.rb +5 -4
  91. data/lib/generators/surveyor/templates/db/migrate/create_surveys.rb +4 -3
  92. data/lib/generators/surveyor/templates/db/migrate/create_validation_conditions.rb +5 -4
  93. data/lib/generators/surveyor/templates/db/migrate/create_validations.rb +3 -2
  94. data/lib/generators/surveyor/templates/db/migrate/drop_unique_index_on_access_code_in_surveys.rb +10 -0
  95. data/lib/generators/surveyor/templates/db/migrate/update_blank_api_ids_on_question_group.rb +22 -0
  96. data/lib/generators/surveyor/templates/db/migrate/update_blank_versions_on_surveys.rb +13 -0
  97. data/lib/generators/surveyor/templates/surveys/date_survey.rb +1 -0
  98. data/lib/generators/surveyor/templates/surveys/kitchen_sink_survey.rb +54 -24
  99. data/lib/generators/surveyor/templates/surveys/quiz.rb +1 -0
  100. data/lib/generators/surveyor/templates/{public/stylesheets/sass → vendor/assets/stylesheets}/custom.sass +1 -1
  101. data/lib/surveyor/common.rb +16 -31
  102. data/lib/surveyor/engine.rb +2 -4
  103. data/lib/surveyor/helpers/asset_pipeline.rb +13 -0
  104. data/lib/surveyor/helpers/formtastic_custom_input.rb +17 -0
  105. data/lib/surveyor/helpers/surveyor_helper_methods.rb +10 -8
  106. data/lib/surveyor/models/answer_methods.rb +3 -0
  107. data/lib/surveyor/models/dependency_condition_methods.rb +27 -28
  108. data/lib/surveyor/models/dependency_methods.rb +3 -0
  109. data/lib/surveyor/models/question_group_methods.rb +3 -0
  110. data/lib/surveyor/models/question_methods.rb +10 -7
  111. data/lib/surveyor/models/response_methods.rb +16 -0
  112. data/lib/surveyor/models/response_set_methods.rb +71 -64
  113. data/lib/surveyor/models/survey_methods.rb +19 -28
  114. data/lib/surveyor/models/survey_section_methods.rb +3 -0
  115. data/lib/surveyor/models/validation_condition_methods.rb +4 -2
  116. data/lib/surveyor/models/validation_methods.rb +3 -0
  117. data/lib/surveyor/parser.rb +198 -148
  118. data/lib/surveyor/redcap_parser.rb +120 -80
  119. data/lib/surveyor/surveyor_controller_methods.rb +86 -37
  120. data/lib/surveyor/version.rb +2 -2
  121. data/lib/surveyor.rb +5 -6
  122. data/lib/tasks/surveyor_tasks.rake +19 -7
  123. data/spec/controllers/surveyor_controller_spec.rb +166 -92
  124. data/spec/factories.rb +33 -32
  125. data/spec/helpers/formtastic_custom_input_spec.rb +16 -0
  126. data/spec/lib/common_spec.rb +0 -39
  127. data/spec/lib/redcap_parser_spec.rb +24 -24
  128. data/spec/models/answer_spec.rb +12 -0
  129. data/spec/models/dependency_condition_spec.rb +279 -323
  130. data/spec/models/dependency_spec.rb +10 -0
  131. data/spec/models/question_group_spec.rb +12 -0
  132. data/spec/models/question_spec.rb +12 -0
  133. data/spec/models/response_set_spec.rb +189 -139
  134. data/spec/models/response_spec.rb +60 -0
  135. data/spec/models/survey_section_spec.rb +9 -0
  136. data/spec/models/survey_spec.rb +72 -9
  137. data/spec/models/validation_condition_spec.rb +9 -1
  138. data/spec/models/validation_spec.rb +10 -0
  139. data/spec/spec_helper.rb +25 -6
  140. data/surveyor.gemspec +5 -4
  141. metadata +332 -291
  142. data/features/step_definitions/common_steps.rb +0 -3
  143. data/lib/formtastic/surveyor_builder.rb +0 -82
  144. data/lib/generators/surveyor/templates/public/javascripts/surveyor/jquery.blockUI.js +0 -499
@@ -0,0 +1,240 @@
1
+ /*
2
+ * --------------------------------------------------------------------
3
+ * jQuery-Plugin - selectToUISlider - creates a UI slider component from a select element(s)
4
+ * by Scott Jehl, scott@filamentgroup.com
5
+ * http://www.filamentgroup.com
6
+ * reference article: http://www.filamentgroup.com/lab/update_jquery_ui_16_slider_from_a_select_element/
7
+ * demo page: http://www.filamentgroup.com/examples/slider_v2/index.html
8
+ *
9
+ * Copyright (c) 2008 Filament Group, Inc
10
+ * Dual licensed under the MIT (filamentgroup.com/examples/mit-license.txt) and GPL (filamentgroup.com/examples/gpl-license.txt) licenses.
11
+ *
12
+ * Usage Notes: please refer to our article above for documentation
13
+ *
14
+ * --------------------------------------------------------------------
15
+ */
16
+
17
+
18
+ jQuery.fn.selectToUISlider = function(settings){
19
+ var selects = jQuery(this);
20
+
21
+ //accessible slider options
22
+ var options = jQuery.extend({
23
+ labels: 3, //number of visible labels
24
+ tooltip: true, //show tooltips, boolean
25
+ tooltipSrc: 'text',//accepts 'value' as well
26
+ labelSrc: 'value',//accepts 'value' as well ,
27
+ sliderOptions: null
28
+ }, settings);
29
+
30
+
31
+ //handle ID attrs - selects each need IDs for handles to find them
32
+ var handleIds = (function(){
33
+ var tempArr = [];
34
+ selects.each(function(){
35
+ tempArr.push('handle_'+jQuery(this).attr('id'));
36
+ });
37
+ return tempArr;
38
+ })();
39
+
40
+ //array of all option elements in select element (ignores optgroups)
41
+ var selectOptions = (function(){
42
+ var opts = [];
43
+ selects.eq(0).find('option').each(function(){
44
+ opts.push({
45
+ value: jQuery(this).attr('value'),
46
+ text: jQuery(this).text()
47
+ });
48
+ });
49
+ return opts;
50
+ })();
51
+
52
+ //array of opt groups if present
53
+ var groups = (function(){
54
+ if(selects.eq(0).find('optgroup').size()>0){
55
+ var groupedData = [];
56
+ selects.eq(0).find('optgroup').each(function(i){
57
+ groupedData[i] = {};
58
+ groupedData[i].label = jQuery(this).attr('label');
59
+ groupedData[i].options = [];
60
+ jQuery(this).find('option').each(function(){
61
+ groupedData[i].options.push({text: jQuery(this).text(), value: jQuery(this).attr('value')});
62
+ });
63
+ });
64
+ return groupedData;
65
+ }
66
+ else return null;
67
+ })();
68
+
69
+ //check if obj is array
70
+ function isArray(obj) {
71
+ return obj.constructor == Array;
72
+ }
73
+ //return tooltip text from option index
74
+ function ttText(optIndex){
75
+ return (options.tooltipSrc == 'text') ? selectOptions[optIndex].text : selectOptions[optIndex].value;
76
+ }
77
+
78
+ //plugin-generated slider options (can be overridden)
79
+ var sliderOptions = {
80
+ step: 1,
81
+ min: 0,
82
+ orientation: 'horizontal',
83
+ max: selectOptions.length-1,
84
+ range: selects.length > 1,//multiple select elements = true
85
+ slide: function(e, ui) {//slide function
86
+ var thisHandle = jQuery(ui.handle);
87
+ //handle feedback
88
+ var textval = ttText(ui.value);
89
+ thisHandle
90
+ .attr('aria-valuetext', textval)
91
+ .attr('aria-valuenow', ui.value)
92
+ .find('.ui-slider-tooltip .ttContent')
93
+ .text( textval );
94
+
95
+ //control original select menu
96
+ var currSelect = jQuery('#' + thisHandle.attr('id').split('handle_')[1]);
97
+ currSelect.find('option').eq(ui.value).attr('selected', 'selected');
98
+ },
99
+ values: (function(){
100
+ var values = [];
101
+ selects.each(function(){
102
+ values.push( jQuery(this).get(0).selectedIndex );
103
+ });
104
+ return values;
105
+ })()
106
+ };
107
+
108
+ //slider options from settings
109
+ options.sliderOptions = (settings) ? jQuery.extend(sliderOptions, settings.sliderOptions) : sliderOptions;
110
+
111
+ //select element change event
112
+ selects.bind('change keyup click', function(){
113
+ var thisIndex = jQuery(this).get(0).selectedIndex;
114
+ var thisHandle = jQuery('#handle_'+ jQuery(this).attr('id'));
115
+ var handleIndex = thisHandle.data('handleNum');
116
+ thisHandle.parents('.ui-slider:eq(0)').slider("values", handleIndex, thisIndex);
117
+ });
118
+
119
+
120
+ //create slider component div
121
+ var sliderComponent = jQuery('<div></div>');
122
+
123
+ //CREATE HANDLES
124
+ selects.each(function(i){
125
+ var hidett = '';
126
+
127
+ //associate label for ARIA
128
+ var thisLabel = jQuery('label[for=' + jQuery(this).attr('id') +']');
129
+ //labelled by aria doesn't seem to work on slider handle. Using title attr as backup
130
+ var labelText = (thisLabel.size()>0) ? 'Slider control for '+ thisLabel.text()+'' : '';
131
+ var thisLabelId = thisLabel.attr('id') || thisLabel.attr('id', 'label_'+handleIds[i]).attr('id');
132
+
133
+
134
+ if( options.tooltip == false ){hidett = ' style="display: none;"';}
135
+ jQuery('<a '+
136
+ 'href="#" tabindex="0" '+
137
+ 'id="'+handleIds[i]+'" '+
138
+ 'class="ui-slider-handle" '+
139
+ 'role="slider" '+
140
+ 'aria-labelledby="'+thisLabelId+'" '+
141
+ 'aria-valuemin="'+options.sliderOptions.min+'" '+
142
+ 'aria-valuemax="'+options.sliderOptions.max+'" '+
143
+ 'aria-valuenow="'+options.sliderOptions.values[i]+'" '+
144
+ 'aria-valuetext="'+ttText(options.sliderOptions.values[i])+'" '+
145
+ '><span class="screenReaderContext">'+labelText+'</span>'+
146
+ '<span class="ui-slider-tooltip ui-widget-content ui-corner-all"'+ hidett +'><span class="ttContent"></span>'+
147
+ '<span class="ui-tooltip-pointer-down ui-widget-content"><span class="ui-tooltip-pointer-down-inner"></span></span>'+
148
+ '</span></a>')
149
+ .data('handleNum',i)
150
+ .appendTo(sliderComponent);
151
+ });
152
+
153
+ //CREATE SCALE AND TICS
154
+
155
+ //write dl if there are optgroups
156
+ if(groups) {
157
+ var inc = 0;
158
+ var scale = sliderComponent.append('<dl class="ui-slider-scale ui-helper-reset" role="presentation"></dl>').find('.ui-slider-scale:eq(0)');
159
+ jQuery(groups).each(function(h){
160
+ scale.append('<dt style="width: '+ (100/groups.length).toFixed(2) +'%' +'; left:'+ (h/(groups.length-1) * 100).toFixed(2) +'%' +'"><span>'+this.label+'</span></dt>');//class name becomes camelCased label
161
+ var groupOpts = this.options;
162
+ jQuery(this.options).each(function(i){
163
+ var style = (inc == selectOptions.length-1 || inc == 0) ? 'style="display: none;"' : '' ;
164
+ var labelText = (options.labelSrc == 'text') ? groupOpts[i].text : groupOpts[i].value;
165
+ scale.append('<dd style="left:'+ leftVal(inc) +'"><span class="ui-slider-label">'+ labelText +'</span><span class="ui-slider-tic ui-widget-content"'+ style +'></span></dd>');
166
+ inc++;
167
+ });
168
+ });
169
+ }
170
+ //write ol
171
+ else {
172
+ var scale = sliderComponent.append('<ol class="ui-slider-scale ui-helper-reset" role="presentation"></ol>').find('.ui-slider-scale:eq(0)');
173
+ jQuery(selectOptions).each(function(i){
174
+ var style = (i == selectOptions.length-1 || i == 0) ? 'style="display: none;"' : '' ;
175
+ var labelText = (options.labelSrc == 'text') ? this.text : this.value;
176
+ scale.append('<li style="left:'+ leftVal(i) +'"><span class="ui-slider-label">'+ labelText +'</span><span class="ui-slider-tic ui-widget-content"'+ style +'></span></li>');
177
+ });
178
+ }
179
+
180
+ function leftVal(i){
181
+ return (i/(selectOptions.length-1) * 100).toFixed(2) +'%';
182
+
183
+ }
184
+
185
+
186
+
187
+
188
+ //show and hide labels depending on labels pref
189
+ //show the last one if there are more than 1 specified
190
+ if(options.labels > 1) sliderComponent.find('.ui-slider-scale li:last span.ui-slider-label, .ui-slider-scale dd:last span.ui-slider-label').addClass('ui-slider-label-show');
191
+
192
+ //set increment
193
+ var increm = Math.max(1, Math.round(selectOptions.length / options.labels));
194
+ //show em based on inc
195
+ for(var j=0; j<selectOptions.length; j+=increm){
196
+ if((selectOptions.length - j) > increm){//don't show if it's too close to the end label
197
+ sliderComponent.find('.ui-slider-scale li:eq('+ j +') span.ui-slider-label, .ui-slider-scale dd:eq('+ j +') span.ui-slider-label').addClass('ui-slider-label-show');
198
+ }
199
+ }
200
+
201
+ //style the dt's
202
+ sliderComponent.find('.ui-slider-scale dt').each(function(i){
203
+ jQuery(this).css({
204
+ 'left': ((100 /( groups.length))*i).toFixed(2) + '%'
205
+ });
206
+ });
207
+
208
+
209
+ //inject and return
210
+ sliderComponent
211
+ .insertAfter(jQuery(this).eq(this.length-1))
212
+ .slider(options.sliderOptions)
213
+ .attr('role','application')
214
+ .find('.ui-slider-label')
215
+ .each(function(){
216
+ jQuery(this).css('marginLeft', -jQuery(this).width()/2);
217
+ });
218
+
219
+ //update tooltip arrow inner color
220
+ sliderComponent.find('.ui-tooltip-pointer-down-inner').each(function(){
221
+ var bWidth = jQuery('.ui-tooltip-pointer-down-inner').css('borderTopWidth');
222
+ var bColor = jQuery(this).parents('.ui-slider-tooltip').css('backgroundColor')
223
+ jQuery(this).css('border-top', bWidth+' solid '+bColor);
224
+ });
225
+
226
+ var values = sliderComponent.slider('values');
227
+
228
+ if(isArray(values)){
229
+ jQuery(values).each(function(i){
230
+ sliderComponent.find('.ui-slider-tooltip .ttContent').eq(i).text( ttText(this) );
231
+ });
232
+ }
233
+ else {
234
+ sliderComponent.find('.ui-slider-tooltip .ttContent').eq(0).text( ttText(values) );
235
+ }
236
+
237
+ return this;
238
+ }
239
+
240
+
@@ -30,79 +30,81 @@ jQuery(document).ready(function(){
30
30
  // $('li input.date').dateinput({
31
31
  // format: 'dd mmm yyyy'
32
32
  // });
33
-
34
- // Default Datepicker uses jQuery UI Datepicker
33
+
34
+ // Default Datepicker uses jQuery UI Datepicker
35
35
  jQuery("input[type='text'].datetime").datetimepicker({
36
- showSecond: true,
37
- showMillisec: false,
38
- timeFormat: 'hh:mm:ss',
39
- dateFormat: 'yy-mm-dd',
40
- changeMonth: true,
41
- changeYear: true
36
+ showSecond: true,
37
+ showMillisec: false,
38
+ timeFormat: 'hh:mm:ss',
39
+ dateFormat: 'yy-mm-dd',
40
+ changeMonth: true,
41
+ changeYear: true
42
42
  });
43
- jQuery("li.date input").datepicker({
44
- dateFormat: 'yy-mm-dd',
45
- changeMonth: true,
46
- changeYear: true
43
+ jQuery("li.date input").datepicker({
44
+ dateFormat: 'yy-mm-dd',
45
+ changeMonth: true,
46
+ changeYear: true
47
47
  });
48
- jQuery("input[type='text'].date").datepicker({
49
- dateFormat: 'yy-mm-dd',
50
- changeMonth: true,
51
- changeYear: true
48
+ jQuery("input[type='text'].date").datepicker({
49
+ dateFormat: 'yy-mm-dd',
50
+ changeMonth: true,
51
+ changeYear: true
52
52
  });
53
- jQuery("input[type='text'].datepicker").datepicker({
54
- dateFormat: 'yy-mm-dd',
55
- changeMonth: true,
56
- changeYear: true
53
+ jQuery("input[type='text'].datepicker").datepicker({
54
+ dateFormat: 'yy-mm-dd',
55
+ changeMonth: true,
56
+ changeYear: true
57
57
  });
58
58
  jQuery("input[type='text'].time").timepicker({});
59
-
59
+
60
60
  jQuery('.surveyor_check_boxes input[type=text]').change(function(){
61
61
  var textValue = $(this).val()
62
62
  if (textValue.length > 0) {
63
63
  $(this).parent().children().has('input[type="checkbox"]')[0].children[0].checked = true;
64
64
  }
65
65
  });
66
-
66
+
67
67
  jQuery('.surveyor_radio input[type=text]').change(function(){
68
68
  var textValue = $(this).val()
69
69
  if (textValue.length > 0) {
70
- $(this).parent().children().has('input[type="radio"]')[0].children[0].checked = true;
70
+ $(this).parent().children().has('input[type="radio"]')[0].children[0].checked = true;
71
71
  }
72
72
  });
73
73
 
74
74
  jQuery("form#survey_form input, form#survey_form select, form#survey_form textarea").change(function(){
75
75
  var elements = [$('[type="submit"]').parent(), $('[name="' + this.name +'"]').closest('li')];
76
- blockElements(elements);
77
-
78
- question_data = $(this).parents('fieldset[id^="q_"],tr[id^="q_"]').find("input, select, textarea").add($("form#survey_form input[name='authenticity_token']")).serialize();
79
- // console.log(unescape(question_data));
80
- $.ajax({
81
- type: "PUT",
82
- url: $(this).parents('form#survey_form').attr("action"),
83
- data: question_data, dataType: 'json',
76
+
77
+ question_data = $(this).parents('fieldset[id^="q_"],tr[id^="q_"]').
78
+ find("input, select, textarea").
79
+ add($("form#survey_form input[name='authenticity_token']")).
80
+ serialize();
81
+ $.ajax({
82
+ type: "PUT",
83
+ url: $(this).parents('form#survey_form').attr("action"),
84
+ data: question_data, dataType: 'json',
84
85
  success: function(response) {
85
- unblockElements(elements);
86
86
  successfulSave(response);
87
- },
88
- error: function(xhr, ajaxOptions, thrownError) {
89
- unblockElements(elements);
90
87
  }
91
88
  });
92
89
  });
93
90
 
94
- // If javascript works, we don't need to show dependents from previous sections at the top of the page.
91
+ // http://www.filamentgroup.com/lab/update_jquery_ui_slider_from_a_select_element_now_with_aria_support/
92
+ $('fieldset.q_slider select').each(function(i,e) {
93
+ $(e).selectToUISlider({"labelSrc": "text"}).hide()
94
+ });
95
+
96
+ // If javascript works, we don't need to show dependents from
97
+ // previous sections at the top of the page.
95
98
  jQuery("#dependents").remove();
96
99
 
97
- function successfulSave(responseText){ // for(key in responseText) { console.log("key is "+[key]+", value is "+responseText[key]); }
98
- // surveyor_controller returns a json object to show/hide elements and insert/remove ids e.g. {"ids": {"2" => 234}, "remove": {"4" => 21}, "hide":["question_12","question_13"],"show":["question_14"]}
100
+ function successfulSave(responseText) {
101
+ // surveyor_controller returns a json object to show/hide elements
102
+ // e.g. {"hide":["question_12","question_13"],"show":["question_14"]}
99
103
  jQuery.each(responseText.show, function(){ showElement(this) });
100
104
  jQuery.each(responseText.hide, function(){ hideElement(this) });
101
- jQuery.each(responseText.ids, function(k,v){ jQuery('#r_'+k+'_question_id').after('<input id="r_'+k+'_id" type="hidden" value="'+v+'" name="r['+k+'][id]"/>'); });
102
- jQuery.each(responseText.remove, function(k,v){ jQuery('#r_'+k+'_id[value="'+v+'"]').remove(); });
103
105
  return false;
104
106
  }
105
-
107
+
106
108
  function showElement(id){
107
109
  group = id.match('^g_') ? true : false;
108
110
  if (group) {
@@ -111,7 +113,7 @@ jQuery(document).ready(function(){
111
113
  jQuery('#' + id).removeClass("q_hidden");
112
114
  }
113
115
  }
114
-
116
+
115
117
  function hideElement(id){
116
118
  group = id.match('^g_') ? true : false;
117
119
  if (group) {
@@ -120,26 +122,19 @@ jQuery(document).ready(function(){
120
122
  jQuery('#' + id).addClass("q_hidden");
121
123
  }
122
124
  }
123
-
124
- function blockElements(elements) {
125
- $.blockUI.defaults.overlayCSS.opacity = 0;
126
- $.blockUI.defaults.message = null;
127
- $.blockUI.defaults.fadeIn = 0;
128
- $.blockUI.defaults.fadeOut = 0;
129
- $.each(elements, function(){ $(this).block()});
130
- }
131
-
132
- function unblockElements(elements) {
133
- $.each(elements, function(){ $(this).unblock()});
134
- }
135
125
 
136
126
  // is_exclusive checkboxes should disble sibling checkboxes
137
- $('input.exclusive:checked').parents('fieldset[id^="q_"]').find(':checkbox').not(".exclusive").attr('checked', false).attr('disabled', true);
127
+ $('input.exclusive:checked').parents('fieldset[id^="q_"]').
128
+ find(':checkbox').
129
+ not(".exclusive").
130
+ attr('checked', false).
131
+ attr('disabled', true);
132
+
138
133
  $('input.exclusive:checkbox').click(function(){
139
134
  var e = $(this);
140
- var others = e.parents('fieldset[id^="q_"]').find(':checkbox').not(".exclusive");
135
+ var others = e.parents('fieldset[id^="q_"]').find(':checkbox').not(e);
141
136
  if(e.is(':checked')){
142
- others.attr('checked', false).attr('disabled', true);
137
+ others.attr('checked', false).attr('disabled', 'disabled');
143
138
  }else{
144
139
  others.attr('disabled', false);
145
140
  }
@@ -1,12 +1,12 @@
1
1
  /*
2
2
  * jQuery Tools 1.2.5 - The missing UI library for the Web
3
- *
3
+ *
4
4
  * [jquery, dateinput, rangeinput, validator]
5
- *
5
+ *
6
6
  * NO COPYRIGHTS OR LICENSES. DO WHAT YOU LIKE.
7
- *
7
+ *
8
8
  * http://flowplayer.org/tools/
9
- *
9
+ *
10
10
  * jQuery JavaScript Library v1.4.2
11
11
  * http://jquery.com/
12
12
  *
@@ -18,10 +18,10 @@
18
18
  * http://sizzlejs.com/
19
19
  * Copyright 2010, The Dojo Foundation
20
20
  * Released under the MIT, BSD, and GPL Licenses.
21
- *
21
+ *
22
22
  * -----
23
- *
24
-
23
+ *
24
+
25
25
 
26
26
  * File generated: Fri Dec 03 11:47:59 GMT 2010
27
27
  */
@@ -7,7 +7,7 @@
7
7
  font-size:18px;
8
8
  padding:4px;
9
9
  text-align:center;
10
- width:194px;
10
+ width:194px;
11
11
  -moz-box-shadow:0 0 10px #eee inset;
12
12
  }
13
13
  */
@@ -15,7 +15,7 @@
15
15
  #calroot {
16
16
  /* place on top of other elements. set a higher value if nessessary */
17
17
  z-index:9999;
18
-
18
+
19
19
  margin-top:-1px;
20
20
  width:198px;
21
21
  padding:2px;
@@ -25,19 +25,19 @@
25
25
  -moz-border-radius:5px;
26
26
  -webkit-border-radius:5px;
27
27
  -moz-box-shadow: 0 0 15px #666;
28
- -webkit-box-shadow: 0 0 15px #666;
28
+ -webkit-box-shadow: 0 0 15px #666;
29
29
  position: absolute;
30
30
  }
31
31
 
32
32
  /* head. contains title, prev/next month controls and possible month/year selectors */
33
- #calhead {
33
+ #calhead {
34
34
  padding:2px 0;
35
35
  height:22px;
36
- }
36
+ }
37
37
 
38
38
  #caltitle {
39
39
  font-size:14px;
40
- color:#0150D1;
40
+ color:#0150D1;
41
41
  float:left;
42
42
  text-align:center;
43
43
  width:155px;
@@ -60,12 +60,12 @@
60
60
  }
61
61
 
62
62
  #calprev.caldisabled, #calnext.caldisabled {
63
- visibility:hidden;
63
+ visibility:hidden;
64
64
  }
65
65
 
66
66
  /* year/month selector */
67
67
  #caltitle select {
68
- font-size:10px;
68
+ font-size:10px;
69
69
  }
70
70
 
71
71
  /* names of the days */
@@ -106,8 +106,8 @@
106
106
  line-height:20px;
107
107
  color:#666;
108
108
  -moz-border-radius:3px;
109
- -webkit-border-radius:3px;
110
- }
109
+ -webkit-border-radius:3px;
110
+ }
111
111
 
112
112
  /* different states */
113
113
  .calweek a:hover, .calfocus {
@@ -116,16 +116,16 @@
116
116
 
117
117
  /* sunday */
118
118
  a.calsun {
119
- color:red;
119
+ color:red;
120
120
  }
121
121
 
122
122
  /* offmonth day */
123
123
  a.caloff {
124
- color:#ccc;
124
+ color:#ccc;
125
125
  }
126
126
 
127
127
  a.caloff:hover {
128
- background-color:rgb(245, 245, 250);
128
+ background-color:rgb(245, 245, 250);
129
129
  }
130
130
 
131
131
 
@@ -59,26 +59,26 @@
59
59
  .ui-widget { font-family: Trebuchet MS, Tahoma, Verdana, Arial, sans-serif; font-size: 1.1em; }
60
60
  .ui-widget .ui-widget { font-size: 1em; }
61
61
  .ui-widget input, .ui-widget select, .ui-widget textarea, .ui-widget button { font-family: Trebuchet MS, Tahoma, Verdana, Arial, sans-serif; font-size: 1em; }
62
- .ui-widget-content { border: 1px solid #dddddd; background: #eeeeee url(ui-bg_highlight-soft_100_eeeeee_1x100.png) 50% top repeat-x; color: #333333; }
62
+ .ui-widget-content { border: 1px solid #dddddd; background: #eeeeee url(../../images/ui-bg_highlight-soft_100_eeeeee_1x100.png) 50% top repeat-x; color: #333333; }
63
63
  .ui-widget-content a { color: #333333; }
64
- .ui-widget-header { border: 1px solid #e78f08; background: #f6a828 url(ui-bg_gloss-wave_35_f6a828_500x100.png) 50% 50% repeat-x; color: #ffffff; font-weight: bold; }
64
+ .ui-widget-header { border: 1px solid #e78f08; background: #f6a828 url(../../images/ui-bg_gloss-wave_35_f6a828_500x100.png) 50% 50% repeat-x; color: #ffffff; font-weight: bold; }
65
65
  .ui-widget-header a { color: #ffffff; }
66
66
 
67
67
  /* Interaction states
68
68
  ----------------------------------*/
69
- .ui-state-default, .ui-widget-content .ui-state-default, .ui-widget-header .ui-state-default { border: 1px solid #cccccc; background: #f6f6f6 url(ui-bg_glass_100_f6f6f6_1x400.png) 50% 50% repeat-x; font-weight: bold; color: #1c94c4; }
69
+ .ui-state-default, .ui-widget-content .ui-state-default, .ui-widget-header .ui-state-default { border: 1px solid #cccccc; background: #f6f6f6 url(../../images/ui-bg_glass_100_f6f6f6_1x400.png) 50% 50% repeat-x; font-weight: bold; color: #1c94c4; }
70
70
  .ui-state-default a, .ui-state-default a:link, .ui-state-default a:visited { color: #1c94c4; text-decoration: none; }
71
- .ui-state-hover, .ui-widget-content .ui-state-hover, .ui-widget-header .ui-state-hover, .ui-state-focus, .ui-widget-content .ui-state-focus, .ui-widget-header .ui-state-focus { border: 1px solid #fbcb09; background: #fdf5ce url(ui-bg_glass_100_fdf5ce_1x400.png) 50% 50% repeat-x; font-weight: bold; color: #c77405; }
71
+ .ui-state-hover, .ui-widget-content .ui-state-hover, .ui-widget-header .ui-state-hover, .ui-state-focus, .ui-widget-content .ui-state-focus, .ui-widget-header .ui-state-focus { border: 1px solid #fbcb09; background: #fdf5ce url(../../images/ui-bg_glass_100_fdf5ce_1x400.png) 50% 50% repeat-x; font-weight: bold; color: #c77405; }
72
72
  .ui-state-hover a, .ui-state-hover a:hover { color: #c77405; text-decoration: none; }
73
- .ui-state-active, .ui-widget-content .ui-state-active, .ui-widget-header .ui-state-active { border: 1px solid #fbd850; background: #ffffff url(ui-bg_glass_65_ffffff_1x400.png) 50% 50% repeat-x; font-weight: bold; color: #eb8f00; }
73
+ .ui-state-active, .ui-widget-content .ui-state-active, .ui-widget-header .ui-state-active { border: 1px solid #fbd850; background: #ffffff url(../../images/ui-bg_glass_65_ffffff_1x400.png) 50% 50% repeat-x; font-weight: bold; color: #eb8f00; }
74
74
  .ui-state-active a, .ui-state-active a:link, .ui-state-active a:visited { color: #eb8f00; text-decoration: none; }
75
75
  .ui-widget :active { outline: none; }
76
76
 
77
77
  /* Interaction Cues
78
78
  ----------------------------------*/
79
- .ui-state-highlight, .ui-widget-content .ui-state-highlight, .ui-widget-header .ui-state-highlight {border: 1px solid #fed22f; background: #ffe45c url(ui-bg_highlight-soft_75_ffe45c_1x100.png) 50% top repeat-x; color: #363636; }
79
+ .ui-state-highlight, .ui-widget-content .ui-state-highlight, .ui-widget-header .ui-state-highlight {border: 1px solid #fed22f; background: #ffe45c url(../../images/ui-bg_highlight-soft_75_ffe45c_1x100.png) 50% top repeat-x; color: #363636; }
80
80
  .ui-state-highlight a, .ui-widget-content .ui-state-highlight a,.ui-widget-header .ui-state-highlight a { color: #363636; }
81
- .ui-state-error, .ui-widget-content .ui-state-error, .ui-widget-header .ui-state-error {border: 1px solid #cd0a0a; background: #b81900 url(ui-bg_diagonals-thick_18_b81900_40x40.png) 50% 50% repeat; color: #ffffff; }
81
+ .ui-state-error, .ui-widget-content .ui-state-error, .ui-widget-header .ui-state-error {border: 1px solid #cd0a0a; background: #b81900 url(../../images/ui-bg_diagonals-thick_18_b81900_40x40.png) 50% 50% repeat; color: #ffffff; }
82
82
  .ui-state-error a, .ui-widget-content .ui-state-error a, .ui-widget-header .ui-state-error a { color: #ffffff; }
83
83
  .ui-state-error-text, .ui-widget-content .ui-state-error-text, .ui-widget-header .ui-state-error-text { color: #ffffff; }
84
84
  .ui-priority-primary, .ui-widget-content .ui-priority-primary, .ui-widget-header .ui-priority-primary { font-weight: bold; }
@@ -89,14 +89,14 @@
89
89
  ----------------------------------*/
90
90
 
91
91
  /* states and images */
92
- .ui-icon { width: 16px; height: 16px; background-image: url(ui-icons_222222_256x240.png); }
93
- .ui-widget-content .ui-icon {background-image: url(ui-icons_222222_256x240.png); }
94
- .ui-widget-header .ui-icon {background-image: url(ui-icons_ffffff_256x240.png); }
95
- .ui-state-default .ui-icon { background-image: url(ui-icons_ef8c08_256x240.png); }
96
- .ui-state-hover .ui-icon, .ui-state-focus .ui-icon {background-image: url(ui-icons_ef8c08_256x240.png); }
97
- .ui-state-active .ui-icon {background-image: url(ui-icons_ef8c08_256x240.png); }
98
- .ui-state-highlight .ui-icon {background-image: url(ui-icons_228ef1_256x240.png); }
99
- .ui-state-error .ui-icon, .ui-state-error-text .ui-icon {background-image: url(ui-icons_ffd27a_256x240.png); }
92
+ .ui-icon { width: 16px; height: 16px; background-image: url(../../images/ui-icons_222222_256x240.png); }
93
+ .ui-widget-content .ui-icon {background-image: url(../../images/ui-icons_222222_256x240.png); }
94
+ .ui-widget-header .ui-icon {background-image: url(../../images/ui-icons_ffffff_256x240.png); }
95
+ .ui-state-default .ui-icon { background-image: url(../../images/ui-icons_ef8c08_256x240.png); }
96
+ .ui-state-hover .ui-icon, .ui-state-focus .ui-icon {background-image: url(../../images/ui-icons_ef8c08_256x240.png); }
97
+ .ui-state-active .ui-icon {background-image: url(../../images/ui-icons_ef8c08_256x240.png); }
98
+ .ui-state-highlight .ui-icon {background-image: url(../../images/ui-icons_228ef1_256x240.png); }
99
+ .ui-state-error .ui-icon, .ui-state-error-text .ui-icon {background-image: url(../../images/ui-icons_ffd27a_256x240.png); }
100
100
 
101
101
  /* positioning */
102
102
  .ui-icon-carat-1-n { background-position: 0 0; }
@@ -291,8 +291,8 @@
291
291
  .ui-corner-all { -moz-border-radius: 4px; -webkit-border-radius: 4px; border-radius: 4px; }
292
292
 
293
293
  /* Overlays */
294
- .ui-widget-overlay { background: #666666 url(ui-bg_diagonals-thick_20_666666_40x40.png) 50% 50% repeat; opacity: .50;filter:Alpha(Opacity=50); }
295
- .ui-widget-shadow { margin: -5px 0 0 -5px; padding: 5px; background: #000000 url(ui-bg_flat_10_000000_40x100.png) 50% 50% repeat-x; opacity: .20;filter:Alpha(Opacity=20); -moz-border-radius: 5px; -webkit-border-radius: 5px; border-radius: 5px; }/*
294
+ .ui-widget-overlay { background: #666666 url(../../images/ui-bg_diagonals-thick_20_666666_40x40.png) 50% 50% repeat; opacity: .50;filter:Alpha(Opacity=50); }
295
+ .ui-widget-shadow { margin: -5px 0 0 -5px; padding: 5px; background: #000000 url(../../images/ui-bg_flat_10_000000_40x100.png) 50% 50% repeat-x; opacity: .20;filter:Alpha(Opacity=20); -moz-border-radius: 5px; -webkit-border-radius: 5px; border-radius: 5px; }/*
296
296
  * jQuery UI Resizable 1.8.6
297
297
  *
298
298
  * Copyright 2010, AUTHORS.txt (http://jqueryui.com/about)
@@ -46,5 +46,5 @@ blockquote, q {
46
46
  }
47
47
  pre {
48
48
  background: #333333;
49
- color: #EFEFEF;
49
+ color: #EFEFEF;
50
50
  }