jakewendt-surveyor 0.11.3

Sign up to get free protection for your applications and to get access to all the features.
Files changed (160) hide show
  1. data/MIT-LICENSE +20 -0
  2. data/README.md +285 -0
  3. data/Rakefile +54 -0
  4. data/VERSION +1 -0
  5. data/app/controllers/surveyor_controller.rb +142 -0
  6. data/app/helpers/survey_form_builder.rb +37 -0
  7. data/app/helpers/surveyor_helper.rb +67 -0
  8. data/app/models/answer.rb +23 -0
  9. data/app/models/dependency.rb +50 -0
  10. data/app/models/dependency_condition.rb +47 -0
  11. data/app/models/question.rb +54 -0
  12. data/app/models/question_group.rb +33 -0
  13. data/app/models/response.rb +94 -0
  14. data/app/models/response_set.rb +316 -0
  15. data/app/models/survey.rb +172 -0
  16. data/app/models/survey_section.rb +18 -0
  17. data/app/models/validation.rb +38 -0
  18. data/app/models/validation_condition.rb +47 -0
  19. data/app/views/layouts/surveyor_default.html.erb +13 -0
  20. data/app/views/partials/_answer.html.haml +58 -0
  21. data/app/views/partials/_question.html.haml +80 -0
  22. data/app/views/partials/_question_group.html.haml +39 -0
  23. data/app/views/surveyor/edit.html.haml +38 -0
  24. data/app/views/surveyor/new.html.haml +16 -0
  25. data/app/views/surveyor/show.html.haml +12 -0
  26. data/config/routes.rb +11 -0
  27. data/features/step_definitions/surveyor_steps.rb +7 -0
  28. data/features/step_definitions/web_steps.rb +273 -0
  29. data/features/support/env.rb +57 -0
  30. data/features/support/paths.rb +25 -0
  31. data/features/surveyor.feature +11 -0
  32. data/generators/extend_surveyor/extend_surveyor_generator.rb +22 -0
  33. data/generators/extend_surveyor/templates/EXTENDING_SURVEYOR +17 -0
  34. data/generators/extend_surveyor/templates/extensions/survey_extensions.rb +24 -0
  35. data/generators/extend_surveyor/templates/extensions/surveyor_controller_extensions.rb +28 -0
  36. data/generators/extend_surveyor/templates/extensions/surveyor_custom.html.erb +13 -0
  37. data/generators/extend_surveyor/templates/extensions/surveyor_helper_extensions.rb +17 -0
  38. data/generators/surveyor/surveyor_generator.rb +67 -0
  39. data/generators/surveyor/templates/README +10 -0
  40. data/generators/surveyor/templates/assets/images/222222_11x11_icon_arrows_leftright.gif +0 -0
  41. data/generators/surveyor/templates/assets/images/222222_11x11_icon_arrows_updown.gif +0 -0
  42. data/generators/surveyor/templates/assets/images/222222_11x11_icon_close.gif +0 -0
  43. data/generators/surveyor/templates/assets/images/222222_11x11_icon_doc.gif +0 -0
  44. data/generators/surveyor/templates/assets/images/222222_11x11_icon_folder_closed.gif +0 -0
  45. data/generators/surveyor/templates/assets/images/222222_11x11_icon_folder_open.gif +0 -0
  46. data/generators/surveyor/templates/assets/images/222222_11x11_icon_minus.gif +0 -0
  47. data/generators/surveyor/templates/assets/images/222222_11x11_icon_plus.gif +0 -0
  48. data/generators/surveyor/templates/assets/images/222222_11x11_icon_resize_se.gif +0 -0
  49. data/generators/surveyor/templates/assets/images/222222_35x9_colorpicker_indicator.gif.gif +0 -0
  50. data/generators/surveyor/templates/assets/images/222222_7x7_arrow_down.gif +0 -0
  51. data/generators/surveyor/templates/assets/images/222222_7x7_arrow_left.gif +0 -0
  52. data/generators/surveyor/templates/assets/images/222222_7x7_arrow_right.gif +0 -0
  53. data/generators/surveyor/templates/assets/images/222222_7x7_arrow_up.gif +0 -0
  54. data/generators/surveyor/templates/assets/images/454545_11x11_icon_arrows_leftright.gif +0 -0
  55. data/generators/surveyor/templates/assets/images/454545_11x11_icon_arrows_updown.gif +0 -0
  56. data/generators/surveyor/templates/assets/images/454545_11x11_icon_close.gif +0 -0
  57. data/generators/surveyor/templates/assets/images/454545_11x11_icon_doc.gif +0 -0
  58. data/generators/surveyor/templates/assets/images/454545_11x11_icon_folder_closed.gif +0 -0
  59. data/generators/surveyor/templates/assets/images/454545_11x11_icon_folder_open.gif +0 -0
  60. data/generators/surveyor/templates/assets/images/454545_11x11_icon_minus.gif +0 -0
  61. data/generators/surveyor/templates/assets/images/454545_11x11_icon_plus.gif +0 -0
  62. data/generators/surveyor/templates/assets/images/454545_7x7_arrow_down.gif +0 -0
  63. data/generators/surveyor/templates/assets/images/454545_7x7_arrow_left.gif +0 -0
  64. data/generators/surveyor/templates/assets/images/454545_7x7_arrow_right.gif +0 -0
  65. data/generators/surveyor/templates/assets/images/454545_7x7_arrow_up.gif +0 -0
  66. data/generators/surveyor/templates/assets/images/888888_11x11_icon_arrows_leftright.gif +0 -0
  67. data/generators/surveyor/templates/assets/images/888888_11x11_icon_arrows_updown.gif +0 -0
  68. data/generators/surveyor/templates/assets/images/888888_11x11_icon_close.gif +0 -0
  69. data/generators/surveyor/templates/assets/images/888888_11x11_icon_doc.gif +0 -0
  70. data/generators/surveyor/templates/assets/images/888888_11x11_icon_folder_closed.gif +0 -0
  71. data/generators/surveyor/templates/assets/images/888888_11x11_icon_folder_open.gif +0 -0
  72. data/generators/surveyor/templates/assets/images/888888_11x11_icon_minus.gif +0 -0
  73. data/generators/surveyor/templates/assets/images/888888_11x11_icon_plus.gif +0 -0
  74. data/generators/surveyor/templates/assets/images/888888_7x7_arrow_down.gif +0 -0
  75. data/generators/surveyor/templates/assets/images/888888_7x7_arrow_left.gif +0 -0
  76. data/generators/surveyor/templates/assets/images/888888_7x7_arrow_right.gif +0 -0
  77. data/generators/surveyor/templates/assets/images/888888_7x7_arrow_up.gif +0 -0
  78. data/generators/surveyor/templates/assets/images/dadada_40x100_textures_02_glass_75.png +0 -0
  79. data/generators/surveyor/templates/assets/images/e6e6e6_40x100_textures_02_glass_75.png +0 -0
  80. data/generators/surveyor/templates/assets/images/ffffff_40x100_textures_01_flat_0.png +0 -0
  81. data/generators/surveyor/templates/assets/images/ffffff_40x100_textures_02_glass_65.png +0 -0
  82. data/generators/surveyor/templates/assets/javascripts/accessibleUISlider.jQuery.js +201 -0
  83. data/generators/surveyor/templates/assets/javascripts/jquery-1.2.6.js +3549 -0
  84. data/generators/surveyor/templates/assets/javascripts/jquery-ui-personalized-1.5.3.js +7616 -0
  85. data/generators/surveyor/templates/assets/javascripts/jquery.form.js +637 -0
  86. data/generators/surveyor/templates/assets/javascripts/surveyor.js +47 -0
  87. data/generators/surveyor/templates/assets/stylesheets/jquery-ui-slider-additions.css +71 -0
  88. data/generators/surveyor/templates/assets/stylesheets/reset.css +50 -0
  89. data/generators/surveyor/templates/assets/stylesheets/sass/surveyor.sass +243 -0
  90. data/generators/surveyor/templates/assets/stylesheets/surveyor.css +235 -0
  91. data/generators/surveyor/templates/assets/stylesheets/ui.theme.css +851 -0
  92. data/generators/surveyor/templates/initializers/haml.rb +8 -0
  93. data/generators/surveyor/templates/initializers/surveyor.rb +10 -0
  94. data/generators/surveyor/templates/migrate/add_correct_answer_id_to_questions.rb +9 -0
  95. data/generators/surveyor/templates/migrate/add_display_order_to_surveys.rb +9 -0
  96. data/generators/surveyor/templates/migrate/add_index_to_response_sets.rb +9 -0
  97. data/generators/surveyor/templates/migrate/add_index_to_surveys.rb +9 -0
  98. data/generators/surveyor/templates/migrate/add_manual_numbering.rb +11 -0
  99. data/generators/surveyor/templates/migrate/add_unique_indicies.rb +17 -0
  100. data/generators/surveyor/templates/migrate/create_answers.rb +37 -0
  101. data/generators/surveyor/templates/migrate/create_dependencies.rb +22 -0
  102. data/generators/surveyor/templates/migrate/create_dependency_conditions.rb +29 -0
  103. data/generators/surveyor/templates/migrate/create_question_groups.rb +27 -0
  104. data/generators/surveyor/templates/migrate/create_questions.rb +36 -0
  105. data/generators/surveyor/templates/migrate/create_response_sets.rb +22 -0
  106. data/generators/surveyor/templates/migrate/create_responses.rb +33 -0
  107. data/generators/surveyor/templates/migrate/create_survey_sections.rb +29 -0
  108. data/generators/surveyor/templates/migrate/create_surveys.rb +31 -0
  109. data/generators/surveyor/templates/migrate/create_validation_conditions.rb +32 -0
  110. data/generators/surveyor/templates/migrate/create_validations.rb +20 -0
  111. data/generators/surveyor/templates/surveys/kitchen_sink_survey.rb +218 -0
  112. data/generators/surveyor/templates/tasks/surveyor.rb +4 -0
  113. data/generators/test_surveyor/templates/TESTING_SURVEYOR +0 -0
  114. data/generators/test_surveyor/templates/environments/cucumber.rb +21 -0
  115. data/generators/test_surveyor/test_surveyor_generator.rb +15 -0
  116. data/jakewendt-surveyor.gemspec +212 -0
  117. data/lib/fixtures_extensions.rb +6 -0
  118. data/lib/jakewendt-surveyor.rb +1 -0
  119. data/lib/surveyor.rb +44 -0
  120. data/lib/surveyor/acts_as_response.rb +33 -0
  121. data/lib/surveyor/config.rb +45 -0
  122. data/lib/tasks/surveyor_tasks.rake +33 -0
  123. data/lib/xml_formatter.rb +12 -0
  124. data/rails/init.rb +1 -0
  125. data/script/surveyor/answer.rb +54 -0
  126. data/script/surveyor/base.rb +77 -0
  127. data/script/surveyor/dependency.rb +13 -0
  128. data/script/surveyor/dependency_condition.rb +40 -0
  129. data/script/surveyor/parser.rb +207 -0
  130. data/script/surveyor/question.rb +37 -0
  131. data/script/surveyor/question_group.rb +26 -0
  132. data/script/surveyor/specs/answer_spec.rb +29 -0
  133. data/script/surveyor/specs/question_spec.rb +63 -0
  134. data/script/surveyor/specs/spec_helper.rb +7 -0
  135. data/script/surveyor/specs/survey_section_spec.rb +23 -0
  136. data/script/surveyor/specs/validation_condition_spec.rb +20 -0
  137. data/script/surveyor/specs/validation_spec.rb +20 -0
  138. data/script/surveyor/survey.rb +35 -0
  139. data/script/surveyor/survey_section.rb +21 -0
  140. data/script/surveyor/validation.rb +21 -0
  141. data/script/surveyor/validation_condition.rb +21 -0
  142. data/script/surveyor/whr_dsl.tmproj +244 -0
  143. data/spec/controllers/surveyor_controller_spec.rb +193 -0
  144. data/spec/factories.rb +145 -0
  145. data/spec/lib/surveyor_spec.rb +44 -0
  146. data/spec/models/answer_spec.rb +29 -0
  147. data/spec/models/dependency_condition_spec.rb +321 -0
  148. data/spec/models/dependency_spec.rb +81 -0
  149. data/spec/models/question_group_spec.rb +35 -0
  150. data/spec/models/question_spec.rb +75 -0
  151. data/spec/models/response_set_spec.rb +245 -0
  152. data/spec/models/response_spec.rb +76 -0
  153. data/spec/models/survey_section_spec.rb +32 -0
  154. data/spec/models/survey_spec.rb +71 -0
  155. data/spec/models/validation_condition_spec.rb +105 -0
  156. data/spec/models/validation_spec.rb +59 -0
  157. data/spec/rcov.opts +2 -0
  158. data/spec/spec.opts +4 -0
  159. data/spec/spec_helper.rb +12 -0
  160. metadata +254 -0
@@ -0,0 +1,11 @@
1
+ Story: Logging in
2
+ As an anonymous user with an account
3
+ I want to log in to my account
4
+ So that I can be myself
5
+
6
+ #
7
+ # Log in: get form
8
+ #
9
+ Scenario: Anonymous user can get a login form.
10
+ Given I am a banana
11
+ Then I should be a banana
@@ -0,0 +1,22 @@
1
+ class ExtendSurveyorGenerator < Rails::Generator::Base
2
+ def manifest
3
+ record do |m|
4
+
5
+ # Copy README to your app
6
+ m.file "EXTENDING_SURVEYOR", "surveys/EXTENDING_SURVEYOR"
7
+
8
+ # Custom layout
9
+ m.file "extensions/surveyor_custom.html.erb", "app/views/layouts/surveyor_custom.html.erb"
10
+
11
+ # Model, helper, and controller extensions
12
+ # http://www.redmine.org/boards/3/topics/4095#message-4136
13
+ # http://blog.mattwynne.net/2009/07/11/rails-tip-use-polymorphism-to-extend-your-controllers-at-runtime/
14
+ m.file "extensions/survey_extensions.rb", "app/models/survey_extensions.rb"
15
+ m.file "extensions/surveyor_helper_extensions.rb", "app/helpers/surveyor_helper_extensions.rb"
16
+ m.file "extensions/surveyor_controller_extensions.rb", "app/controllers/surveyor_controller_extensions.rb"
17
+
18
+ m.readme "EXTENDING_SURVEYOR"
19
+
20
+ end
21
+ end
22
+ end
@@ -0,0 +1,17 @@
1
+
2
+ = Extending Surveyor =
3
+
4
+ * Any of surveyor model class_eval, class methods, and instance methods may be modified.
5
+ * SurveyorHelper class_eval and instance methods may be modified.
6
+ * SurveyorController class_eval, class methods, instance methods, and actions can be modified. Action methods should be specified separately in the Actions submodule.
7
+
8
+ Samples files have been generated at:
9
+
10
+ * app/models/survey_extensions.rb
11
+ * app/helpers/surveyor_helper_extensions.rb
12
+ * app/controllers/surveyor_controller_extensions.rb
13
+
14
+ To activate, add the config['extend'] array in config/initializers/surveyor.rb:
15
+
16
+ config['extend'] = %w(survey surveyor_helper surveyor_controller)
17
+
@@ -0,0 +1,24 @@
1
+ module SurveyExtensions
2
+ def self.included(base)
3
+ base.extend(ClassMethods)
4
+ base.send(:include, InstanceMethods)
5
+ base.class_eval do
6
+ # Same as typing in the class
7
+
8
+ end
9
+ end
10
+
11
+ module ClassMethods
12
+ end
13
+
14
+ module InstanceMethods
15
+ # def title
16
+ # foo
17
+ # end
18
+ # def foo
19
+ # "bar"
20
+ # end
21
+ end
22
+ end
23
+
24
+ # Add "survey" to config['extend'] array in config/initializers/surveyor.rb to activate these extensions
@@ -0,0 +1,28 @@
1
+ module SurveyorControllerExtensions
2
+ def self.included(base)
3
+ base.extend(ClassMethods)
4
+ base.send(:include, InstanceMethods)
5
+ base.class_eval do
6
+ # Same as typing in the class
7
+ # before_filter :pimp_my_ride
8
+ end
9
+ end
10
+
11
+ module ClassMethods
12
+ end
13
+
14
+ module InstanceMethods
15
+ # def pimp_my_ride
16
+ # flash[:notice] = "pimped!"
17
+ # end
18
+ end
19
+
20
+ module Actions
21
+ # Redefine the controller actions [index, new, create, show, update] here
22
+ # def new
23
+ # render :text =>"surveys are down"
24
+ # end
25
+ end
26
+ end
27
+
28
+ # Add "surveyor_controller" to config['extend'] array in config/initializers/surveyor.rb to activate these extensions
@@ -0,0 +1,13 @@
1
+ <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
2
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
3
+ <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
4
+ <head>
5
+ <meta http-equiv="content-type" content="text/html;charset=UTF-8" />
6
+ <title>Survey: <%= controller.action_name %></title>
7
+ <%= surveyor_includes %>
8
+ </head>
9
+ <body>
10
+ <div id="flash"><%= flash[:notice] %></div>
11
+ <%= yield %>
12
+ </body>
13
+ </html>
@@ -0,0 +1,17 @@
1
+ module SurveyorHelperExtensions
2
+ def self.included(base) # :nodoc:
3
+ base.send(:include, InstanceMethods)
4
+ base.class_eval do
5
+ # Same as typing in the module
6
+ # alias_method_chain :question_number_helper, :sauce
7
+ end
8
+ end
9
+
10
+ module InstanceMethods
11
+ # def question_number_helper_with_sauce(number)
12
+ # question_number_helper_without_sauce(number) + "Extra sauce"
13
+ # end
14
+ end
15
+ end
16
+
17
+ # Add "surveyor_helper" to config['extend'] array in config/initializers/surveyor.rb to activate these extensions
@@ -0,0 +1,67 @@
1
+ class SurveyorGenerator < Rails::Generator::Base
2
+ def manifest
3
+ record do |m|
4
+
5
+ m.directory "surveys"
6
+
7
+ # Copy README to your app
8
+ m.file "../../../README.md", "surveys/README.md"
9
+
10
+ # Gem plugin rake tasks
11
+ m.file "tasks/surveyor.rb", "lib/tasks/surveyor.rb"
12
+ if file_has_line(destination_path('Rakefile'), /^require 'tasks\/surveyor'$/ )
13
+ logger.skipped 'Rakefile'
14
+ else
15
+ File.open(destination_path('Rakefile'), 'ab') {|file| file.write("\nrequire 'tasks/surveyor'\n") }
16
+ # http://ggr.com/how-to-include-a-gems-rake-tasks-in-your-rails-app.html
17
+ logger.appended 'Rakefile'
18
+ end
19
+
20
+ # HAML
21
+ m.file "initializers/surveyor.rb", "config/initializers/surveyor.rb"
22
+ m.file "initializers/haml.rb", "config/initializers/haml.rb"
23
+
24
+ # Migrate
25
+ # not using m.migration_template because all migration timestamps end up the same, causing a collision when running rake db:migrate
26
+ # coped functionality from RAILS_GEM_PATH/lib/rails_generator/commands.rb
27
+ m.directory "db/migrate"
28
+ [ "create_surveys", "create_survey_sections", "create_questions", "create_question_groups", "create_answers",
29
+ "create_response_sets", "create_responses",
30
+ "create_dependencies", "create_dependency_conditions",
31
+ "create_validations", "create_validation_conditions",
32
+ "add_display_order_to_surveys", "add_correct_answer_id_to_questions",
33
+ "add_index_to_response_sets", "add_index_to_surveys",
34
+ "add_unique_indicies", "add_manual_numbering"
35
+ ].each_with_index do |model, i|
36
+ unless (prev_migrations = Dir.glob("db/migrate/[0-9]*_*.rb").grep(/[0-9]+_#{model}.rb$/)).empty?
37
+ prev_migration_timestamp = prev_migrations[0].match(/([0-9]+)_#{model}.rb$/)[1]
38
+ end
39
+ # raise "Another migration is already named #{model}" if not Dir.glob("db/migrate/[0-9]*_*.rb").grep(/[0-9]+_#{model}.rb$/).empty?
40
+ m.template("migrate/#{model}.rb", "db/migrate/#{(prev_migration_timestamp || Time.now.utc.strftime("%Y%m%d%H%M%S").to_i + i).to_s}_#{model}.rb")
41
+ end
42
+
43
+ # Generate CSS
44
+ css_root = File.join(File.dirname(__FILE__), "templates", "assets", "stylesheets")
45
+ `sass #{css_root}/sass/surveyor.sass #{css_root}/surveyor.css`
46
+
47
+ # Assets
48
+ ["images", "javascripts", "stylesheets"].each do |asset_type|
49
+ m.directory "public/#{asset_type}/surveyor"
50
+ Dir.glob(File.join(File.dirname(__FILE__), "templates", "assets", asset_type, "*.*")).map{|path| File.basename(path)}.each do |filename|
51
+ m.file "assets/#{asset_type}/#{filename}", "public/#{asset_type}/surveyor/#{filename}"
52
+ end
53
+ end
54
+
55
+ # Surveys
56
+ m.directory "surveys/fixtures"
57
+ m.file "surveys/kitchen_sink_survey.rb", "surveys/kitchen_sink_survey.rb"
58
+
59
+ m.readme "README"
60
+
61
+ end
62
+ end
63
+ def file_has_line(filename, rxp)
64
+ File.readlines(filename).each{ |line| return true if line =~ rxp }
65
+ false
66
+ end
67
+ end
@@ -0,0 +1,10 @@
1
+
2
+ Surveyor installed. Next, run the migrations:
3
+
4
+ rake db:migrate
5
+
6
+ Try out the "kitchen sink" survey:
7
+
8
+ rake surveyor FILE=surveys/kitchen_sink_survey.rb
9
+
10
+ Or see README.md for configuration and customization details
@@ -0,0 +1,201 @@
1
+ /*
2
+ * --------------------------------------------------------------------
3
+ * jQuery-Plugin - accessibleUISlider - 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/progressive_enhancement_convert_select_box_to_accessible_jquery_ui_slider
7
+ * demo page: http://www.filamentgroup.com/examples/slider/demo.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
+ * Version: 1.0, 08.12.08
15
+ * Changelog:
16
+ *
17
+ * --------------------------------------------------------------------
18
+ */
19
+
20
+
21
+
22
+ jQuery.fn.accessibleUISlider = function(settings){
23
+ var selects = jQuery(this);
24
+
25
+ //id attrs - selects need ids for this feature to work - links handles to original select menus
26
+ var elIds = (function(){
27
+ var tempArr = [];
28
+ selects.each(function(){
29
+ tempArr.push(jQuery(this).attr('id'));
30
+ });
31
+ return tempArr;
32
+ })();
33
+
34
+ //array of all option elements in select element
35
+ var options = (function(){
36
+ var opts = [];
37
+ selects.eq(0).find('option').each(function(i){
38
+ opts.push({
39
+ value: jQuery(this).attr('value'),
40
+ text: jQuery(this).text()
41
+ });
42
+ });
43
+ return opts;
44
+ })();
45
+
46
+ //presets by selected indexes
47
+ var presets = (function(){
48
+ var indexes = [];
49
+ selects.each(function(){
50
+ var thisIndex = jQuery(this).find('option:selected').get(0).index;
51
+ var thisPercentage = Math.round((thisIndex / (options.length-1)) *100);
52
+ indexes.push(thisPercentage);
53
+ });
54
+ return indexes;
55
+ })();
56
+
57
+ //set up slider options API
58
+ var sliderAPI = jQuery.extend({
59
+ labels: 3,
60
+ inject: true,
61
+ rangeOpacity: 0.7,
62
+ width: selects.parent().width(),
63
+ range: selects.length > 1,//boolean for whether it's a range or not
64
+ steps: options.length-1,
65
+ stepping: 0,
66
+ handles: function(){//set starting locations to selected index, if applicable
67
+ var tempArr = [];
68
+ selects.each(function(i){
69
+ tempArr[i] = {
70
+ start: presets[i],
71
+ min: 0,
72
+ max: 100,
73
+ id: 'handle_'+i
74
+ };
75
+ });
76
+ return tempArr;
77
+ }(),
78
+ change: function(e, ui) {//slide function
79
+ var that = jQuery(this);
80
+ var currValue = ui.value;
81
+ var currIndex = Math.round(currValue / 100 * (options.length-1));
82
+ var currValue = options[currIndex].value;
83
+ var currText = options[currIndex].text;
84
+ //handle feedback tooltip and aria attrs
85
+ var feedback = ui.handle.find('.ui-slider-tooltip');
86
+ feedback.html(currText).parent().attr('aria-valuetext', currValue).attr('aria-valuenow', currValue);
87
+ //control original select menu
88
+ var currSelect = jQuery('#'+ui.handle.attr('id').split('handle_')[1]);
89
+ currSelect.find('option').eq(currIndex).attr('selected', 'selected');
90
+ }
91
+ }, settings);
92
+
93
+ selects.change(function(){
94
+ var thisIndex = jQuery(this).find('option:selected').get(0).index;
95
+ var thisLeft = Math.ceil((thisIndex / (options.length-1))* 100);
96
+ var thisIndex = jQuery('#handle_'+ jQuery(this).attr('id')).parent().prev('a').size();
97
+ jQuery('#handle_'+ jQuery(this).attr('id')).parents('.ui-slider:eq(0)').slider("moveTo", thisLeft,thisIndex);
98
+ });
99
+
100
+ //opt groups if present
101
+ var groups = (function(){
102
+ if(selects.eq(0).find('optgroup').size()>0){
103
+ var groupedData = [];
104
+ selects.eq(0).find('optgroup').each(function(i){
105
+ groupedData[i] = {};
106
+ groupedData[i].label = jQuery(this).attr('label');
107
+ groupedData[i].options = [];
108
+ jQuery(this).find('option').each(function(){
109
+ groupedData[i].options.push({text: jQuery(this).text(), value: jQuery(this).attr('value')});
110
+ });
111
+ });
112
+ return groupedData;
113
+ }
114
+ else return false;
115
+ })();
116
+
117
+ //create slider component div
118
+ var sliderComponent = jQuery('<div class="sliderComponent"></div>');
119
+
120
+ //CREATE HANDLES
121
+ selects.each(function(i){
122
+ sliderComponent.append('<div id="handle_'+elIds[i]+'" tabindex="'+ i+1 +'" class="ui-slider-handle ui-default-state" role="slider" aria-valuemin="'+ sliderAPI.minValue +'" aria-valuemax="'+ sliderAPI.maxValue +'"><span class="ui-slider-tooltip ui-component-content"></span></div>');
123
+ });
124
+
125
+ //CREATE SCALE AND TICS
126
+ sliderComponent.width(sliderAPI.width);
127
+
128
+ //write dl if there are optgroups
129
+ if(groups) {
130
+ var scale = sliderComponent.append('<dl class="ui-slider-scale"></dl>').find('.ui-slider-scale:eq(0)');
131
+ jQuery(groups).each(function(){
132
+ scale.append('<dt><span>'+this.label+'</span></dt>');//class name becomes camelCased label
133
+ var groupOpts = this.options;
134
+ jQuery(this.options).each(function(i){
135
+ scale.append('<dd><span class="ui-slider-label">'+ groupOpts[i].text +'</span><span class="ui-slider-tic ui-component-content"></span></dd>');
136
+ });
137
+ });
138
+ }
139
+ //write ol
140
+ else {
141
+ var scale = sliderComponent.append('<ol class="ui-slider-scale"></ol>').find('.ui-slider-scale:eq(0)');
142
+ jQuery(options).each(function(){
143
+ scale.append('<li><span class="ui-slider-label">'+this.text+'</span><span class="ui-slider-tic ui-component-content"></span></li>');
144
+ });
145
+ }
146
+
147
+ //style the li's or dd's
148
+ sliderComponent.find('.ui-slider-scale li, .ui-slider-scale dd').each(function(i){
149
+ jQuery(this).css({
150
+ 'left': ((100 /( options.length-1))*i).toFixed(2) + '%'
151
+ });
152
+ });
153
+
154
+ //first and last classes, and right align the last li/dd
155
+ sliderComponent.find('.ui-slider-scale li:first, .ui-slider-scale dd:first').addClass('first');
156
+ sliderComponent.find('.ui-slider-scale li:last, .ui-slider-scale dd:last').addClass('last').each(function(){
157
+ jQuery(this).css({'right': 0, 'left':'auto'});
158
+ });
159
+
160
+ //show and hide labels depending on showLabels pref
161
+ //show the last one if there are more than 1 specified
162
+ if(sliderAPI.labels > 1) sliderComponent.find('.ui-slider-scale li:last span.ui-slider-label, .ui-slider-scale dd:last span.ui-slider-label').css('text-indent', 0).addClass('ui-slider-label-show');
163
+ //set increment
164
+ var increm = Math.round(options.length / sliderAPI.labels);
165
+ //show em based on inc
166
+ for(var j=0; j<options.length; j+=increm){
167
+ if((options.length - j) > increm){//don't show if it's too close to the end label
168
+ 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');
169
+ }
170
+ }
171
+
172
+ //style the dt's
173
+ sliderComponent.find('.ui-slider-scale dt').each(function(i){
174
+ var aPixel = ((3 / sliderAPI.width) * 100).toFixed(2);
175
+ jQuery(this).css({
176
+ 'left': ((100 /( groups.length))*i).toFixed(2) + '%',
177
+ 'width': (((sliderAPI.width / groups.length) / sliderAPI.width) * 100).toFixed(2)- aPixel +'%'
178
+ });
179
+ });
180
+
181
+ sliderAPI.markup = sliderComponent;
182
+
183
+ //port slider function to pass api in.
184
+ sliderAPI.markup.slider = function(settings){
185
+ var sliderAPI_port = jQuery.extend(sliderAPI, settings);
186
+ jQuery(this).slider(sliderAPI_port).find('.ui-slider-range').css('opacity', sliderAPI_port.rangeOpacity);
187
+ return this;
188
+ }
189
+
190
+ //if inject is true, inject slider after last select element and init, otherwise return api including markup
191
+ if(sliderAPI.inject){
192
+ sliderAPI.markup.insertAfter(jQuery(this).eq(this.length-1)).slider(sliderAPI).find('.ui-slider-range').css('opacity', sliderAPI.rangeOpacity);
193
+ return this;
194
+ }
195
+ else{
196
+ return sliderAPI;
197
+ }
198
+
199
+ }
200
+
201
+