yodel_admin 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (321) hide show
  1. data/.gitignore +6 -0
  2. data/Gemfile +4 -0
  3. data/Rakefile +1 -0
  4. data/lib/layouts/admin_list_record.html +94 -0
  5. data/lib/layouts/admin_login.html +131 -0
  6. data/lib/layouts/admin_page/admin_list_page.html +55 -0
  7. data/lib/layouts/admin_page/admin_settings_page.html +34 -0
  8. data/lib/layouts/admin_page/admin_tree_page.html +51 -0
  9. data/lib/layouts/admin_page.html +56 -0
  10. data/lib/layouts/admin_record_form.html +74 -0
  11. data/lib/migrations/01_admin_pages.rb +99 -0
  12. data/lib/migrations/02_admin_default_pages.rb +98 -0
  13. data/lib/models/admin_editor_page.rb +27 -0
  14. data/lib/models/admin_list_page.rb +121 -0
  15. data/lib/models/admin_root_page.rb +9 -0
  16. data/lib/models/admin_settings_page.rb +20 -0
  17. data/lib/models/admin_sync_page.rb +82 -0
  18. data/lib/models/admin_tree_page.rb +141 -0
  19. data/lib/public/admin/chosen/chosen-sprite.png +0 -0
  20. data/lib/public/admin/chosen/chosen.css +340 -0
  21. data/lib/public/admin/chosen/chosen.jquery.min.js +10 -0
  22. data/lib/public/admin/css/admin.css +1086 -0
  23. data/lib/public/admin/css/reset.css +48 -0
  24. data/lib/public/admin/css/smoothness/images/ui-bg_flat_0_aaaaaa_40x100.png +0 -0
  25. data/lib/public/admin/css/smoothness/images/ui-bg_flat_75_ffffff_40x100.png +0 -0
  26. data/lib/public/admin/css/smoothness/images/ui-bg_glass_55_fbf9ee_1x400.png +0 -0
  27. data/lib/public/admin/css/smoothness/images/ui-bg_glass_65_ffffff_1x400.png +0 -0
  28. data/lib/public/admin/css/smoothness/images/ui-bg_glass_75_dadada_1x400.png +0 -0
  29. data/lib/public/admin/css/smoothness/images/ui-bg_glass_75_e6e6e6_1x400.png +0 -0
  30. data/lib/public/admin/css/smoothness/images/ui-bg_glass_95_fef1ec_1x400.png +0 -0
  31. data/lib/public/admin/css/smoothness/images/ui-bg_highlight-soft_75_cccccc_1x100.png +0 -0
  32. data/lib/public/admin/css/smoothness/images/ui-icons_222222_256x240.png +0 -0
  33. data/lib/public/admin/css/smoothness/images/ui-icons_2e83ff_256x240.png +0 -0
  34. data/lib/public/admin/css/smoothness/images/ui-icons_454545_256x240.png +0 -0
  35. data/lib/public/admin/css/smoothness/images/ui-icons_888888_256x240.png +0 -0
  36. data/lib/public/admin/css/smoothness/images/ui-icons_cd0a0a_256x240.png +0 -0
  37. data/lib/public/admin/css/smoothness/jquery-ui-1.8.16.custom.css +380 -0
  38. data/lib/public/admin/images/add.png +0 -0
  39. data/lib/public/admin/images/clock.png +0 -0
  40. data/lib/public/admin/images/close.png +0 -0
  41. data/lib/public/admin/images/cross.png +0 -0
  42. data/lib/public/admin/images/default_icon.png +0 -0
  43. data/lib/public/admin/images/delete.png +0 -0
  44. data/lib/public/admin/images/deploy_spinner.gif +0 -0
  45. data/lib/public/admin/images/drag.png +0 -0
  46. data/lib/public/admin/images/group_icon.png +0 -0
  47. data/lib/public/admin/images/left_arrow.png +0 -0
  48. data/lib/public/admin/images/load_spinner.gif +0 -0
  49. data/lib/public/admin/images/load_spinner_selected.gif +0 -0
  50. data/lib/public/admin/images/missing_image.png +0 -0
  51. data/lib/public/admin/images/new.png +0 -0
  52. data/lib/public/admin/images/open.png +0 -0
  53. data/lib/public/admin/images/right_arrow.png +0 -0
  54. data/lib/public/admin/images/save_spinner.gif +0 -0
  55. data/lib/public/admin/images/search.png +0 -0
  56. data/lib/public/admin/images/tick.png +0 -0
  57. data/lib/public/admin/images/user_icon.png +0 -0
  58. data/lib/public/admin/images/yodel.png +0 -0
  59. data/lib/public/admin/js/admin.js +1030 -0
  60. data/lib/public/admin/js/jquery-ui-1.8.16.custom.min.js +227 -0
  61. data/lib/public/admin/js/jquery.min.js +18 -0
  62. data/lib/public/admin/js/jquery.tablesorter.min.js +4 -0
  63. data/lib/public/admin/js/json2.js +480 -0
  64. data/lib/public/admin/js/yodel_jquery.js +241 -0
  65. data/lib/public/admin/tiny_mce/jquery.tinymce.js +338 -0
  66. data/lib/public/admin/tiny_mce/langs/en.js +223 -0
  67. data/lib/public/admin/tiny_mce/license.txt +504 -0
  68. data/lib/public/admin/tiny_mce/plugins/advhr/css/advhr.css +5 -0
  69. data/lib/public/admin/tiny_mce/plugins/advhr/editor_plugin.js +1 -0
  70. data/lib/public/admin/tiny_mce/plugins/advhr/editor_plugin_src.js +57 -0
  71. data/lib/public/admin/tiny_mce/plugins/advhr/js/rule.js +43 -0
  72. data/lib/public/admin/tiny_mce/plugins/advhr/langs/en_dlg.js +7 -0
  73. data/lib/public/admin/tiny_mce/plugins/advhr/rule.htm +58 -0
  74. data/lib/public/admin/tiny_mce/plugins/advimage/css/advimage.css +13 -0
  75. data/lib/public/admin/tiny_mce/plugins/advimage/editor_plugin.js +1 -0
  76. data/lib/public/admin/tiny_mce/plugins/advimage/editor_plugin_src.js +50 -0
  77. data/lib/public/admin/tiny_mce/plugins/advimage/image.htm +235 -0
  78. data/lib/public/admin/tiny_mce/plugins/advimage/img/sample.gif +0 -0
  79. data/lib/public/admin/tiny_mce/plugins/advimage/js/image.js +458 -0
  80. data/lib/public/admin/tiny_mce/plugins/advimage/langs/en_dlg.js +45 -0
  81. data/lib/public/admin/tiny_mce/plugins/advlink/css/advlink.css +8 -0
  82. data/lib/public/admin/tiny_mce/plugins/advlink/editor_plugin.js +1 -0
  83. data/lib/public/admin/tiny_mce/plugins/advlink/editor_plugin_src.js +61 -0
  84. data/lib/public/admin/tiny_mce/plugins/advlink/js/advlink.js +532 -0
  85. data/lib/public/admin/tiny_mce/plugins/advlink/langs/en_dlg.js +54 -0
  86. data/lib/public/admin/tiny_mce/plugins/advlink/link.htm +338 -0
  87. data/lib/public/admin/tiny_mce/plugins/advlist/editor_plugin.js +1 -0
  88. data/lib/public/admin/tiny_mce/plugins/advlist/editor_plugin_src.js +176 -0
  89. data/lib/public/admin/tiny_mce/plugins/autolink/editor_plugin.js +1 -0
  90. data/lib/public/admin/tiny_mce/plugins/autolink/editor_plugin_src.js +172 -0
  91. data/lib/public/admin/tiny_mce/plugins/autoresize/editor_plugin.js +1 -0
  92. data/lib/public/admin/tiny_mce/plugins/autoresize/editor_plugin_src.js +137 -0
  93. data/lib/public/admin/tiny_mce/plugins/autosave/editor_plugin.js +1 -0
  94. data/lib/public/admin/tiny_mce/plugins/autosave/editor_plugin_src.js +431 -0
  95. data/lib/public/admin/tiny_mce/plugins/autosave/langs/en.js +4 -0
  96. data/lib/public/admin/tiny_mce/plugins/bbcode/editor_plugin.js +1 -0
  97. data/lib/public/admin/tiny_mce/plugins/bbcode/editor_plugin_src.js +120 -0
  98. data/lib/public/admin/tiny_mce/plugins/contextmenu/editor_plugin.js +1 -0
  99. data/lib/public/admin/tiny_mce/plugins/contextmenu/editor_plugin_src.js +160 -0
  100. data/lib/public/admin/tiny_mce/plugins/directionality/editor_plugin.js +1 -0
  101. data/lib/public/admin/tiny_mce/plugins/directionality/editor_plugin_src.js +82 -0
  102. data/lib/public/admin/tiny_mce/plugins/emotions/editor_plugin.js +1 -0
  103. data/lib/public/admin/tiny_mce/plugins/emotions/editor_plugin_src.js +43 -0
  104. data/lib/public/admin/tiny_mce/plugins/emotions/emotions.htm +41 -0
  105. data/lib/public/admin/tiny_mce/plugins/emotions/img/smiley-cool.gif +0 -0
  106. data/lib/public/admin/tiny_mce/plugins/emotions/img/smiley-cry.gif +0 -0
  107. data/lib/public/admin/tiny_mce/plugins/emotions/img/smiley-embarassed.gif +0 -0
  108. data/lib/public/admin/tiny_mce/plugins/emotions/img/smiley-foot-in-mouth.gif +0 -0
  109. data/lib/public/admin/tiny_mce/plugins/emotions/img/smiley-frown.gif +0 -0
  110. data/lib/public/admin/tiny_mce/plugins/emotions/img/smiley-innocent.gif +0 -0
  111. data/lib/public/admin/tiny_mce/plugins/emotions/img/smiley-kiss.gif +0 -0
  112. data/lib/public/admin/tiny_mce/plugins/emotions/img/smiley-laughing.gif +0 -0
  113. data/lib/public/admin/tiny_mce/plugins/emotions/img/smiley-money-mouth.gif +0 -0
  114. data/lib/public/admin/tiny_mce/plugins/emotions/img/smiley-sealed.gif +0 -0
  115. data/lib/public/admin/tiny_mce/plugins/emotions/img/smiley-smile.gif +0 -0
  116. data/lib/public/admin/tiny_mce/plugins/emotions/img/smiley-surprised.gif +0 -0
  117. data/lib/public/admin/tiny_mce/plugins/emotions/img/smiley-tongue-out.gif +0 -0
  118. data/lib/public/admin/tiny_mce/plugins/emotions/img/smiley-undecided.gif +0 -0
  119. data/lib/public/admin/tiny_mce/plugins/emotions/img/smiley-wink.gif +0 -0
  120. data/lib/public/admin/tiny_mce/plugins/emotions/img/smiley-yell.gif +0 -0
  121. data/lib/public/admin/tiny_mce/plugins/emotions/js/emotions.js +22 -0
  122. data/lib/public/admin/tiny_mce/plugins/emotions/langs/en_dlg.js +20 -0
  123. data/lib/public/admin/tiny_mce/plugins/example/dialog.htm +22 -0
  124. data/lib/public/admin/tiny_mce/plugins/example/editor_plugin.js +1 -0
  125. data/lib/public/admin/tiny_mce/plugins/example/editor_plugin_src.js +84 -0
  126. data/lib/public/admin/tiny_mce/plugins/example/img/example.gif +0 -0
  127. data/lib/public/admin/tiny_mce/plugins/example/js/dialog.js +19 -0
  128. data/lib/public/admin/tiny_mce/plugins/example/langs/en.js +3 -0
  129. data/lib/public/admin/tiny_mce/plugins/example/langs/en_dlg.js +3 -0
  130. data/lib/public/admin/tiny_mce/plugins/example_dependency/editor_plugin.js +1 -0
  131. data/lib/public/admin/tiny_mce/plugins/example_dependency/editor_plugin_src.js +50 -0
  132. data/lib/public/admin/tiny_mce/plugins/fullpage/css/fullpage.css +143 -0
  133. data/lib/public/admin/tiny_mce/plugins/fullpage/editor_plugin.js +1 -0
  134. data/lib/public/admin/tiny_mce/plugins/fullpage/editor_plugin_src.js +399 -0
  135. data/lib/public/admin/tiny_mce/plugins/fullpage/fullpage.htm +259 -0
  136. data/lib/public/admin/tiny_mce/plugins/fullpage/js/fullpage.js +232 -0
  137. data/lib/public/admin/tiny_mce/plugins/fullpage/langs/en_dlg.js +85 -0
  138. data/lib/public/admin/tiny_mce/plugins/fullscreen/editor_plugin.js +1 -0
  139. data/lib/public/admin/tiny_mce/plugins/fullscreen/editor_plugin_src.js +159 -0
  140. data/lib/public/admin/tiny_mce/plugins/fullscreen/fullscreen.htm +109 -0
  141. data/lib/public/admin/tiny_mce/plugins/iespell/editor_plugin.js +1 -0
  142. data/lib/public/admin/tiny_mce/plugins/iespell/editor_plugin_src.js +54 -0
  143. data/lib/public/admin/tiny_mce/plugins/inlinepopups/editor_plugin.js +1 -0
  144. data/lib/public/admin/tiny_mce/plugins/inlinepopups/editor_plugin_src.js +699 -0
  145. data/lib/public/admin/tiny_mce/plugins/inlinepopups/skins/clearlooks2/img/alert.gif +0 -0
  146. data/lib/public/admin/tiny_mce/plugins/inlinepopups/skins/clearlooks2/img/button.gif +0 -0
  147. data/lib/public/admin/tiny_mce/plugins/inlinepopups/skins/clearlooks2/img/buttons.gif +0 -0
  148. data/lib/public/admin/tiny_mce/plugins/inlinepopups/skins/clearlooks2/img/confirm.gif +0 -0
  149. data/lib/public/admin/tiny_mce/plugins/inlinepopups/skins/clearlooks2/img/corners.gif +0 -0
  150. data/lib/public/admin/tiny_mce/plugins/inlinepopups/skins/clearlooks2/img/horizontal.gif +0 -0
  151. data/lib/public/admin/tiny_mce/plugins/inlinepopups/skins/clearlooks2/img/vertical.gif +0 -0
  152. data/lib/public/admin/tiny_mce/plugins/inlinepopups/skins/clearlooks2/window.css +90 -0
  153. data/lib/public/admin/tiny_mce/plugins/inlinepopups/template.htm +387 -0
  154. data/lib/public/admin/tiny_mce/plugins/insertdatetime/editor_plugin.js +1 -0
  155. data/lib/public/admin/tiny_mce/plugins/insertdatetime/editor_plugin_src.js +83 -0
  156. data/lib/public/admin/tiny_mce/plugins/layer/editor_plugin.js +1 -0
  157. data/lib/public/admin/tiny_mce/plugins/layer/editor_plugin_src.js +214 -0
  158. data/lib/public/admin/tiny_mce/plugins/legacyoutput/editor_plugin.js +1 -0
  159. data/lib/public/admin/tiny_mce/plugins/legacyoutput/editor_plugin_src.js +139 -0
  160. data/lib/public/admin/tiny_mce/plugins/lists/editor_plugin.js +1 -0
  161. data/lib/public/admin/tiny_mce/plugins/lists/editor_plugin_src.js +769 -0
  162. data/lib/public/admin/tiny_mce/plugins/media/css/media.css +17 -0
  163. data/lib/public/admin/tiny_mce/plugins/media/editor_plugin.js +1 -0
  164. data/lib/public/admin/tiny_mce/plugins/media/editor_plugin_src.js +822 -0
  165. data/lib/public/admin/tiny_mce/plugins/media/js/embed.js +73 -0
  166. data/lib/public/admin/tiny_mce/plugins/media/js/media.js +389 -0
  167. data/lib/public/admin/tiny_mce/plugins/media/langs/en_dlg.js +112 -0
  168. data/lib/public/admin/tiny_mce/plugins/media/media.htm +897 -0
  169. data/lib/public/admin/tiny_mce/plugins/media/moxieplayer.swf +0 -0
  170. data/lib/public/admin/tiny_mce/plugins/nonbreaking/editor_plugin.js +1 -0
  171. data/lib/public/admin/tiny_mce/plugins/nonbreaking/editor_plugin_src.js +53 -0
  172. data/lib/public/admin/tiny_mce/plugins/noneditable/editor_plugin.js +1 -0
  173. data/lib/public/admin/tiny_mce/plugins/noneditable/editor_plugin_src.js +95 -0
  174. data/lib/public/admin/tiny_mce/plugins/pagebreak/editor_plugin.js +1 -0
  175. data/lib/public/admin/tiny_mce/plugins/pagebreak/editor_plugin_src.js +74 -0
  176. data/lib/public/admin/tiny_mce/plugins/paste/editor_plugin.js +1 -0
  177. data/lib/public/admin/tiny_mce/plugins/paste/editor_plugin_src.js +942 -0
  178. data/lib/public/admin/tiny_mce/plugins/paste/js/pastetext.js +36 -0
  179. data/lib/public/admin/tiny_mce/plugins/paste/js/pasteword.js +51 -0
  180. data/lib/public/admin/tiny_mce/plugins/paste/langs/en_dlg.js +5 -0
  181. data/lib/public/admin/tiny_mce/plugins/paste/pastetext.htm +27 -0
  182. data/lib/public/admin/tiny_mce/plugins/paste/pasteword.htm +21 -0
  183. data/lib/public/admin/tiny_mce/plugins/preview/editor_plugin.js +1 -0
  184. data/lib/public/admin/tiny_mce/plugins/preview/editor_plugin_src.js +53 -0
  185. data/lib/public/admin/tiny_mce/plugins/preview/example.html +28 -0
  186. data/lib/public/admin/tiny_mce/plugins/preview/jscripts/embed.js +73 -0
  187. data/lib/public/admin/tiny_mce/plugins/preview/preview.html +17 -0
  188. data/lib/public/admin/tiny_mce/plugins/print/editor_plugin.js +1 -0
  189. data/lib/public/admin/tiny_mce/plugins/print/editor_plugin_src.js +34 -0
  190. data/lib/public/admin/tiny_mce/plugins/save/editor_plugin.js +1 -0
  191. data/lib/public/admin/tiny_mce/plugins/save/editor_plugin_src.js +101 -0
  192. data/lib/public/admin/tiny_mce/plugins/searchreplace/css/searchreplace.css +6 -0
  193. data/lib/public/admin/tiny_mce/plugins/searchreplace/editor_plugin.js +1 -0
  194. data/lib/public/admin/tiny_mce/plugins/searchreplace/editor_plugin_src.js +61 -0
  195. data/lib/public/admin/tiny_mce/plugins/searchreplace/js/searchreplace.js +142 -0
  196. data/lib/public/admin/tiny_mce/plugins/searchreplace/langs/en_dlg.js +16 -0
  197. data/lib/public/admin/tiny_mce/plugins/searchreplace/searchreplace.htm +100 -0
  198. data/lib/public/admin/tiny_mce/plugins/spellchecker/css/content.css +1 -0
  199. data/lib/public/admin/tiny_mce/plugins/spellchecker/editor_plugin.js +1 -0
  200. data/lib/public/admin/tiny_mce/plugins/spellchecker/editor_plugin_src.js +434 -0
  201. data/lib/public/admin/tiny_mce/plugins/spellchecker/img/wline.gif +0 -0
  202. data/lib/public/admin/tiny_mce/plugins/style/css/props.css +13 -0
  203. data/lib/public/admin/tiny_mce/plugins/style/editor_plugin.js +1 -0
  204. data/lib/public/admin/tiny_mce/plugins/style/editor_plugin_src.js +55 -0
  205. data/lib/public/admin/tiny_mce/plugins/style/js/props.js +635 -0
  206. data/lib/public/admin/tiny_mce/plugins/style/langs/en_dlg.js +70 -0
  207. data/lib/public/admin/tiny_mce/plugins/style/props.htm +840 -0
  208. data/lib/public/admin/tiny_mce/plugins/tabfocus/editor_plugin.js +1 -0
  209. data/lib/public/admin/tiny_mce/plugins/tabfocus/editor_plugin_src.js +122 -0
  210. data/lib/public/admin/tiny_mce/plugins/table/cell.htm +180 -0
  211. data/lib/public/admin/tiny_mce/plugins/table/css/cell.css +17 -0
  212. data/lib/public/admin/tiny_mce/plugins/table/css/row.css +25 -0
  213. data/lib/public/admin/tiny_mce/plugins/table/css/table.css +13 -0
  214. data/lib/public/admin/tiny_mce/plugins/table/editor_plugin.js +1 -0
  215. data/lib/public/admin/tiny_mce/plugins/table/editor_plugin_src.js +1363 -0
  216. data/lib/public/admin/tiny_mce/plugins/table/js/cell.js +319 -0
  217. data/lib/public/admin/tiny_mce/plugins/table/js/merge_cells.js +27 -0
  218. data/lib/public/admin/tiny_mce/plugins/table/js/row.js +237 -0
  219. data/lib/public/admin/tiny_mce/plugins/table/js/table.js +450 -0
  220. data/lib/public/admin/tiny_mce/plugins/table/langs/en_dlg.js +75 -0
  221. data/lib/public/admin/tiny_mce/plugins/table/merge_cells.htm +32 -0
  222. data/lib/public/admin/tiny_mce/plugins/table/row.htm +158 -0
  223. data/lib/public/admin/tiny_mce/plugins/table/table.htm +188 -0
  224. data/lib/public/admin/tiny_mce/plugins/template/blank.htm +12 -0
  225. data/lib/public/admin/tiny_mce/plugins/template/css/template.css +23 -0
  226. data/lib/public/admin/tiny_mce/plugins/template/editor_plugin.js +1 -0
  227. data/lib/public/admin/tiny_mce/plugins/template/editor_plugin_src.js +159 -0
  228. data/lib/public/admin/tiny_mce/plugins/template/js/template.js +106 -0
  229. data/lib/public/admin/tiny_mce/plugins/template/langs/en_dlg.js +15 -0
  230. data/lib/public/admin/tiny_mce/plugins/template/template.htm +31 -0
  231. data/lib/public/admin/tiny_mce/plugins/visualchars/editor_plugin.js +1 -0
  232. data/lib/public/admin/tiny_mce/plugins/visualchars/editor_plugin_src.js +83 -0
  233. data/lib/public/admin/tiny_mce/plugins/wordcount/editor_plugin.js +1 -0
  234. data/lib/public/admin/tiny_mce/plugins/wordcount/editor_plugin_src.js +114 -0
  235. data/lib/public/admin/tiny_mce/plugins/xhtmlxtras/abbr.htm +142 -0
  236. data/lib/public/admin/tiny_mce/plugins/xhtmlxtras/acronym.htm +142 -0
  237. data/lib/public/admin/tiny_mce/plugins/xhtmlxtras/attributes.htm +149 -0
  238. data/lib/public/admin/tiny_mce/plugins/xhtmlxtras/cite.htm +142 -0
  239. data/lib/public/admin/tiny_mce/plugins/xhtmlxtras/css/attributes.css +11 -0
  240. data/lib/public/admin/tiny_mce/plugins/xhtmlxtras/css/popup.css +9 -0
  241. data/lib/public/admin/tiny_mce/plugins/xhtmlxtras/del.htm +162 -0
  242. data/lib/public/admin/tiny_mce/plugins/xhtmlxtras/editor_plugin.js +1 -0
  243. data/lib/public/admin/tiny_mce/plugins/xhtmlxtras/editor_plugin_src.js +132 -0
  244. data/lib/public/admin/tiny_mce/plugins/xhtmlxtras/ins.htm +162 -0
  245. data/lib/public/admin/tiny_mce/plugins/xhtmlxtras/js/abbr.js +28 -0
  246. data/lib/public/admin/tiny_mce/plugins/xhtmlxtras/js/acronym.js +28 -0
  247. data/lib/public/admin/tiny_mce/plugins/xhtmlxtras/js/attributes.js +111 -0
  248. data/lib/public/admin/tiny_mce/plugins/xhtmlxtras/js/cite.js +28 -0
  249. data/lib/public/admin/tiny_mce/plugins/xhtmlxtras/js/del.js +53 -0
  250. data/lib/public/admin/tiny_mce/plugins/xhtmlxtras/js/element_common.js +229 -0
  251. data/lib/public/admin/tiny_mce/plugins/xhtmlxtras/js/ins.js +53 -0
  252. data/lib/public/admin/tiny_mce/plugins/xhtmlxtras/langs/en_dlg.js +32 -0
  253. data/lib/public/admin/tiny_mce/themes/advanced/about.htm +52 -0
  254. data/lib/public/admin/tiny_mce/themes/advanced/anchor.htm +26 -0
  255. data/lib/public/admin/tiny_mce/themes/advanced/charmap.htm +51 -0
  256. data/lib/public/admin/tiny_mce/themes/advanced/color_picker.htm +74 -0
  257. data/lib/public/admin/tiny_mce/themes/advanced/editor_template.js +1 -0
  258. data/lib/public/admin/tiny_mce/themes/advanced/editor_template_src.js +1358 -0
  259. data/lib/public/admin/tiny_mce/themes/advanced/image.htm +80 -0
  260. data/lib/public/admin/tiny_mce/themes/advanced/img/colorpicker.jpg +0 -0
  261. data/lib/public/admin/tiny_mce/themes/advanced/img/flash.gif +0 -0
  262. data/lib/public/admin/tiny_mce/themes/advanced/img/icons.gif +0 -0
  263. data/lib/public/admin/tiny_mce/themes/advanced/img/iframe.gif +0 -0
  264. data/lib/public/admin/tiny_mce/themes/advanced/img/pagebreak.gif +0 -0
  265. data/lib/public/admin/tiny_mce/themes/advanced/img/quicktime.gif +0 -0
  266. data/lib/public/admin/tiny_mce/themes/advanced/img/realmedia.gif +0 -0
  267. data/lib/public/admin/tiny_mce/themes/advanced/img/shockwave.gif +0 -0
  268. data/lib/public/admin/tiny_mce/themes/advanced/img/trans.gif +0 -0
  269. data/lib/public/admin/tiny_mce/themes/advanced/img/video.gif +0 -0
  270. data/lib/public/admin/tiny_mce/themes/advanced/img/windowsmedia.gif +0 -0
  271. data/lib/public/admin/tiny_mce/themes/advanced/js/about.js +73 -0
  272. data/lib/public/admin/tiny_mce/themes/advanced/js/anchor.js +42 -0
  273. data/lib/public/admin/tiny_mce/themes/advanced/js/charmap.js +355 -0
  274. data/lib/public/admin/tiny_mce/themes/advanced/js/color_picker.js +329 -0
  275. data/lib/public/admin/tiny_mce/themes/advanced/js/image.js +247 -0
  276. data/lib/public/admin/tiny_mce/themes/advanced/js/link.js +153 -0
  277. data/lib/public/admin/tiny_mce/themes/advanced/js/source_editor.js +56 -0
  278. data/lib/public/admin/tiny_mce/themes/advanced/langs/en.js +68 -0
  279. data/lib/public/admin/tiny_mce/themes/advanced/langs/en_dlg.js +54 -0
  280. data/lib/public/admin/tiny_mce/themes/advanced/link.htm +57 -0
  281. data/lib/public/admin/tiny_mce/themes/advanced/shortcuts.htm +47 -0
  282. data/lib/public/admin/tiny_mce/themes/advanced/skins/default/content.css +48 -0
  283. data/lib/public/admin/tiny_mce/themes/advanced/skins/default/dialog.css +117 -0
  284. data/lib/public/admin/tiny_mce/themes/advanced/skins/default/img/buttons.png +0 -0
  285. data/lib/public/admin/tiny_mce/themes/advanced/skins/default/img/items.gif +0 -0
  286. data/lib/public/admin/tiny_mce/themes/advanced/skins/default/img/menu_arrow.gif +0 -0
  287. data/lib/public/admin/tiny_mce/themes/advanced/skins/default/img/menu_check.gif +0 -0
  288. data/lib/public/admin/tiny_mce/themes/advanced/skins/default/img/progress.gif +0 -0
  289. data/lib/public/admin/tiny_mce/themes/advanced/skins/default/img/tabs.gif +0 -0
  290. data/lib/public/admin/tiny_mce/themes/advanced/skins/default/ui.css +214 -0
  291. data/lib/public/admin/tiny_mce/themes/advanced/skins/highcontrast/content.css +23 -0
  292. data/lib/public/admin/tiny_mce/themes/advanced/skins/highcontrast/dialog.css +105 -0
  293. data/lib/public/admin/tiny_mce/themes/advanced/skins/highcontrast/ui.css +102 -0
  294. data/lib/public/admin/tiny_mce/themes/advanced/skins/o2k7/content.css +47 -0
  295. data/lib/public/admin/tiny_mce/themes/advanced/skins/o2k7/dialog.css +117 -0
  296. data/lib/public/admin/tiny_mce/themes/advanced/skins/o2k7/img/button_bg.png +0 -0
  297. data/lib/public/admin/tiny_mce/themes/advanced/skins/o2k7/img/button_bg_black.png +0 -0
  298. data/lib/public/admin/tiny_mce/themes/advanced/skins/o2k7/img/button_bg_silver.png +0 -0
  299. data/lib/public/admin/tiny_mce/themes/advanced/skins/o2k7/ui.css +217 -0
  300. data/lib/public/admin/tiny_mce/themes/advanced/skins/o2k7/ui_black.css +8 -0
  301. data/lib/public/admin/tiny_mce/themes/advanced/skins/o2k7/ui_silver.css +5 -0
  302. data/lib/public/admin/tiny_mce/themes/advanced/source_editor.htm +25 -0
  303. data/lib/public/admin/tiny_mce/themes/simple/editor_template.js +1 -0
  304. data/lib/public/admin/tiny_mce/themes/simple/editor_template_src.js +84 -0
  305. data/lib/public/admin/tiny_mce/themes/simple/img/icons.gif +0 -0
  306. data/lib/public/admin/tiny_mce/themes/simple/langs/en.js +11 -0
  307. data/lib/public/admin/tiny_mce/themes/simple/skins/default/content.css +25 -0
  308. data/lib/public/admin/tiny_mce/themes/simple/skins/default/ui.css +32 -0
  309. data/lib/public/admin/tiny_mce/themes/simple/skins/o2k7/content.css +17 -0
  310. data/lib/public/admin/tiny_mce/themes/simple/skins/o2k7/img/button_bg.png +0 -0
  311. data/lib/public/admin/tiny_mce/themes/simple/skins/o2k7/ui.css +35 -0
  312. data/lib/public/admin/tiny_mce/tiny_mce.js +1 -0
  313. data/lib/public/admin/tiny_mce/tiny_mce_popup.js +5 -0
  314. data/lib/public/admin/tiny_mce/tiny_mce_src.js +15519 -0
  315. data/lib/public/admin/tiny_mce/utils/editable_selects.js +70 -0
  316. data/lib/public/admin/tiny_mce/utils/form_utils.js +210 -0
  317. data/lib/public/admin/tiny_mce/utils/mctabs.js +162 -0
  318. data/lib/public/admin/tiny_mce/utils/validate.js +252 -0
  319. data/lib/yodel_admin.rb +3 -0
  320. data/yodel_admin.gemspec +22 -0
  321. metadata +365 -0
@@ -0,0 +1,1030 @@
1
+ var MENU_WIDTH = 371;
2
+
3
+ // Array Remove - By John Resig (MIT Licensed)
4
+ Array.prototype.remove = function(from, to) {
5
+ var rest = this.slice((to || from) + 1 || this.length);
6
+ this.length = from < 0 ? this.length + from : from;
7
+ return this.push.apply(this, rest);
8
+ };
9
+
10
+ function initialiseWidgets() {
11
+ hideModelPanel();
12
+ initialiseHTMLFields();
13
+ initialiseMultipleSelectFields();
14
+ addClearLinks();
15
+ }
16
+
17
+ function initialiseHTMLFields() {
18
+ if($('.list').length) {
19
+ var width = '320px';
20
+ var row1 = 'bold,italic,underline,strikethrough,sub,sup,charmap,|,justifyleft,justifycenter,justifyright,justifyfull';
21
+ var row2 = 'formatselect,fontsizeselect,|,bullist,numlist,outdent,indent,blockquote';
22
+ var row3 = 'link,unlink,|,code';
23
+ } else {
24
+ var width = '100%';
25
+ var row1 = 'bold,italic,underline,strikethrough,sub,sup,charmap,|,justifyleft,justifycenter,justifyright,justifyfull,|,formatselect,fontsizeselect,|,bullist,numlist,outdent,indent,blockquote,|,link,unlink,|,code';
26
+ var row2 = '';
27
+ var row3 = '';
28
+ }
29
+
30
+ $('textarea.html').each(function(index, field) {
31
+ $(field).tinymce({
32
+ script_url : '/admin/tiny_mce/tiny_mce.js',
33
+ theme : "advanced",
34
+ plugins : "safari,inlinepopups,paste",
35
+ width: width,
36
+ height: '200',
37
+ theme_advanced_blockformats: 'p,h1,h2,h3',
38
+
39
+ theme_advanced_buttons1 : row1,
40
+ theme_advanced_buttons2 : row2,
41
+ theme_advanced_buttons3 : row3,
42
+ theme_advanced_toolbar_location : "top",
43
+ theme_advanced_toolbar_align : "left",
44
+ theme_advanced_statusbar_location : "none",
45
+ theme_advanced_resizing : false
46
+ });
47
+ });
48
+ }
49
+
50
+ function initialiseMultipleSelectFields() {
51
+ $('select[multiple=multiple]').chosen();
52
+ }
53
+
54
+ function addClearLinks() {
55
+ $('#record_form .field-type-attachment p, #record_form .field-type-image p').each(function(index, p) {
56
+ var clear = $('<a class="clear">clear</a>');
57
+ $(p).append(clear);
58
+ if($(p).find('span').html() == 'none')
59
+ clear.hide();
60
+ });
61
+ }
62
+
63
+ $('#admin_save button').click(function(event) {
64
+ $('#admin_save_spinner').fadeIn().delay(1000).fadeOut();
65
+ $('#admin_save_success').delay(1500).fadeIn().delay(2000).fadeOut();
66
+ });
67
+
68
+
69
+
70
+ var menus = {};
71
+
72
+ function showMenu(parentName, recordID, initialLoad) {
73
+ if(menus[recordID]) {
74
+ pushNavigationPanel(parentName, menus[recordID]);
75
+ } else {
76
+ jQuery.getJSON(jsonURL + '?id=' + recordID, function(data) {
77
+ menus[recordID] = data;
78
+ pushNavigationPanel(parentName, data, initialLoad);
79
+ highlightSelectedRow(recordID);
80
+ });
81
+ }
82
+ }
83
+
84
+
85
+
86
+
87
+ var NEW_ROW = '<h1 class="new"><div class="folder_state spacer"></div><div class="icon"><div class="spinner"></div><img src="/admin/images/new.png"></div>New</h1></li>';
88
+
89
+ function constructRecordListItem(tree) {
90
+ // add the icon, name, slide and delete icons
91
+ var list = '<li class="record" data-record-id="' + tree.id + '" data-type="' + tree.type + '">';
92
+
93
+ // the h1 contains the content elements for each record
94
+ if(tree.menu_root)
95
+ list += '<h1 class="new_panel">';
96
+ else
97
+ list += '<h1>';
98
+
99
+ // add space for any children underneath this record
100
+ var canHaveChildren = (types[tree.type].validChildren.length > 0 && !tree.menu_root);
101
+ var hasChildren = (tree.children && tree.children.length > 0);
102
+ if(!tree.root) {
103
+ list += '<div class="folder_state';
104
+ if(hasChildren)
105
+ list += ' open';
106
+ list += '"></div>';
107
+ }
108
+
109
+ // add the slider, delete and drag handle icons if necessary
110
+ list += '<div class="icon"><div class="spinner"></div><img src="';
111
+ if(tree.icon)
112
+ list += tree.icon;
113
+ else
114
+ list += '/admin/images/default_icon.png';
115
+ list += '"></div><p>' + tree.name + '</p>';
116
+ if(tree.menu_root)
117
+ list += '<div class="slide"></div>';
118
+ if(!tree.root)
119
+ list += '<div class="delete"></div><div class="drag"></div>';
120
+ if(canHaveChildren) {
121
+ list += '<div class="add_child';
122
+ if(hasChildren || tree.root)
123
+ list += ' hidden';
124
+ list += '"></div>';
125
+ }
126
+ list += '</h1>';
127
+
128
+ // generate a tree for child elements of this record
129
+ var child_lists = [];
130
+ for(var i = 0, c = tree.children.length; i < c; i++)
131
+ child_lists.push(constructRecordListItem(tree.children[i]));
132
+
133
+ if(canHaveChildren)
134
+ child_lists.push('<li>' + NEW_ROW);
135
+
136
+ if(!tree.root)
137
+ list += '<ul class="child_elements" style="display: none">';
138
+ else
139
+ list += '<ul class="child_elements">';
140
+
141
+ return list + child_lists.join('') + '</ul></li>';
142
+ }
143
+
144
+ function constructRecordList(tree) {
145
+ return '<ul>' + constructRecordListItem(tree) + '</ul>';
146
+ }
147
+
148
+
149
+ var navigationPanels = [];
150
+
151
+ function dragError(parent, oldIndex, row) {
152
+ alert('Sorry, an error occurred updating the position of this record. Please reload the page and try again.');
153
+
154
+ // move the row back to its old position; record indexes are 1 based
155
+ if(oldIndex == 1) {
156
+ row.insertBefore('.record[data-record-id=' + parent.children[1].id + ']');
157
+ } else {
158
+ row.insertAfter('.record[data-record-id=' + parent.children[oldIndex - 2].id + ']');
159
+ }
160
+ }
161
+
162
+ function pushNavigationPanel(rootName, tree, isPageRoot) {
163
+ // create the panel html
164
+ html = '<nav class="previous_folder">';
165
+ if(rootName) {
166
+ html += '<a href="#" class="prev_nav_panel'
167
+ if(isPageRoot)
168
+ html += ' root';
169
+ html += '">' + rootName + '</a>';
170
+ }
171
+ html += '</nav><nav class="records">' + constructRecordList(tree) + '</nav></div>';
172
+
173
+ // push the panel to the elements list
174
+ var panel = $('<div class="navigation_panel">');
175
+ panel.html(html);
176
+ panel.data('tree', tree);
177
+ navigationPanels.push(panel);
178
+
179
+ // prepare for animation and insert the panel
180
+ if(navigationPanels.length != 1)
181
+ panel.css('left', MENU_WIDTH + 'px');
182
+ $('#navigation_panels').append(panel);
183
+ panel.find('ul.child_elements').sortable({
184
+ containment: 'parent',
185
+ items: '> li.record',
186
+ axis: 'y',
187
+ handle: 'div.drag',
188
+ revert: 200,
189
+ cursor: 'ns-resize',
190
+ start: function(event, ui) {
191
+ ui.item.addClass('dragging');
192
+ },
193
+ stop: function(event, ui) {
194
+ ui.item.removeClass('dragging');
195
+
196
+ // save the new record index
197
+ var tree = navigationPanels[navigationPanels.length - 1].data('tree');
198
+ var id = ui.item.attr('data-record-id');
199
+ var record = null;
200
+ var parent = null;
201
+
202
+ // find the record by id
203
+ if(id == tree.id)
204
+ record = tree;
205
+ else
206
+ record = findRecord(tree, id);
207
+
208
+ // try and find the parent record
209
+ if(record && record.parent_id)
210
+ parent = findRecord(tree, record.parent_id);
211
+ if(!parent) {
212
+ alert("Sorry, an error occurred updating the position of this record (the parent record could not be found). Please refresh the page and try again.");
213
+ return;
214
+ }
215
+
216
+ // if this is the only child of the parent, ignore the index change
217
+ if(parent.children.length == 1)
218
+ return;
219
+
220
+ // otherwise detect the new index of this record
221
+ var oldIndex = record.index;
222
+ if(ui.item.prev().length != 0) {
223
+ var sibling = findRecord(tree, ui.item.prev().attr('data-record-id'));
224
+ var newIndex = sibling.index;
225
+ if(record.index > sibling.index)
226
+ newIndex += 1;
227
+ } else {
228
+ var newIndex = 1;
229
+ }
230
+ if(oldIndex == newIndex)
231
+ return;
232
+
233
+ // save the updated index
234
+ $.ajax(jsonURL, {
235
+ data: {id: record.id, _method: 'put', action: 'set_index', index: newIndex},
236
+ dataType: 'json',
237
+ type: 'post',
238
+ success: function(data, textStatus, jqXHR) {
239
+ if(data.success == false) {
240
+ dragError(parent, oldIndex, ui.item);
241
+ return;
242
+ }
243
+
244
+ // update backing object
245
+ record.index = newIndex;
246
+
247
+ // update the index of other affected records
248
+ if(newIndex > oldIndex) {
249
+ for(var i = oldIndex; i < newIndex; i++)
250
+ parent.children[i].index -= 1;
251
+ } else {
252
+ for(var i = (newIndex - 1); i < (oldIndex - 2); i++)
253
+ parent.children[i].index += 1;
254
+ }
255
+
256
+ // change the position of the record in the parent's list of children
257
+ parent.children.splice(oldIndex - 1, 1);
258
+ parent.children.splice(newIndex - 1, 0, record);
259
+
260
+ }, error: function(jqXHR, textStatus, errorThrown) {
261
+ dragError(parent, oldIndex, ui.item);
262
+ }
263
+ });
264
+ }
265
+ });
266
+
267
+ // animate the panel in to view
268
+ if(navigationPanels.length != 1) {
269
+ navigationPanels[navigationPanels.length - 2].animate({left: '-' + MENU_WIDTH + 'px'});
270
+ panel.animate({left: '0px'});
271
+ }
272
+ }
273
+
274
+ function popNavigationPanel() {
275
+ if(navigationPanels.length == 1)
276
+ return;
277
+
278
+ // swap between the previous and current panels, and remove the current panel
279
+ navigationPanels[navigationPanels.length - 2].animate({left: '0px'});
280
+ navigationPanels[navigationPanels.length - 1].animate({left: MENU_WIDTH + 'px'}, {complete: function() {
281
+ $(this).remove();
282
+ }});
283
+ navigationPanels = navigationPanels.slice(0, -1);
284
+
285
+ // sliding back a navigation panel means the currently displayed record
286
+ // can no longer be displayed; clear the record form and any highlights
287
+ $('#record').empty();
288
+ $('.record h1.selected').removeClass('selected');
289
+ }
290
+
291
+
292
+ function showNavigationPanel(recordID, element) {
293
+ // get the name of the root element in the current list
294
+ var rootName = $(element).parents('nav.records').find('> ul > li > h1 > p').html();
295
+
296
+ // show the new navigation panel
297
+ showMenu(rootName, recordID);
298
+ }
299
+
300
+ function showPreviousNavigationPanel(event) {
301
+ popNavigationPanel();
302
+ event.preventDefault();
303
+ }
304
+
305
+
306
+ // folder open/close
307
+ function showOrHideChildren(event) {
308
+ event.preventDefault();
309
+ event.stopPropagation();
310
+ if($(event.target).hasClass('open'))
311
+ showChildren(event);
312
+ else
313
+ hideChildren(event);
314
+ }
315
+
316
+ function showChildren(event) {
317
+ var button = $(event.target);
318
+
319
+ button.parents('h1').siblings('ul').animate({
320
+ height: 'show',
321
+ opacity: 'show'
322
+ }, 400);
323
+
324
+ button.removeClass('open');
325
+ button.addClass('close');
326
+ }
327
+
328
+ function hideChildren(event) {
329
+ var button = $(event.target);
330
+
331
+ button.parents('h1').siblings('ul').animate({
332
+ height: 'hide',
333
+ opacity: 'hide'
334
+ }, 400);
335
+
336
+ button.removeClass('close');
337
+ button.addClass('open');
338
+ }
339
+
340
+
341
+ // update an existing record or add a record to the tree
342
+ function updateRecord(record) {
343
+ // either find the parent record by searching from the root of the
344
+ // current tree, or the updated record is the root of the current tree
345
+ var tree = navigationPanels[navigationPanels.length - 1].data('tree');
346
+ var treeRecord = null;
347
+ var parent = null;
348
+
349
+ if(record.id == tree.id)
350
+ treeRecord = tree;
351
+ else
352
+ if(record.parent_id == tree.id)
353
+ parent = tree;
354
+ else
355
+ parent = findRecord(tree, record.parent_id);
356
+
357
+ if(!treeRecord && !parent) {
358
+ alert("Sorry, an error occurred while creating this record (no parent or record could be found). Please refresh the page and try again.");
359
+ return;
360
+ }
361
+
362
+ // if we found a parent, determine if this is a new or existing record
363
+ var update = false;
364
+ if(parent) {
365
+ if(!parent.children)
366
+ parent.children = [];
367
+
368
+ // try and find an existing record
369
+ for(var i = 0, c = parent.children.length; i < c; i++) {
370
+ if(parent.children[i].id == record.id) {
371
+ treeRecord = parent.children[i];
372
+ update = true;
373
+ break;
374
+ }
375
+ }
376
+
377
+ // if none was found, create a blank record
378
+ if(!update) {
379
+ treeRecord = {children:[]};
380
+ parent.children.push(treeRecord);
381
+ }
382
+ } else {
383
+ // if there's no parent, treeRecord must be an existing root record
384
+ update = true;
385
+ }
386
+
387
+ // copy the new values across
388
+ treeRecord.id = record.id;
389
+ treeRecord.icon = record.icon;
390
+ treeRecord.index = record.index;
391
+ treeRecord.root = treeRecord.root || false;
392
+ treeRecord.menu_root = record.menu_root;
393
+ treeRecord.name = record.name;
394
+ treeRecord.parent_id = record.parent_id;
395
+ treeRecord.type = record.type;
396
+
397
+ if(update) {
398
+ // change the existing record's name
399
+ $('.record[data-record-id=' + record.id + '] > h1 > p').html(record.name);
400
+
401
+ } else {
402
+ // if this is the first new child of the parent, hide the new (+)
403
+ // button, show the "New" row, show the list, and set the disclosure
404
+ // button to - (indicating the folder is open)
405
+ var parentRow = $('.record[data-record-id=' + parent.id + ']');
406
+ var parentChildList = parentRow.find('> .child_elements');
407
+ if(parent && !parent.root && !parent.menu_root) {
408
+ if(parent.children.length == 1) {
409
+ parentChildList.show();
410
+ parentRow.find('> h1 > .add_child').addClass('hidden');
411
+ parentRow.find('> h1 > .folder_state').addClass('close');
412
+ parentRow.find('> h1 > .folder_state').removeClass('open');
413
+ }
414
+ }
415
+
416
+ // insert the new row
417
+ var row = constructRecordListItem(treeRecord);
418
+ parentChildList.find('> li:last-child').before(row);
419
+ highlightSelectedRow(treeRecord.id);
420
+
421
+ // if the row is a menu root, slide to the new menu
422
+ if(treeRecord.menu_root)
423
+ showNavigationPanel(treeRecord.id, parentRow);
424
+ }
425
+ }
426
+
427
+ function findRecord(parent, id) {
428
+ if(parent.id == id)
429
+ return parent;
430
+
431
+ if(parent.children && parent.children.length > 0) {
432
+ for(var i = 0, c = parent.children.length; i < c; i++) {
433
+ if(parent.children[i].id == id)
434
+ return parent.children[i];
435
+ var record = findRecord(parent.children[i], id);
436
+ if(record != false)
437
+ return record;
438
+ }
439
+ }
440
+ return false;
441
+ }
442
+
443
+ // delete a record from the tree
444
+ function deleteRecordInTree(parent, id) {
445
+ if(parent.children && parent.children.length > 0) {
446
+ for(var i = 0, c = parent.children.length; i < c; i++) {
447
+ var record = parent.children[i];
448
+ if(record.id == id) {
449
+ parent.children.remove(i, i);
450
+ return parent;
451
+ } else {
452
+ var result = deleteRecordInTree(record, id);
453
+ if(result)
454
+ return result;
455
+ }
456
+ }
457
+ }
458
+ return false;
459
+ }
460
+
461
+
462
+
463
+
464
+ // delete buttons
465
+ function deleteButtonPressed(event) {
466
+ event.preventDefault();
467
+ event.stopPropagation();
468
+ var recordRow = $(event.target).parents('li').first();
469
+ var recordTypeName = types[recordRow.attr('data-type')].humanName;
470
+ var recordID = recordRow.attr('data-record-id');
471
+
472
+ if(confirm('Are you sure you want to delete this ' + recordTypeName + '?')) {
473
+ showSpinner(recordRow);
474
+ $.ajax(jsonURL, {
475
+ data: {id: recordID, _method: 'delete'},
476
+ dataType: 'json',
477
+ type: 'post',
478
+ success: function(data, textStatus, jqXHR) {
479
+ // delete the backing object
480
+ var tree = navigationPanels[navigationPanels.length - 1].data('tree');
481
+ var parent = deleteRecordInTree(tree, recordID);
482
+
483
+ // remove the row representing the object
484
+ recordRow.remove();
485
+
486
+ // clear the record panel if this record was being displayed
487
+ if($('#record_id').val() == recordID)
488
+ $('#record').empty();
489
+
490
+ // clear the record panel if this record was the parent of a
491
+ // new record currently being created
492
+ if($('#parent').val() == recordID)
493
+ $('#record').empty();
494
+
495
+ // collapse the record if this was the last child record
496
+ if(parent && parent.children.length == 0 && !parent.root) {
497
+ var parentRow = $('.record[data-record-id=' + parent.id + ']');
498
+ var parentChildList = parentRow.find('> .child_elements');
499
+ var folderState = parentRow.find('> h1 > .folder_state');
500
+ parentChildList.hide();
501
+ parentRow.find('h1 > .add_child').removeClass('hidden');
502
+ folderState.removeClass('close');
503
+ folderState.removeClass('open');
504
+
505
+ // if a new record was being created under the parent, and this
506
+ // deleted record was the last child, change the highlighted
507
+ // row from the 'new' row to the parent row itself
508
+ if(parentChildList.find('li .new').hasClass('selected')) {
509
+ parentChildList.find('li .new').removeClass('selected');
510
+ parentRow.find('> h1').addClass('selected');
511
+ }
512
+ }
513
+
514
+ // remove the record from the menu list if it was a menu root
515
+ if(menus[recordID])
516
+ delete menus[recordID];
517
+ }, error: function(jqXHR, textStatus, errorThrown) {
518
+ // FIXME: better error message
519
+ hideSpinner(recordRow);
520
+ alert('Sorry, an error occurred deleting this record. Please reload the page and try again.');
521
+ }
522
+ });
523
+ }
524
+ }
525
+
526
+
527
+ // attachment/photo clearing
528
+ function clearAttachmentOrPhoto(event) {
529
+ event.preventDefault();
530
+ var link = $(event.target);
531
+ var container = link.closest('.field-type-attachment, .field-type-image');
532
+ link.hide();
533
+ container.find('p span').html('none');
534
+ container.find('input[type=checkbox]').attr('checked', true);
535
+ container.find('input[type=file]').val('');
536
+ link.closest('.field-type-image').find('img').hide();
537
+ }
538
+
539
+ function hideClear(event) {
540
+ var file_input = $(event.target);
541
+ var container = file_input.closest('.field-type-attachment, .field-type-image');
542
+ container.find('input[type=checkbox]').removeAttr('checked');
543
+ container.find('.clear').show();
544
+ }
545
+
546
+
547
+ // new record type panel
548
+ var modelPanelShowing = false;
549
+ function showModelPanel(event) {
550
+ event.preventDefault();
551
+ event.stopPropagation();
552
+ var recordRow = $(event.target).parents('li.record');
553
+
554
+ // hide all new model buttons, then display only those valid for the selected parent
555
+ // if the model only has a single allowed child type, immediately show a new record form
556
+ var childTypes = types[recordRow.attr('data-type')].validChildren;
557
+ var parentID = recordRow.attr('data-record-id');
558
+
559
+ if(childTypes.length == 1) {
560
+ var modelID = types[childTypes[0]].id;
561
+ loadNewRecord(modelID, parentID);
562
+ return;
563
+ } else {
564
+ $('#new_model_panel ul a').hide();
565
+ for(var i = 0, c = childTypes.length; i < c; i++) {
566
+ $('a.model[data-type="' + childTypes[i] + '"]').show();
567
+ }
568
+ }
569
+
570
+ $('#new_model_panel').attr('data-parent-id', parentID);
571
+ $('#new_model_panel').fadeIn();
572
+ $('#admin_content').fadeOut();
573
+ modelPanelShowing = true;
574
+ }
575
+
576
+ function hideModelPanel(event) {
577
+ if(!modelPanelShowing) return;
578
+ if(event) event.preventDefault();
579
+ if(modelPanelShowing) {
580
+ $('#new_model_panel').fadeOut();
581
+ $('#admin_content').fadeIn();
582
+ $('#new_model_panel .spinner').hide();
583
+ $('#new_model_panel .icon').show();
584
+ }
585
+ modelPanelShowing = false;
586
+ }
587
+
588
+
589
+
590
+
591
+ // options and section toggle button
592
+ function toggleSectionVisibility(event) {
593
+ event.preventDefault();
594
+ $(event.target).closest('section').find('> div').slideToggle('slow');
595
+ $(event.target).html($(event.target).html() == 'show' ? 'hide' : 'show');
596
+ event.preventDefault();
597
+ }
598
+
599
+
600
+ // delete an embedded doc
601
+ function deleteEmbeddedDoc(event) {
602
+ event.preventDefault();
603
+ var target = $(event.target);
604
+ var documents = target.parents('div.embedded_documents');
605
+ var type = documents.attr('data-type');
606
+
607
+ if(confirm('Are you sure you want to delete this ' + type + '?')) {
608
+ target.parents('div.embedded_document').animate({
609
+ height: 'hide',
610
+ opacity: 'hide'
611
+ }, {
612
+ complete: function() {
613
+ // show the 'No TYPE' text if we are removing the last embedded doc in a collection
614
+ if(documents.find('div.embedded_document').size() == 1)
615
+ documents.find('.no_embedded_documents').animate({height: 'show', opacity: 'show'});
616
+ $(this).remove();
617
+ }
618
+ });
619
+ }
620
+ }
621
+
622
+ // add a new embedded doc
623
+ function addEmbeddedDoc(event) {
624
+ event.preventDefault();
625
+ var target = $(event.target);
626
+ var documents = target.parents('div.embedded_documents');
627
+
628
+ // construct a new document form an insert in to the collection
629
+ var doc = $('<div class="embedded_document" style="display: none"><a href="#" class="delete_embedded_document"></a><table><tr><td id="label_col"></td><td id="input_col"></td></tr><tr><td><label>Photo</label></td><td><div class="attachment photo"><div class="photo_preview"><img src="sample_photo.jpg"></div><p class="current_value"><span class="title">File:</span>train.jpeg <a href="#" class="clear">Clear</a></p><p><span class="title">Select:</span><input type="file"></p><input type="hidden" name="delete_X" class="delete" value="false"></div></td></tr><tr><td><label>Name</label></td><td><input type="text"></td></tr></table></div>');
630
+ $(event.target).before(doc);
631
+
632
+ // hide the 'No TYPE' text if we are adding a new embedded doc in to an empty collection
633
+ // animate the insertion of the new doc after hiding the 'No TYPE' text or immediately
634
+ if(documents.find('div.embedded_document').size() == 1) {
635
+ documents.find('.no_embedded_documents').animate({
636
+ height: 'hide',
637
+ opacity: 'hide'
638
+ }, {
639
+ duration: 150,
640
+ complete: function() {
641
+ doc.animate({height: 'show', opacity: 'show'});
642
+ }
643
+ });
644
+ } else {
645
+ doc.animate({height: 'show', opacity: 'show'});
646
+ }
647
+ }
648
+
649
+
650
+
651
+ $('div.delete').live('click', deleteButtonPressed);
652
+ $('div.folder_state').live('click', showOrHideChildren);
653
+
654
+ $('a.clear').live('click', clearAttachmentOrPhoto);
655
+ $('input[type=file]').live('change', hideClear);
656
+
657
+ $('a.prev_nav_panel').live('click', showPreviousNavigationPanel);
658
+ $('a.section_toggle').live('click', toggleSectionVisibility);
659
+ $('a.delete_embedded_document').live('click', deleteEmbeddedDoc);
660
+ $('a.add_embedded_document').live('click', addEmbeddedDoc);
661
+
662
+ $('h1.new').live('click', showModelPanel);
663
+ $('div.add_child').live('click', showModelPanel);
664
+ $('#cancel_new_record').live('click', hideModelPanel);
665
+
666
+ $('.opens-editor').click(function(event) {
667
+ $.ajax($(event.target).attr('href'));
668
+ event.preventDefault();
669
+ });
670
+
671
+
672
+
673
+
674
+
675
+ // show and hide spinners to indicate network activity. More than
676
+ // one spinner at a time may be shown (e.g deleting two records
677
+ // while loading another)
678
+ function showSpinner(row) {
679
+ if(typeof row == 'string')
680
+ row = $('.record[data-record-id=' + row + '] > h1 > .icon .spinner').show();
681
+ else
682
+ row = $(row).find('.icon .spinner').show();
683
+ }
684
+
685
+ function hideSpinner(row) {
686
+ if(typeof row == 'string')
687
+ row = $('.record[data-record-id=' + row + '] > h1 > .icon .spinner').hide();
688
+ else
689
+ row = $(row).find('.icon .spinner').hide();
690
+ }
691
+
692
+ // un-highlight all other rows, and highlight a new selected record
693
+ function highlightSelectedRow(row) {
694
+ $('.record h1.selected').removeClass('selected');
695
+ hideSpinner(row);
696
+ if(typeof row == 'string')
697
+ row = $('.record[data-record-id=' + row + '] > h1');
698
+ else
699
+ row = $(row);
700
+ row.addClass('selected');
701
+ }
702
+
703
+ // load an existing record's form
704
+ function loadRecord(id) {
705
+ $('#record').load(htmlURL + '?action=show&id=' + id, function(text, status, req) {
706
+ highlightSelectedRow(id);
707
+ hideModelPanel();
708
+ initialiseWidgets();
709
+ });
710
+ }
711
+
712
+ // show a menu root record
713
+ $('.record > h1.new_panel').live('click', function(event) {
714
+ var recordID = $(this).parent().attr('data-record-id');
715
+ showSpinner(this);
716
+ loadRecord(recordID);
717
+ showNavigationPanel(recordID, this);
718
+ event.stopImmediatePropagation();
719
+ });
720
+
721
+ // show a normal record
722
+ $('.record > h1').live('click', function(event) {
723
+ showSpinner(this);
724
+ loadRecord($(this).parent().attr('data-record-id'));
725
+ });
726
+
727
+ // load a blank (new) record
728
+ function loadNewRecord(modelID, parentID, modelWasSelected) {
729
+ // for parents with existing children, show a spinner on and highlight
730
+ // the 'new' row, otherwise highlight the parent row itself
731
+ var tree = navigationPanels[navigationPanels.length - 1].data('tree');
732
+ var parent = findRecord(tree, parentID);
733
+
734
+ if(modelWasSelected == undefined) {
735
+ if(parent.children.length == 0)
736
+ showSpinner(parentID);
737
+ else
738
+ showSpinner($('.record[data-record-id=' + parentID + '] > .child_elements > li > h1.new'));
739
+ }
740
+
741
+ // load the blank default record
742
+ $('#record').load(htmlURL + '?action=new&model=' + modelID + '&parent=' + parentID, function(text, status, req) {
743
+ initialiseWidgets();
744
+ if(parent.children.length == 0)
745
+ highlightSelectedRow(parentID);
746
+ else
747
+ highlightSelectedRow($('.record[data-record-id=' + parentID + '] > .child_elements > li > h1.new'));
748
+ });
749
+ }
750
+
751
+ $('a.model').click(function(event) {
752
+ var parentID = $('#new_model_panel').attr('data-parent-id');
753
+ var modelID = $(this).attr('data-model-id');
754
+ event.preventDefault();
755
+
756
+ $(this).find('.spinner').show();
757
+ $(this).find('.icon').hide();
758
+ loadNewRecord(modelID, parentID, true);
759
+ });
760
+
761
+ $('#add_domain').click(function(event) {
762
+ var domain = $('#new_domain').val();
763
+ if(domain != '') {
764
+ $('#domains_list').append("<li><input type='hidden' name='domains[]' value='" + domain + "'>" + domain + " - <a href='#' class='remove_domain'>remove</a></li>");
765
+ $('#new_domain').val('')
766
+ }
767
+ event.preventDefault();
768
+ });
769
+
770
+ $('.remove_domain').live('click', function(event) {
771
+ $(event.target).closest('li').remove();
772
+ });
773
+
774
+
775
+
776
+
777
+
778
+ // syncing
779
+ var SYNC_URL = '/admin/sync.json';
780
+ var syncing = false;
781
+
782
+ function showSyncStatus(status) {
783
+ jQuery('#site_menu > p').queue(function () {
784
+ jQuery('#site_menu > p span').html(status);
785
+ jQuery(this).fadeIn();
786
+ jQuery(this).dequeue();
787
+ });
788
+ }
789
+
790
+ function hideSyncStatus() {
791
+ syncing = false;
792
+ jQuery('#site_menu > p').queue(function () {
793
+ jQuery(this).fadeOut();
794
+ jQuery(this).dequeue();
795
+ });
796
+ }
797
+
798
+ function push(creating) {
799
+ showSyncStatus('Pushing changes');
800
+ var errorText = "Sorry, an error occurred while pushing changes to the remote server";
801
+
802
+ jQuery.ajax(SYNC_URL, {type: 'POST', success: function(data) {
803
+ if(!data.success) {
804
+ if(data.reason)
805
+ alert(errorText + ": " + data.reason);
806
+ else if(data.conflicts)
807
+ alert("The following files are in conflict and need to be resolved before pushing: " + data.conflicts.join(','));
808
+ else
809
+ alert(errorText + ".");
810
+ } else if(creating) {
811
+ window.open('http://' + data.remoteDomain + '/', 'livesite');
812
+ window.location.reload()
813
+ }
814
+ }, error: function(jqXHR, textStatus, errorThrown) {
815
+ alert(errorText + ".");
816
+ }, complete: function(jqXHR, textStatus) {
817
+ hideSyncStatus();
818
+ }});
819
+ }
820
+
821
+ $('.sync.push').live('click', function(event) {
822
+ if(syncing)
823
+ return;
824
+ else
825
+ syncing = true;
826
+ push();
827
+ });
828
+
829
+ $('.sync.create').live('click', function(event) {
830
+ if(syncing)
831
+ return;
832
+ else
833
+ syncing = true;
834
+ showSyncStatus('Creating site');
835
+
836
+ jQuery.ajax(SYNC_URL, {data: {remote: $(this).attr('data-sync-remote')}, type: 'POST', success: function(data) {
837
+ if(data.success) {
838
+ push(true);
839
+ } else {
840
+ alert("Sorry, an error occurred while creating this site on the remote server: " + data.reason);
841
+ hideSyncStatus();
842
+ }
843
+ }, error: function(jqXHR, textStatus, errorThrown) {
844
+ alert("Sorry, an error occurred while creating this site on the remote server.");
845
+ hideSyncStatus();
846
+ }});
847
+ });
848
+
849
+ $('.sync.pull').live('click', function(event) {
850
+ if(syncing)
851
+ return;
852
+ else
853
+ syncing = true;
854
+ showSyncStatus('Pulling changes');
855
+ var errorText = "Sorry, an error occurred while pulling changes from the remote server";
856
+
857
+ jQuery.ajax(SYNC_URL, {type: 'GET', success: function(data) {
858
+ if(!data.success) {
859
+ if(data.reason)
860
+ alert(errorText + ": " + data.reason);
861
+ else if(data.requires_push)
862
+ alert(errorText + ": No remote server is associated with this site");
863
+ else if(data.conflicts)
864
+ alert("The following files are in conflict and need to be resolved before pulling: " + data.conflicts.join(','));
865
+ else
866
+ alert(errorText + ".");
867
+ }
868
+ }, error: function(jqXHR, textStatus, errorThrown) {
869
+ alert(errorText + ".");
870
+ }, complete: function(jqXHR, textStatus) {
871
+ hideSyncStatus();
872
+ }});
873
+ });
874
+
875
+
876
+
877
+
878
+
879
+ // admin list page
880
+ function adminListPageValueExtractor(node) {
881
+ return $(node).attr('data-value');
882
+ }
883
+
884
+ function fixHeaders(table) {
885
+ var headers = table.find('th');
886
+ var cols = table.find('col');
887
+
888
+ headers.each(function(index, header) {
889
+ var header = $(header);
890
+ var offset = header.offset();
891
+ if(index == (headers.length - 1))
892
+ header.width(header.width() + 2);
893
+ else
894
+ header.width(header.width());
895
+ $(cols[index]).width(header.outerWidth());
896
+ header.css('left', offset.left + 'px');
897
+ header.css('top', (offset.top - 37) + 'px');
898
+ header.css('position', 'fixed');
899
+ });
900
+ }
901
+
902
+ function searchList() {
903
+ var terms = $('#search').val().split(' ');
904
+ $('#list_items table tbody tr').each(function(index, row) {
905
+ var match = false;
906
+ var text = [];
907
+
908
+ // extract the text of the cell of each row, separated by spaces
909
+ $(row).find('td').each(function(index, cell) {
910
+ text.push($(cell).text());
911
+ });
912
+ text = text.join(' ');
913
+
914
+ // determine if any of the terms are matched by the row text
915
+ for(var i = 0; i < terms.length; i++) {
916
+ if(text.indexOf(terms[i]) != -1) {
917
+ match = true;
918
+ break;
919
+ }
920
+ }
921
+
922
+ if(match)
923
+ $(row).css('display', 'table-row');
924
+ else
925
+ $(row).css('display', 'none');
926
+ });
927
+ }
928
+
929
+ $('#search').keyup(function() {
930
+ searchList();
931
+ });
932
+
933
+ $('#search').blur(function() {
934
+ searchList();
935
+ });
936
+
937
+ function highlightSelectedListRow(row) {
938
+ $('#list_items tbody tr').removeClass('selected');
939
+ if(row)
940
+ row.addClass('selected');
941
+ }
942
+
943
+ $('#list_items tbody tr').live('click', function() {
944
+ var row = $(this);
945
+ var recordID = row.attr('data-record-id');
946
+ $('#activity_spinner').fadeIn();
947
+
948
+ $('#record').load(htmlURL + '?id=' + recordID, function(text, status, req) {
949
+ $('#activity_spinner').fadeOut();
950
+ if(status == 'error') {
951
+ alert("Sorry, an error occurred loading this record. Please refresh the page and try again.");
952
+ } else {
953
+ highlightSelectedListRow(row);
954
+ initialiseWidgets();
955
+ $('#record').scrollTop(0);
956
+ }
957
+ });
958
+ });
959
+
960
+ function updateListRecord(json) {
961
+ var values = json.record;
962
+ var row = $('#list_items table tr[data-record-id=' + values['_id'] + ']').first();
963
+ $('#record_name').html(json.name);
964
+
965
+ if(row.length == 0) {
966
+ // insert a new row for the new record
967
+ row = $(json['_row_html']);
968
+ $('#list_items table tbody').append(row);
969
+ } else {
970
+ // update the row values
971
+ row.replaceWith(json['_row_html']);
972
+ row = $('#list_items table tr[data-record-id=' + values['_id'] + ']').first();
973
+ }
974
+
975
+ // tablesorter defers running update with setTimeout; work around
976
+ // this so redrawings occur after the cache has been updated
977
+ $('#list_items table').trigger('update');
978
+ setTimeout(function () {
979
+ var currentSort = $('#list_items table').first()[0].config.sortList;
980
+ $('#list_items table').trigger("sorton", [currentSort]);
981
+ highlightSelectedListRow(row);
982
+ }, 10);
983
+ }
984
+
985
+ $('.list #record .delete').live('click', function(event) {
986
+ event.preventDefault();
987
+ event.stopPropagation();
988
+ var recordID = $(event.target).attr('data-record-id');
989
+ var recordTypeName = $(event.target).attr('data-record-type');
990
+
991
+ if(confirm('Are you sure you want to delete this ' + recordTypeName + '?')) {
992
+ $('#delete_spinner').fadeIn();
993
+ $.ajax(jsonURL, {
994
+ data: {id: recordID, _method: 'delete'},
995
+ dataType: 'json',
996
+ type: 'post',
997
+
998
+ success: function(data, textStatus, jqXHR) {
999
+ $('#record').html('');
1000
+ $('#list_items table tr[data-record-id=' + recordID + ']').remove();
1001
+ $('#list_items table').trigger('update');
1002
+
1003
+ }, error: function(jqXHR, textStatus, errorThrown) {
1004
+ // FIXME: better error message
1005
+ alert('Sorry, an error occurred deleting this record. Please reload the page and try again.');
1006
+
1007
+ }, complete: function() {
1008
+ $('#delete_spinner').fadeOut();
1009
+ }
1010
+ });
1011
+ }
1012
+ });
1013
+
1014
+ $('#new_record').live('click', function(event) {
1015
+ event.preventDefault();
1016
+ event.stopPropagation();
1017
+ $('#activity_spinner').fadeIn();
1018
+
1019
+ $('#record').load(htmlURL + '?new=true', function(text, status, req) {
1020
+ $('#activity_spinner').fadeOut();
1021
+ if(status == 'error') {
1022
+ alert("Sorry, an error occurred loading a new record form. Please refresh the page and try again.");
1023
+ } else {
1024
+ highlightSelectedListRow();
1025
+ initialiseWidgets();
1026
+ $('#record').scrollTop(0);
1027
+ }
1028
+ });
1029
+ })
1030
+