glebtv-ckeditor 4.0.2.7 → 4.1.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (281) hide show
  1. checksums.yaml +7 -0
  2. data/README.rdoc +5 -195
  3. data/{vendor → app}/assets/javascripts/ckeditor/CHANGES.md +56 -0
  4. data/{vendor → app}/assets/javascripts/ckeditor/LICENSE.md +0 -0
  5. data/{vendor → app}/assets/javascripts/ckeditor/README.md +0 -0
  6. data/{vendor → app}/assets/javascripts/ckeditor/build-config.js +0 -0
  7. data/app/assets/javascripts/ckeditor/ckeditor.js +881 -0
  8. data/{vendor → app}/assets/javascripts/ckeditor/config.js.erb +0 -0
  9. data/app/assets/javascripts/ckeditor/contents.css +103 -0
  10. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/gal_add.jpg +0 -0
  11. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/gal_add.png +0 -0
  12. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/gal_del.png +0 -0
  13. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/gal_more.gif +0 -0
  14. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/preloader.gif +0 -0
  15. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/avi.gif +0 -0
  16. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/ckfnothumb.gif +0 -0
  17. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/doc.gif +0 -0
  18. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/docx.gif +0 -0
  19. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/exe.gif +0 -0
  20. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/gz.gif +0 -0
  21. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/htm.gif +0 -0
  22. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/jpg.gif +0 -0
  23. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/mp3.gif +0 -0
  24. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/mpg.gif +0 -0
  25. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/pdf.gif +0 -0
  26. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/psd.gif +0 -0
  27. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/rar.gif +0 -0
  28. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/swf.gif +0 -0
  29. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/tar.gif +0 -0
  30. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/txt.gif +0 -0
  31. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/unknown.gif +0 -0
  32. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/wmv.gif +0 -0
  33. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/xls.gif +0 -0
  34. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/xlsx.gif +0 -0
  35. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/images/thumbs/zip.gif +0 -0
  36. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/javascripts/application.js +0 -0
  37. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/javascripts/fileuploader.js +0 -0
  38. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/javascripts/jquery.min.js +0 -0
  39. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/javascripts/jquery.tmpl.min.js +0 -0
  40. data/{vendor → app}/assets/javascripts/ckeditor/filebrowser/javascripts/rails.js +0 -0
  41. data/app/assets/javascripts/ckeditor/filebrowser/stylesheets/uploader.css +118 -0
  42. data/app/assets/javascripts/ckeditor/{init.js → init.js.erb} +1 -1
  43. data/{vendor → app}/assets/javascripts/ckeditor/lang/en.js +1 -1
  44. data/{vendor → app}/assets/javascripts/ckeditor/lang/ru.js +1 -1
  45. data/{vendor → app}/assets/javascripts/ckeditor/plugins/CKCss/ckcss.png +0 -0
  46. data/{vendor → app}/assets/javascripts/ckeditor/plugins/CKCss/css/styles.css +0 -0
  47. data/{vendor → app}/assets/javascripts/ckeditor/plugins/CKCss/dialogs/ckcss.js +0 -0
  48. data/{vendor → app}/assets/javascripts/ckeditor/plugins/CKCss/lang/en.js +0 -0
  49. data/{vendor → app}/assets/javascripts/ckeditor/plugins/CKCss/lang/ru.js +0 -0
  50. data/{vendor → app}/assets/javascripts/ckeditor/plugins/CKCss/plugin.js +0 -0
  51. data/{vendor → app}/assets/javascripts/ckeditor/plugins/LoremIpsum/images/icon.png +0 -0
  52. data/{vendor → app}/assets/javascripts/ckeditor/plugins/LoremIpsum/images/icon1.png +0 -0
  53. data/{vendor → app}/assets/javascripts/ckeditor/plugins/LoremIpsum/plugin.js +0 -0
  54. data/{vendor → app}/assets/javascripts/ckeditor/plugins/a11yhelp/dialogs/a11yhelp.js +0 -0
  55. data/{vendor → app}/assets/javascripts/ckeditor/plugins/a11yhelp/dialogs/lang/en.js +0 -0
  56. data/{vendor → app}/assets/javascripts/ckeditor/plugins/a11yhelp/dialogs/lang/ru.js +0 -0
  57. data/{vendor → app}/assets/javascripts/ckeditor/plugins/clipboard/dialogs/paste.js +0 -0
  58. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/css/codemirror.ckeditor.css +38 -0
  59. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/css/codemirror.css +246 -245
  60. data/app/assets/javascripts/ckeditor/plugins/codemirror/css/codemirror.min.css +1 -0
  61. data/app/assets/javascripts/ckeditor/plugins/codemirror/icons/AutoComplete.png +0 -0
  62. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/icons/AutoFormat.png +0 -0
  63. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/icons/CommentSelectedRange.png +0 -0
  64. data/app/assets/javascripts/ckeditor/plugins/codemirror/icons/SearchCode.png +0 -0
  65. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/icons/UncommentSelectedRange.png +0 -0
  66. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/js/addon/dialog/dialog.js +81 -76
  67. data/app/assets/javascripts/ckeditor/plugins/codemirror/js/addon/edit/closebrackets.js +52 -0
  68. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/js/addon/edit/closetag.js +1 -2
  69. data/app/assets/javascripts/ckeditor/plugins/codemirror/js/addon/edit/continuecomment.js +44 -0
  70. data/app/assets/javascripts/ckeditor/plugins/codemirror/js/addon/edit/continuelist.js +25 -0
  71. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/js/addon/edit/matchbrackets.js +0 -0
  72. data/app/assets/javascripts/ckeditor/plugins/codemirror/js/addon/fold/brace-fold.js +31 -0
  73. data/app/assets/javascripts/ckeditor/plugins/codemirror/js/addon/fold/foldcode.js +32 -0
  74. data/app/assets/javascripts/ckeditor/plugins/codemirror/js/addon/fold/xml-fold.js +64 -0
  75. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/js/addon/format/autoFormatAll.js +0 -0
  76. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/js/addon/format/formatting.js +0 -0
  77. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/js/addon/search/match-highlighter.js +0 -0
  78. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/js/addon/search/search.js +131 -131
  79. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/js/addon/search/searchcursor.js +8 -9
  80. data/app/assets/javascripts/ckeditor/plugins/codemirror/js/codemirror.addons.min.js +1 -0
  81. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/js/codemirror.js +264 -132
  82. data/app/assets/javascripts/ckeditor/plugins/codemirror/js/codemirror.min.js +1 -0
  83. data/app/assets/javascripts/ckeditor/plugins/codemirror/js/codemirror.modes.min.js +1 -0
  84. data/app/assets/javascripts/ckeditor/plugins/codemirror/js/codemirror.search-addons.min.js +1 -0
  85. data/{vendor/assets/javascripts/ckeditor/plugins/codemirror/js → app/assets/javascripts/ckeditor/plugins/codemirror/js/mode}/css.js +337 -235
  86. data/{vendor/assets/javascripts/ckeditor/plugins/codemirror/js → app/assets/javascripts/ckeditor/plugins/codemirror/js/mode}/htmlmixed.js +0 -0
  87. data/{vendor/assets/javascripts/ckeditor/plugins/codemirror/js → app/assets/javascripts/ckeditor/plugins/codemirror/js/mode}/javascript.js +17 -6
  88. data/{vendor/assets/javascripts/ckeditor/plugins/codemirror/js → app/assets/javascripts/ckeditor/plugins/codemirror/js/mode}/xml.js +9 -5
  89. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/lang/en.js +4 -2
  90. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/lang/ru.js +0 -0
  91. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/plugin.js +146 -34
  92. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/theme/ambiance-mobile.css +0 -1
  93. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/theme/ambiance.css +0 -1
  94. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/theme/blackboard.css +0 -0
  95. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/theme/cobalt.css +0 -0
  96. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/theme/eclipse.css +1 -1
  97. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/theme/elegant.css +0 -0
  98. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/theme/erlang-dark.css +5 -5
  99. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/theme/lesser-dark.css +0 -0
  100. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/theme/monokai.css +0 -0
  101. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/theme/neat.css +0 -0
  102. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/theme/night.css +0 -0
  103. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/theme/rubyblue.css +0 -0
  104. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/theme/solarized.css +0 -0
  105. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/theme/twilight.css +0 -0
  106. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/theme/vibrant-ink.css +0 -0
  107. data/{vendor → app}/assets/javascripts/ckeditor/plugins/codemirror/theme/xq-dark.css +0 -0
  108. data/app/assets/javascripts/ckeditor/plugins/codemirror/theme/xq-light.css +43 -0
  109. data/{vendor → app}/assets/javascripts/ckeditor/plugins/colorbutton/icons/bgcolor.png +0 -0
  110. data/{vendor → app}/assets/javascripts/ckeditor/plugins/colorbutton/icons/textcolor.png +0 -0
  111. data/{vendor → app}/assets/javascripts/ckeditor/plugins/colorbutton/lang/en.js +0 -0
  112. data/{vendor → app}/assets/javascripts/ckeditor/plugins/colorbutton/lang/ru.js +0 -0
  113. data/{vendor → app}/assets/javascripts/ckeditor/plugins/colorbutton/plugin.js +6 -2
  114. data/{vendor → app}/assets/javascripts/ckeditor/plugins/colordialog/dialogs/colordialog.js +0 -0
  115. data/{vendor → app}/assets/javascripts/ckeditor/plugins/colordialog/lang/en.js +0 -0
  116. data/{vendor → app}/assets/javascripts/ckeditor/plugins/colordialog/lang/ru.js +0 -0
  117. data/{vendor → app}/assets/javascripts/ckeditor/plugins/colordialog/plugin.js +1 -1
  118. data/{vendor → app}/assets/javascripts/ckeditor/plugins/dialog/dialogDefinition.js +0 -0
  119. data/{vendor → app}/assets/javascripts/ckeditor/plugins/fakeobjects/images/spacer.gif +0 -0
  120. data/{vendor → app}/assets/javascripts/ckeditor/plugins/flash/dialogs/flash.js +10 -9
  121. data/{vendor → app}/assets/javascripts/ckeditor/plugins/flash/images/placeholder.png +0 -0
  122. data/{vendor → app}/assets/javascripts/ckeditor/plugins/font/lang/en.js +0 -0
  123. data/{vendor → app}/assets/javascripts/ckeditor/plugins/font/lang/ru.js +0 -0
  124. data/{vendor → app}/assets/javascripts/ckeditor/plugins/font/plugin.js +5 -2
  125. data/{vendor → app}/assets/javascripts/ckeditor/plugins/highslide/dialogs/hs.js +0 -0
  126. data/{vendor → app}/assets/javascripts/ckeditor/plugins/highslide/icon.png +0 -0
  127. data/{vendor → app}/assets/javascripts/ckeditor/plugins/highslide/lang/en.js +0 -0
  128. data/{vendor → app}/assets/javascripts/ckeditor/plugins/highslide/lang/ru.js +0 -0
  129. data/{vendor → app}/assets/javascripts/ckeditor/plugins/highslide/plugin.js +0 -0
  130. data/{vendor → app}/assets/javascripts/ckeditor/plugins/highslide/readme.txt +0 -0
  131. data/app/assets/javascripts/ckeditor/plugins/icons.png +0 -0
  132. data/{vendor → app}/assets/javascripts/ckeditor/plugins/iframedialog/plugin.js +0 -0
  133. data/app/assets/javascripts/ckeditor/plugins/image/dialogs/image.js +43 -0
  134. data/{vendor → app}/assets/javascripts/ckeditor/plugins/image/images/noimage.png +0 -0
  135. data/{vendor → app}/assets/javascripts/ckeditor/plugins/link/dialogs/anchor.js +0 -0
  136. data/{vendor → app}/assets/javascripts/ckeditor/plugins/link/dialogs/link.js +15 -15
  137. data/{vendor → app}/assets/javascripts/ckeditor/plugins/link/images/anchor.png +0 -0
  138. data/{vendor → app}/assets/javascripts/ckeditor/plugins/magicline/images/icon.png +0 -0
  139. data/{vendor → app}/assets/javascripts/ckeditor/plugins/mediaembed/images/icon.png +0 -0
  140. data/{vendor → app}/assets/javascripts/ckeditor/plugins/oembed/images/icon.png +0 -0
  141. data/app/assets/javascripts/ckeditor/plugins/oembed/libs/jquery.oembed.js +68 -0
  142. data/app/assets/javascripts/ckeditor/plugins/oembed/libs/jquery.oembed.min.js +68 -0
  143. data/{vendor → app}/assets/javascripts/ckeditor/plugins/panelbutton/plugin.js +0 -0
  144. data/app/assets/javascripts/ckeditor/plugins/pastefromword/filter/default.js +31 -0
  145. data/{vendor → app}/assets/javascripts/ckeditor/plugins/scayt/LICENSE.md +0 -0
  146. data/{vendor → app}/assets/javascripts/ckeditor/plugins/scayt/README.md +0 -0
  147. data/{vendor → app}/assets/javascripts/ckeditor/plugins/scayt/dialogs/options.js +0 -0
  148. data/{vendor → app}/assets/javascripts/ckeditor/plugins/scayt/dialogs/toolbar.css +0 -0
  149. data/{vendor → app}/assets/javascripts/ckeditor/plugins/specialchar/dialogs/lang/en.js +0 -0
  150. data/{vendor → app}/assets/javascripts/ckeditor/plugins/specialchar/dialogs/specialchar.js +0 -0
  151. data/app/assets/javascripts/ckeditor/plugins/table/dialogs/table.js +21 -0
  152. data/{vendor → app}/assets/javascripts/ckeditor/plugins/tabletools/dialogs/tableCell.js +0 -0
  153. data/{vendor → app}/assets/javascripts/ckeditor/plugins/wsc/LICENSE.md +0 -0
  154. data/{vendor → app}/assets/javascripts/ckeditor/plugins/wsc/README.md +0 -0
  155. data/{vendor → app}/assets/javascripts/ckeditor/plugins/wsc/dialogs/ciframe.html +0 -0
  156. data/{vendor → app}/assets/javascripts/ckeditor/plugins/wsc/dialogs/tmpFrameset.html +0 -0
  157. data/{vendor → app}/assets/javascripts/ckeditor/plugins/wsc/dialogs/wsc.css +0 -0
  158. data/{vendor → app}/assets/javascripts/ckeditor/plugins/wsc/dialogs/wsc.js +0 -0
  159. data/app/assets/javascripts/ckeditor/samples/ajax.html +82 -0
  160. data/app/assets/javascripts/ckeditor/samples/api.html +207 -0
  161. data/app/assets/javascripts/ckeditor/samples/appendto.html +57 -0
  162. data/app/assets/javascripts/ckeditor/samples/assets/inlineall/logo.png +0 -0
  163. data/app/assets/javascripts/ckeditor/samples/assets/outputxhtml/outputxhtml.css +204 -0
  164. data/app/assets/javascripts/ckeditor/samples/assets/posteddata.php +59 -0
  165. data/app/assets/javascripts/ckeditor/samples/assets/sample.css +3 -0
  166. data/app/assets/javascripts/ckeditor/samples/assets/sample.jpg +0 -0
  167. data/app/assets/javascripts/ckeditor/samples/assets/uilanguages/languages.js +7 -0
  168. data/app/assets/javascripts/ckeditor/samples/datafiltering.html +401 -0
  169. data/app/assets/javascripts/ckeditor/samples/divreplace.html +141 -0
  170. data/app/assets/javascripts/ckeditor/samples/index.html +125 -0
  171. data/app/assets/javascripts/ckeditor/samples/inlineall.html +311 -0
  172. data/app/assets/javascripts/ckeditor/samples/inlinebycode.html +122 -0
  173. data/app/assets/javascripts/ckeditor/samples/plugins/dialog/assets/my_dialog.js +48 -0
  174. data/app/assets/javascripts/ckeditor/samples/plugins/dialog/dialog.html +187 -0
  175. data/app/assets/javascripts/ckeditor/samples/plugins/enterkey/enterkey.html +103 -0
  176. data/app/assets/javascripts/ckeditor/samples/plugins/htmlwriter/assets/outputforflash/outputforflash.fla +0 -0
  177. data/app/assets/javascripts/ckeditor/samples/plugins/htmlwriter/assets/outputforflash/outputforflash.swf +0 -0
  178. data/app/assets/javascripts/ckeditor/samples/plugins/htmlwriter/assets/outputforflash/swfobject.js +18 -0
  179. data/app/assets/javascripts/ckeditor/samples/plugins/htmlwriter/outputforflash.html +280 -0
  180. data/app/assets/javascripts/ckeditor/samples/plugins/htmlwriter/outputhtml.html +221 -0
  181. data/app/assets/javascripts/ckeditor/samples/plugins/magicline/magicline.html +207 -0
  182. data/{vendor/assets/javascripts/ckeditor/plugins/stylesheetparser/samples → app/assets/javascripts/ckeditor/samples/plugins/stylesheetparser}/assets/sample.css +70 -70
  183. data/{vendor/assets/javascripts/ckeditor/plugins/stylesheetparser/samples → app/assets/javascripts/ckeditor/samples/plugins/stylesheetparser}/stylesheetparser.html +82 -82
  184. data/app/assets/javascripts/ckeditor/samples/plugins/toolbar/toolbar.html +232 -0
  185. data/app/assets/javascripts/ckeditor/samples/plugins/wysiwygarea/fullpage.html +77 -0
  186. data/app/assets/javascripts/ckeditor/samples/readonly.html +73 -0
  187. data/app/assets/javascripts/ckeditor/samples/replacebyclass.html +57 -0
  188. data/app/assets/javascripts/ckeditor/samples/replacebycode.html +56 -0
  189. data/app/assets/javascripts/ckeditor/samples/sample.css +339 -0
  190. data/app/assets/javascripts/ckeditor/samples/sample.js +33 -0
  191. data/app/assets/javascripts/ckeditor/samples/sample_posteddata.php +16 -0
  192. data/app/assets/javascripts/ckeditor/samples/tabindex.html +75 -0
  193. data/app/assets/javascripts/ckeditor/samples/uicolor.html +69 -0
  194. data/app/assets/javascripts/ckeditor/samples/uilanguages.html +119 -0
  195. data/app/assets/javascripts/ckeditor/samples/xhtmlstyle.html +231 -0
  196. data/{vendor → app}/assets/javascripts/ckeditor/skins/moono/dialog.css +0 -0
  197. data/{vendor → app}/assets/javascripts/ckeditor/skins/moono/dialog_ie.css +0 -0
  198. data/{vendor → app}/assets/javascripts/ckeditor/skins/moono/dialog_ie7.css +0 -0
  199. data/{vendor → app}/assets/javascripts/ckeditor/skins/moono/dialog_ie8.css +0 -0
  200. data/app/assets/javascripts/ckeditor/skins/moono/dialog_iequirks.css +5 -0
  201. data/{vendor → app}/assets/javascripts/ckeditor/skins/moono/dialog_opera.css +0 -0
  202. data/{vendor → app}/assets/javascripts/ckeditor/skins/moono/editor.css +1 -1
  203. data/{vendor/assets/javascripts/ckeditor/skins/moono/editor_ie.css → app/assets/javascripts/ckeditor/skins/moono/editor_gecko.css} +1 -1
  204. data/{vendor/assets/javascripts/ckeditor/skins/moono/editor_ie8.css → app/assets/javascripts/ckeditor/skins/moono/editor_ie.css} +1 -1
  205. data/{vendor → app}/assets/javascripts/ckeditor/skins/moono/editor_ie7.css +1 -1
  206. data/app/assets/javascripts/ckeditor/skins/moono/editor_ie8.css +5 -0
  207. data/{vendor/assets/javascripts/ckeditor/skins/moono/editor_gecko.css → app/assets/javascripts/ckeditor/skins/moono/editor_iequirks.css} +1 -1
  208. data/app/assets/javascripts/ckeditor/skins/moono/icons.png +0 -0
  209. data/{vendor → app}/assets/javascripts/ckeditor/skins/moono/images/arrow.png +0 -0
  210. data/{vendor → app}/assets/javascripts/ckeditor/skins/moono/images/close.png +0 -0
  211. data/{vendor → app}/assets/javascripts/ckeditor/skins/moono/images/mini.png +0 -0
  212. data/{vendor → app}/assets/javascripts/ckeditor/skins/moono/readme.md +0 -0
  213. data/{vendor → app}/assets/javascripts/ckeditor/styles.js +1 -2
  214. data/app/controllers/ckeditor/application_controller.rb +6 -12
  215. data/app/controllers/ckeditor/attachment_files_controller.rb +6 -2
  216. data/app/controllers/ckeditor/pictures_controller.rb +6 -2
  217. data/app/views/ckeditor/shared/_asset.html.erb +4 -4
  218. data/app/views/ckeditor/shared/_asset_tmpl.html.erb +1 -1
  219. data/lib/ckeditor.rb +91 -19
  220. data/lib/ckeditor/engine.rb +5 -8
  221. data/lib/ckeditor/helpers/controllers.rb +7 -3
  222. data/lib/ckeditor/helpers/form_builder.rb +1 -1
  223. data/lib/ckeditor/helpers/form_helper.rb +12 -15
  224. data/lib/ckeditor/helpers/view_helper.rb +1 -1
  225. data/lib/ckeditor/hooks/cancan.rb +46 -0
  226. data/lib/ckeditor/hooks/simple_form.rb +11 -0
  227. data/lib/ckeditor/orm/active_record.rb +1 -3
  228. data/lib/ckeditor/orm/base.rb +4 -0
  229. data/lib/ckeditor/orm/mongoid.rb +1 -3
  230. data/lib/ckeditor/utils.rb +25 -8
  231. data/lib/ckeditor/version.rb +2 -2
  232. data/lib/generators/ckeditor/install_generator.rb +2 -2
  233. data/lib/generators/ckeditor/templates/active_record/carrierwave/ckeditor/asset.rb +2 -2
  234. data/lib/generators/ckeditor/templates/active_record/carrierwave/ckeditor/attachment_file.rb +4 -4
  235. data/lib/generators/ckeditor/templates/active_record/carrierwave/ckeditor/picture.rb +4 -4
  236. data/lib/generators/ckeditor/templates/active_record/carrierwave/migration.rb +1 -1
  237. data/lib/generators/ckeditor/templates/active_record/paperclip/ckeditor/attachment_file.rb +4 -4
  238. data/lib/generators/ckeditor/templates/active_record/paperclip/ckeditor/picture.rb +8 -8
  239. data/lib/generators/ckeditor/templates/active_record/paperclip/migration.rb +6 -6
  240. data/lib/generators/ckeditor/templates/base/carrierwave/uploaders/ckeditor_attachment_file_uploader.rb +1 -7
  241. data/lib/generators/ckeditor/templates/base/carrierwave/uploaders/ckeditor_picture_uploader.rb +1 -7
  242. data/lib/generators/ckeditor/templates/base/dragonfly/initializer.rb +3 -3
  243. data/lib/generators/ckeditor/templates/ckeditor.rb +3 -0
  244. data/lib/generators/ckeditor/templates/mongoid/carrierwave/ckeditor/asset.rb +1 -1
  245. data/lib/generators/ckeditor/templates/mongoid/carrierwave/ckeditor/attachment_file.rb +4 -4
  246. data/lib/generators/ckeditor/templates/mongoid/carrierwave/ckeditor/picture.rb +4 -4
  247. data/test/dummy/app/views/posts/_form.html.erb +3 -3
  248. data/test/dummy/script/rails +0 -0
  249. data/test/functional/posts_controller_test.rb +3 -3
  250. metadata +346 -321
  251. data/vendor/assets/javascripts/ckeditor/ckeditor.js +0 -830
  252. data/vendor/assets/javascripts/ckeditor/filebrowser/stylesheets/uploader.css.sass +0 -102
  253. data/vendor/assets/javascripts/ckeditor/plugins/code/code/code.js +0 -48
  254. data/vendor/assets/javascripts/ckeditor/plugins/code/images/code.png +0 -0
  255. data/vendor/assets/javascripts/ckeditor/plugins/code/plugin.js +0 -17
  256. data/vendor/assets/javascripts/ckeditor/plugins/codemirror/css/codemirror.min.css +0 -1
  257. data/vendor/assets/javascripts/ckeditor/plugins/codemirror/js/addon/edit/closebrackets.js +0 -29
  258. data/vendor/assets/javascripts/ckeditor/plugins/codemirror/js/addon/edit/continuelist.js +0 -28
  259. data/vendor/assets/javascripts/ckeditor/plugins/codemirror/js/addon/foldcode/foldcode.js +0 -183
  260. data/vendor/assets/javascripts/ckeditor/plugins/codemirror/js/codemirror.addons.min.js +0 -1
  261. data/vendor/assets/javascripts/ckeditor/plugins/codemirror/js/codemirror.min.js +0 -1
  262. data/vendor/assets/javascripts/ckeditor/plugins/codemirror/js/codemirror.modes.min.js +0 -1
  263. data/vendor/assets/javascripts/ckeditor/plugins/codemirror/js/codemirror.search-addons.min.js +0 -1
  264. data/vendor/assets/javascripts/ckeditor/plugins/icons.png +0 -0
  265. data/vendor/assets/javascripts/ckeditor/plugins/image/dialogs/image.js +0 -41
  266. data/vendor/assets/javascripts/ckeditor/plugins/mediaembed/plugin.js +0 -67
  267. data/vendor/assets/javascripts/ckeditor/plugins/oembed/lang/de.js +0 -12
  268. data/vendor/assets/javascripts/ckeditor/plugins/oembed/lang/en.js +0 -12
  269. data/vendor/assets/javascripts/ckeditor/plugins/oembed/lang/fr.js +0 -14
  270. data/vendor/assets/javascripts/ckeditor/plugins/oembed/lang/nl.js +0 -12
  271. data/vendor/assets/javascripts/ckeditor/plugins/oembed/lang/ru.js +0 -12
  272. data/vendor/assets/javascripts/ckeditor/plugins/oembed/libs/jquery.oembed.js +0 -912
  273. data/vendor/assets/javascripts/ckeditor/plugins/oembed/libs/jquery.oembed.min.js +0 -1
  274. data/vendor/assets/javascripts/ckeditor/plugins/oembed/plugin.js +0 -102
  275. data/vendor/assets/javascripts/ckeditor/plugins/pastefromword/filter/default.js +0 -31
  276. data/vendor/assets/javascripts/ckeditor/plugins/specialchar/dialogs/lang/ru.js +0 -13
  277. data/vendor/assets/javascripts/ckeditor/plugins/stylesheetparser/plugin.js +0 -138
  278. data/vendor/assets/javascripts/ckeditor/plugins/table/dialogs/table.js +0 -20
  279. data/vendor/assets/javascripts/ckeditor/skins/moono/dialog_iequirks.css +0 -689
  280. data/vendor/assets/javascripts/ckeditor/skins/moono/editor_iequirks.css +0 -1245
  281. data/vendor/assets/javascripts/ckeditor/skins/moono/icons.png +0 -0
@@ -17,16 +17,15 @@
17
17
  this.matches = function(reverse, pos) {
18
18
  if (reverse) {
19
19
  query.lastIndex = 0;
20
- var line = cm.getLine(pos.line).slice(0, pos.ch), match = query.exec(line), start = 0;
21
- while (match) {
22
- start += match.index + 1;
23
- line = line.slice(start);
24
- query.lastIndex = 0;
25
- var newmatch = query.exec(line);
26
- if (newmatch) match = newmatch;
27
- else break;
20
+ var line = cm.getLine(pos.line).slice(0, pos.ch), cutOff = 0, match, start;
21
+ for (;;) {
22
+ query.lastIndex = cutOff;
23
+ var newMatch = query.exec(line);
24
+ if (!newMatch) break;
25
+ match = newMatch;
26
+ start = match.index;
27
+ cutOff = match.index + 1;
28
28
  }
29
- start--;
30
29
  } else {
31
30
  query.lastIndex = pos.ch;
32
31
  var line = cm.getLine(pos.line), match = query.exec(line),
@@ -0,0 +1 @@
1
+ (function(){function i(n){for(var r={name:"autoCloseBrackets",Backspace:function(t){if(t.somethingSelected())return CodeMirror.Pass;var i=t.getCursor(),r=t.getLine(i.line);if(i.ch&&i.ch<r.length&&n.indexOf(r.slice(i.ch-1,i.ch+1))%2==0)t.replaceRange("",CodeMirror.Pos(i.line,i.ch-1),CodeMirror.Pos(i.line,i.ch+1));else return CodeMirror.Pass}},u=[],i=0;i<n.length;i+=2)(function(n,i){function e(t){var r=t.getSelection();t.replaceSelection(n+r+i)}function f(n){var t=n.getCursor(),r=n.getRange(t,CodeMirror.Pos(t.line,t.ch+1));if(r!=i||n.somethingSelected())return CodeMirror.Pass;n.execCommand("goCharRight")}n!=i&&u.push(i),r["'"+n+"'"]=function(r){if(r.somethingSelected())return e(r);if(n!=i||f(r)==CodeMirror.Pass){var o=r.getCursor(),s=CodeMirror.Pos(o.line,o.ch+1),h=r.getLine(o.line),c=h.charAt(o.ch);if(h.length==o.ch||u.indexOf(c)>=0||t.test(c))r.replaceSelection(n+i,{head:s,anchor:s});else return CodeMirror.Pass}},n!=i&&(r["'"+i+"'"]=f)})(n.charAt(i),n.charAt(i+1));return r}var n="()[]{}''\"\"",t=/\s/;CodeMirror.defineOption("autoCloseBrackets",!1,function(t,r,u){var f=u&&u!=CodeMirror.Init;r&&!f?t.addKeyMap(i(typeof r=="string"?r:n)):!r&&f&&t.removeKeyMap("autoCloseBrackets")})})(),function(){function n(n,u){var e=n.getCursor(),o=n.getTokenAt(e),l=CodeMirror.innerMode(n.getMode(),o.state),s=l.state,a,c,v,f;if(l.mode.name!="xml")return CodeMirror.Pass;var h=n.getOption("autoCloseTags"),y=l.mode.configuration=="html",p=typeof h=="object"&&h.dontCloseTags||y&&i,w=typeof h=="object"&&h.indentTags||y&&r;if(u==">"&&s.tagName){if(f=s.tagName,o.end>e.ch&&(f=f.slice(0,f.length-o.end+e.ch)),a=f.toLowerCase(),o.type=="tag"&&s.type=="closeTag"||o.string.indexOf("/")>-1||p&&t(p,a)>-1)return CodeMirror.Pass;c=w&&t(w,a)>-1,v=c?CodeMirror.Pos(e.line+1,0):CodeMirror.Pos(e.line,e.ch+1),n.replaceSelection(">"+(c?"\n\n":"")+"<\/"+f+">",{head:v,anchor:v}),c&&(n.indentLine(e.line+1),n.indentLine(e.line+2));return}if(u=="/"&&o.string=="<"){f=s.context&&s.context.tagName,f&&n.replaceSelection("/"+f+">","end");return}return CodeMirror.Pass}function t(n,t){if(n.indexOf)return n.indexOf(t);for(var i=0,r=n.length;i<r;++i)if(n[i]==t)return i;return-1}CodeMirror.defineOption("autoCloseTags",!1,function(t,i,r){if(i&&(r==CodeMirror.Init||!r)){var u={name:"autoCloseTags"};(typeof i!="object"||i.whenClosing)&&(u["'/'"]=function(t){return n(t,"/")}),(typeof i!="object"||i.whenOpening)&&(u["'>'"]=function(t){return n(t,">")}),t.addKeyMap(u)}else!i&&r!=CodeMirror.Init&&r&&t.removeKeyMap("autoCloseTags")});var i=["area","base","br","col","command","embed","hr","img","input","keygen","link","meta","param","source","track","wbr"],r=["applet","blockquote","body","button","div","dl","fieldset","form","frameset","h1","h2","h3","h4","h5","h6","head","html","iframe","layer","legend","object","ol","p","select","table","ul"]}(),function(){function i(n){var e=n.getCursor(),t=n.getTokenAt(e),i=CodeMirror.innerMode(n.getMode(),t.state).mode,r,o,u,f,s;if(t.type=="comment"&&i.blockCommentStart&&(o=t.string.indexOf(i.blockCommentEnd),u=n.getRange(CodeMirror.Pos(e.line,0),CodeMirror.Pos(e.line,t.end)),o==-1||o!=t.string.length-i.blockCommentEnd.length))if(t.string.indexOf(i.blockCommentStart)==0){if(r=u.slice(0,t.start),!/^\s*$/.test(r))for(r="",s=0;s<t.start;++s)r+=" "}else(f=u.indexOf(i.blockCommentContinue))!=-1&&f+i.blockCommentContinue.length>t.start&&/^\s*$/.test(u.slice(0,f))&&(r=u.slice(0,f));if(r!=null)n.replaceSelection("\n"+r+i.blockCommentContinue,"end");else return CodeMirror.Pass}for(var t=["clike","css","javascript"],n=0;n<t.length;++n)CodeMirror.extendMode(t[n],{blockCommentStart:"/*",blockCommentEnd:"*/",blockCommentContinue:" * "});CodeMirror.defineOption("continueComments",null,function(n,t,r){r&&r!=CodeMirror.Init&&n.removeKeyMap("continueComment");var u={name:"continueComment"};u[typeof t=="string"?t:"Enter"]=i,n.addKeyMap(u)})}(),function(){function u(t){function a(r,u,f){var e,a,s,l;if(r.text)for(e=o?0:r.text.length-1,a=o?r.text.length:-1,f!=null&&(e=f+h);e!=a;e+=h)if(s=r.text.charAt(e),p.test(s)&&t.getTokenAt(n(u,e+1)).type==y)if(l=i[s],l.charAt(1)==">"==o)c.push(s);else{if(c.pop()!=l.charAt(0))return{pos:e,match:!1};if(!c.length)return{pos:e,match:!0}}}var f=t.getCursor(),s=t.getLineHandle(f.line),u=f.ch-1,l=u>=0&&i[s.text.charAt(u)]||i[s.text.charAt(++u)],r,e,v;if(!l)return null;var o=l.charAt(1)==">",h=o?1:-1,y=t.getTokenAt(n(f.line,u+1)).type,c=[s.text.charAt(u)],p=/[(){}[\]]/;for(r=f.line,v=o?Math.min(r+100,t.lineCount()):Math.max(-1,r-100);r!=v;r+=h)if(e=r==f.line?a(s,r,u):a(t.getLineHandle(r),r),e)break;return{from:n(f.line,u),to:e&&n(r,e.pos),match:e&&e.match}}function f(t,i){var f=u(t),e;if(f&&!(t.getLine(f.from.line).length>r)&&(!f.to||!(t.getLine(f.to.line).length>r))){var s=f.match?"CodeMirror-matchingbracket":"CodeMirror-nonmatchingbracket",c=t.markText(f.from,n(f.from.line,f.from.ch+1),{className:s}),h=f.to&&t.markText(f.to,n(f.to.line,f.to.ch+1),{className:s});if(o&&t.state.focused&&t.display.input.focus(),e=function(){t.operation(function(){c.clear(),h&&h.clear()})},i)setTimeout(e,800);else return e}}function e(n){n.operation(function(){t&&(t(),t=null),n.somethingSelected()||(t=f(n,!1))})}var o=/MSIE \d/.test(navigator.userAgent)&&(document.documentMode==null||document.documentMode<8),n=CodeMirror.Pos,r=1e3,i={"(":")>",")":"(<","[":"]>","]":"[<","{":"}>","}":"{<"},t=null;CodeMirror.defineOption("matchBrackets",!1,function(n,t){if(t)n.on("cursorActivity",e);else n.off("cursorActivity",e)}),CodeMirror.defineExtension("matchBrackets",function(){f(this,!0)}),CodeMirror.defineExtension("findMatchingBracket",function(){return u(this)})}(),CodeMirror.newFoldFunction=function(n,t){if(t==null&&(t="↔"),typeof t=="string"){var i=document.createTextNode(t);t=document.createElement("span"),t.appendChild(i),t.className="CodeMirror-foldmarker"}return function(i,r){var u,e,o,f,s,h;if(typeof r=="number"&&(r=CodeMirror.Pos(r,0)),u=n(i,r),u){for(e=i.findMarksAt(u.from),o=0,f=0;f<e.length;++f)e[f].__isFold&&(++o,e[f].clear());if(!o){s=t.cloneNode(!0);CodeMirror.on(s,"mousedown",function(){h.clear()});h=i.markText(u.from,u.to,{replacedWith:s,clearOnEnter:!0,__isFold:!0})}}}},CodeMirror.braceRangeFinder=function(n,t){for(var f=t.line,l=n.getLine(f),y=l.length,s,a,e,v,p,h,w,r,u,i,o,c;;){if(e=l.lastIndexOf("{",y),e<t.ch)break;if(a=n.getTokenAt(CodeMirror.Pos(f,e+1)).type,!/^(comment|string)/.test(a)){s=e;break}y=e-1}if(s!=null&&!(l.lastIndexOf("}")>s)){v=1,p=n.lineCount();n:for(r=f+1;r<p;++r)for(u=n.getLine(r),i=0;;){if(o=u.indexOf("{",i),c=u.indexOf("}",i),o<0&&(o=u.length),c<0&&(c=u.length),i=Math.min(o,c),i==u.length)break;if(n.getTokenAt(CodeMirror.Pos(r,i+1)).type==a)if(i==o)++v;else if(!--v){h=r,w=i;break n}++i}if(h!=null&&h!=f+1)return{from:CodeMirror.Pos(f,s+1),to:CodeMirror.Pos(h,w)}}},CodeMirror.tagRangeFinder=function(){var n="A-Z_a-z\\u00C0-\\u00D6\\u00D8-\\u00F6\\u00F8-\\u02FF\\u0370-\\u037D\\u037F-\\u1FFF\\u200C-\\u200D\\u2070-\\u218F\\u2C00-\\u2FEF\\u3001-\\uD7FF\\uF900-\\uFDCF\\uFDF0-\\uFFFD",i=n+"-:.0-9\\u00B7\\u0300-\\u036F\\u203F-\\u2040",t=new RegExp("<(/?)(["+n+"]["+i+"]*)","g");return function(n,i){function l(){if(!(e>=n.lastLine()))return r=0,o=n.getLine(++e),!0}function a(){for(var n,t,i;;){if(n=o.indexOf(">",r),n==-1)if(l())continue;else return;return t=o.lastIndexOf("/",n),i=t>-1&&/^\s*$/.test(o.slice(t+1,n)),r=n+1,i?"selfClose":"regular"}}function v(){for(;;){t.lastIndex=r;var n=t.exec(o);if(!n)if(l())continue;else return;return r=n.index+n[0].length,n}}for(var e=i.line,r=i.ch,o=n.getLine(e),u=[],y,h,c,s;;){if(h=v(),!h||e!=i.line||!(c=a()))return;if(!h[1]&&c!="selfClose"){u.push(h[2]),y=r;break}}for(;;){var f=v(),c,p=e,w=r-(f?f[0].length:0);if(!f||!(c=a()))return;if(c!="selfClose")if(f[1]){for(s=u.length-1;s>=0;--s)if(u[s]==f[2]){u.length=s;break}if(!u.length)return{from:CodeMirror.Pos(i.line,y),to:CodeMirror.Pos(p,w)}}else u.push(f[2])}}}(),function(){CodeMirror.defineExtension("autoFormatAll",function(n,t){function v(){h+="\n",e=!0,++a}for(var r=this,f=r.getMode(),o=r.getRange(n,t).split("\n"),s=CodeMirror.copyState(f,r.getTokenAt(n).state),y=r.getOption("tabSize"),h="",a=0,e=n.ch==0,i,u=0;u<o.length;++u){for(i=new CodeMirror.StringStream(o[u],y);!i.eol();){var c=CodeMirror.innerMode(f,s),p=f.token(i,s),l=i.current();i.start=i.pos,(!e||/\S/.test(l))&&(h+=l,e=!1),!e&&c.mode.newlineAfterToken&&c.mode.newlineAfterToken(p,l,i.string.slice(i.pos)||o[u+1]||"",c.state)&&v()}!i.pos&&f.blankLine&&f.blankLine(s),!e&&u<o.length-1&&v()}r.operation(function(){r.replaceRange(h,n,t);for(var i=n.line+1,u=n.line+a;i<=u;++i)r.indentLine(i,"smart");r.setCursor({line:0,ch:0})})})}(),function(){CodeMirror.extendMode("css",{commentStart:"/*",commentEnd:"*/",newlineAfterToken:function(n,t){return/^[;{}]$/.test(t)}}),CodeMirror.extendMode("javascript",{commentStart:"/*",commentEnd:"*/",newlineAfterToken:function(n,t,i,r){return this.jsonMode?/^[\[,{]$/.test(t)||/^}/.test(i):t==";"&&r.lexical&&r.lexical.type==")"?!1:/^[;{}]$/.test(t)&&!/^;/.test(i)}});var n=/^(a|abbr|acronym|area|base|bdo|big|br|button|caption|cite|code|col|colgroup|dd|del|dfn|em|frame|hr|iframe|img|input|ins|kbd|label|legend|link|map|object|optgroup|option|param|q|samp|script|select|small|span|strong|sub|sup|textarea|tt|var)$/;CodeMirror.extendMode("xml",{commentStart:"<!--",commentEnd:"-->",newlineAfterToken:function(t,i,r,u){var f=!1;return this.configuration=="html"&&(f=u.context?n.test(u.context.tagName):!1),!f&&(t=="tag"&&/>$/.test(i)&&u.context||/^</.test(r))}}),CodeMirror.defineExtension("commentRange",function(n,t,i){var r=this,u=CodeMirror.innerMode(r.getMode(),r.getTokenAt(t).state).mode;r.operation(function(){if(n)r.replaceRange(u.commentEnd,i),r.replaceRange(u.commentStart,t),t.line==i.line&&t.ch==i.ch&&r.setCursor(t.line,t.ch+u.commentStart.length);else{var f=r.getRange(t,i),e=f.indexOf(u.commentStart),o=f.lastIndexOf(u.commentEnd);e>-1&&o>-1&&o>e&&(f=f.substr(0,e)+f.substring(e+u.commentStart.length,o)+f.substr(o+u.commentEnd.length)),r.replaceRange(f,t,i)}})}),CodeMirror.defineExtension("autoIndentRange",function(n,t){var i=this;this.operation(function(){for(var r=n.line;r<=t.line;r++)i.indentLine(r,"smart")})}),CodeMirror.defineExtension("autoFormatRange",function(n,t){function v(){h+="\n",e=!0,++a}for(var i=this,f=i.getMode(),o=i.getRange(n,t).split("\n"),s=CodeMirror.copyState(f,i.getTokenAt(n).state),y=i.getOption("tabSize"),h="",a=0,e=n.ch==0,r,u=0;u<o.length;++u){for(r=new CodeMirror.StringStream(o[u],y);!r.eol();){var c=CodeMirror.innerMode(f,s),p=f.token(r,s),l=r.current();r.start=r.pos,(!e||/\S/.test(l))&&(h+=l,e=!1),!e&&c.mode.newlineAfterToken&&c.mode.newlineAfterToken(p,l,r.string.slice(r.pos)||o[u+1]||"",c.state)&&v()}!r.pos&&f.blankLine&&f.blankLine(s),!e&&u<o.length-1&&v()}i.operation(function(){i.replaceRange(h,n,t);for(var r=n.line+1,u=n.line+a;r<=u;++r)i.indentLine(r,"smart");i.setSelection(n,i.getCursor(!1))})})}(),function(){function r(n){this.minChars=typeof n=="object"&&n.minChars||t,this.style=typeof n=="object"&&n.style||i,this.overlay=null}function n(n){n.operation(function(){var t=n._matchHighlightState,i;(t.overlay&&(n.removeOverlay(t.overlay),t.overlay=null),n.somethingSelected())&&((i=n.getSelection().replace(/^\s+|\s+$/g,""),i.length<t.minChars)||n.addOverlay(t.overlay=u(i,t.style)))})}function u(n,t){return{token:function(i){if(i.match(n))return t;i.next(),i.skipTo(n.charAt(0))||i.skipToEnd()}}}var t=2,i="matchhighlight";CodeMirror.defineOption("highlightSelectionMatches",!1,function(t,i,u){var e=u&&u!=CodeMirror.Init,f;if(i&&!e){t._matchHighlightState=new r(i);t.on("cursorActivity",n)}else!i&&e&&(f=t._matchHighlightState.overlay,f&&t.removeOverlay(f),t._matchHighlightState=null,t.off("cursorActivity",n))})}()
@@ -1,4 +1,4 @@
1
- // CodeMirror version 3.1
1
+ // CodeMirror version 3.11
2
2
  //
3
3
  // CodeMirror is the only global var we claim
4
4
  window.CodeMirror = (function() {
@@ -41,7 +41,7 @@ window.CodeMirror = (function() {
41
41
 
42
42
  function CodeMirror(place, options) {
43
43
  if (!(this instanceof CodeMirror)) return new CodeMirror(place, options);
44
-
44
+
45
45
  this.options = options = options || {};
46
46
  // Determine effective options based on given values and defaults.
47
47
  for (var opt in defaults) if (!options.hasOwnProperty(opt) && defaults.hasOwnProperty(opt))
@@ -93,10 +93,14 @@ window.CodeMirror = (function() {
93
93
 
94
94
  function makeDisplay(place, docStart) {
95
95
  var d = {};
96
+
96
97
  var input = d.input = elt("textarea", null, null, "position: absolute; padding: 0; width: 1px; height: 1em; outline: none;");
97
98
  if (webkit) input.style.width = "1000px";
98
99
  else input.setAttribute("wrap", "off");
100
+ // if border: 0; -- iOS fails to open keyboard (issue #1287)
101
+ if (ios) input.style.border = "1px solid black";
99
102
  input.setAttribute("autocorrect", "off"); input.setAttribute("autocapitalize", "off");
103
+
100
104
  // Wraps and hides input textarea
101
105
  d.inputDiv = elt("div", [input], null, "overflow: hidden; position: relative; width: 3px; height: 0px;");
102
106
  // The actual fake scrollbars.
@@ -120,7 +124,7 @@ window.CodeMirror = (function() {
120
124
  // Set to the height of the text, causes scrolling
121
125
  d.sizer = elt("div", [d.mover], "CodeMirror-sizer");
122
126
  // D is needed because behavior of elts with overflow: auto and padding is inconsistent across browsers
123
- d.heightForcer = elt("div", "\u00a0", null, "position: absolute; height: " + scrollerCutOff + "px");
127
+ d.heightForcer = elt("div", null, null, "position: absolute; height: " + scrollerCutOff + "px; width: 1px;");
124
128
  // Will contain the gutters, if any
125
129
  d.gutters = elt("div", null, "CodeMirror-gutters");
126
130
  d.lineGutter = null;
@@ -181,7 +185,7 @@ window.CodeMirror = (function() {
181
185
 
182
186
  // Used for measuring wheel scrolling granularity
183
187
  d.wheelDX = d.wheelDY = d.wheelStartX = d.wheelStartY = null;
184
-
188
+
185
189
  return d;
186
190
  }
187
191
 
@@ -318,7 +322,7 @@ window.CodeMirror = (function() {
318
322
  // Re-synchronize the fake scrollbars with the actual size of the
319
323
  // content. Optionally force a scrollTop.
320
324
  function updateScrollbars(d /* display */, docHeight) {
321
- var totalHeight = docHeight + 2 * paddingTop(d);
325
+ var totalHeight = docHeight + paddingVert(d);
322
326
  d.sizer.style.minHeight = d.heightForcer.style.top = totalHeight + "px";
323
327
  var scrollHeight = Math.max(totalHeight, d.scroller.scrollHeight);
324
328
  var needsH = d.scroller.scrollWidth > d.scroller.clientWidth;
@@ -326,7 +330,7 @@ window.CodeMirror = (function() {
326
330
  if (needsV) {
327
331
  d.scrollbarV.style.display = "block";
328
332
  d.scrollbarV.style.bottom = needsH ? scrollbarWidth(d.measure) + "px" : "0";
329
- d.scrollbarV.firstChild.style.height =
333
+ d.scrollbarV.firstChild.style.height =
330
334
  (scrollHeight - d.scroller.clientHeight + d.scrollbarV.clientHeight) + "px";
331
335
  } else d.scrollbarV.style.display = "";
332
336
  if (needsH) {
@@ -636,7 +640,7 @@ window.CodeMirror = (function() {
636
640
  // Lines with gutter elements, widgets or a background class need
637
641
  // to be wrapped again, and have the extra elements added to the
638
642
  // wrapper div
639
-
643
+
640
644
  if (reuse) {
641
645
  reuse.alignable = null;
642
646
  var isOk = true, widgetsSeen = 0;
@@ -669,7 +673,7 @@ window.CodeMirror = (function() {
669
673
  }
670
674
  // Kludge to make sure the styled element lies behind the selection (by z-index)
671
675
  if (line.bgClass)
672
- wrap.insertBefore(elt("div", "\u00a0", line.bgClass + " CodeMirror-linebackground"), wrap.firstChild);
676
+ wrap.insertBefore(elt("div", null, line.bgClass + " CodeMirror-linebackground"), wrap.firstChild);
673
677
  if (cm.options.lineNumbers || markers) {
674
678
  var gutterWrap = wrap.insertBefore(elt("div", null, null, "position: absolute; left: " +
675
679
  (cm.options.fixedGutter ? dims.fixedPos : -dims.gutterTotalWidth) + "px"),
@@ -929,8 +933,9 @@ window.CodeMirror = (function() {
929
933
  }
930
934
 
931
935
  // POSITION MEASUREMENT
932
-
936
+
933
937
  function paddingTop(display) {return display.lineSpace.offsetTop;}
938
+ function paddingVert(display) {return display.mover.offsetHeight - display.lineSpace.offsetHeight;}
934
939
  function paddingLeft(display) {
935
940
  var e = removeChildrenAndAdd(display.measure, elt("pre", null, null, "text-align: left")).appendChild(elt("span", "x"));
936
941
  return e.offsetLeft;
@@ -939,7 +944,7 @@ window.CodeMirror = (function() {
939
944
  function measureChar(cm, line, ch, data) {
940
945
  var dir = -1;
941
946
  data = data || measureLine(cm, line);
942
-
947
+
943
948
  for (var pos = ch;; pos += dir) {
944
949
  var r = data[pos];
945
950
  if (r) break;
@@ -950,24 +955,30 @@ window.CodeMirror = (function() {
950
955
  top: r.top, bottom: r.bottom};
951
956
  }
952
957
 
953
- function measureLine(cm, line) {
954
- // First look in the cache
955
- var display = cm.display, cache = cm.display.measureLineCache;
958
+ function findCachedMeasurement(cm, line) {
959
+ var cache = cm.display.measureLineCache;
956
960
  for (var i = 0; i < cache.length; ++i) {
957
961
  var memo = cache[i];
958
962
  if (memo.text == line.text && memo.markedSpans == line.markedSpans &&
959
- display.scroller.clientWidth == memo.width &&
963
+ cm.display.scroller.clientWidth == memo.width &&
960
964
  memo.classes == line.textClass + "|" + line.bgClass + "|" + line.wrapClass)
961
965
  return memo.measure;
962
966
  }
963
-
964
- var measure = measureLineInner(cm, line);
965
- // Store result in the cache
966
- var memo = {text: line.text, width: display.scroller.clientWidth,
967
- markedSpans: line.markedSpans, measure: measure,
968
- classes: line.textClass + "|" + line.bgClass + "|" + line.wrapClass};
969
- if (cache.length == 16) cache[++display.measureLineCachePos % 16] = memo;
970
- else cache.push(memo);
967
+ }
968
+
969
+ function measureLine(cm, line) {
970
+ // First look in the cache
971
+ var measure = findCachedMeasurement(cm, line);
972
+ if (!measure) {
973
+ // Failing that, recompute and store result in cache
974
+ measure = measureLineInner(cm, line);
975
+ var cache = cm.display.measureLineCache;
976
+ var memo = {text: line.text, width: cm.display.scroller.clientWidth,
977
+ markedSpans: line.markedSpans, measure: measure,
978
+ classes: line.textClass + "|" + line.bgClass + "|" + line.wrapClass};
979
+ if (cache.length == 16) cache[++cm.display.measureLineCachePos % 16] = memo;
980
+ else cache.push(memo);
981
+ }
971
982
  return measure;
972
983
  }
973
984
 
@@ -1032,15 +1043,25 @@ window.CodeMirror = (function() {
1032
1043
  var vr = cur.top;
1033
1044
  cur.top = vranges[vr]; cur.bottom = vranges[vr+1];
1034
1045
  }
1035
- if (!cm.options.lineWrapping) {
1036
- var last = pre.lastChild;
1037
- if (last.nodeType == 3) last = pre.appendChild(elt("span", "\u200b"));
1038
- data.width = getRect(last).right - outer.left;
1039
- }
1040
1046
 
1041
1047
  return data;
1042
1048
  }
1043
1049
 
1050
+ function measureLineWidth(cm, line) {
1051
+ var hasBadSpan = false;
1052
+ if (line.markedSpans) for (var i = 0; i < line.markedSpans; ++i) {
1053
+ var sp = line.markedSpans[i];
1054
+ if (sp.collapsed && (sp.to == null || sp.to == line.text.length)) hasBadSpan = true;
1055
+ }
1056
+ var cached = !hasBadSpan && findCachedMeasurement(cm, line);
1057
+ if (cached) return measureChar(cm, line, line.text.length, cached).right;
1058
+
1059
+ var pre = lineContent(cm, line);
1060
+ var end = pre.appendChild(zeroWidthElement(cm.display.measure));
1061
+ removeChildrenAndAdd(cm.display.measure, pre);
1062
+ return getRect(end).right - getRect(cm.display.lineDiv).left;
1063
+ }
1064
+
1044
1065
  function clearCaches(cm) {
1045
1066
  cm.display.measureLineCache.length = cm.display.measureLineCachePos = 0;
1046
1067
  cm.display.cachedCharWidth = cm.display.cachedTextHeight = null;
@@ -1068,6 +1089,26 @@ window.CodeMirror = (function() {
1068
1089
  return rect;
1069
1090
  }
1070
1091
 
1092
+ // Context may be "window", "page", "div", or "local"/null
1093
+ // Result is in local coords
1094
+ function fromCoordSystem(cm, coords, context) {
1095
+ if (context == "div") return coords;
1096
+ var left = coords.left, top = coords.top;
1097
+ if (context == "page") {
1098
+ left -= window.pageXOffset || (document.documentElement || document.body).scrollLeft;
1099
+ top -= window.pageYOffset || (document.documentElement || document.body).scrollTop;
1100
+ }
1101
+ var lineSpaceBox = getRect(cm.display.lineSpace);
1102
+ left -= lineSpaceBox.left;
1103
+ top -= lineSpaceBox.top;
1104
+ if (context == "local" || !context) {
1105
+ var editorBox = getRect(cm.display.wrapper);
1106
+ left -= editorBox.left;
1107
+ top -= editorBox.top;
1108
+ }
1109
+ return {left: left, top: top};
1110
+ }
1111
+
1071
1112
  function charCoords(cm, pos, context, lineObj) {
1072
1113
  if (!lineObj) lineObj = getLine(cm.doc, pos.line);
1073
1114
  return intoCoordSystem(cm, lineObj, measureChar(cm, lineObj, pos.ch), context);
@@ -1139,15 +1180,15 @@ window.CodeMirror = (function() {
1139
1180
 
1140
1181
  function coordsCharInner(cm, lineObj, lineNo, x, y) {
1141
1182
  var innerOff = y - heightAtLine(cm, lineObj);
1142
- var wrongLine = false, cWidth = cm.display.wrapper.clientWidth;
1183
+ var wrongLine = false, adjust = 2 * cm.display.wrapper.clientWidth;
1143
1184
  var measurement = measureLine(cm, lineObj);
1144
1185
 
1145
1186
  function getX(ch) {
1146
1187
  var sp = cursorCoords(cm, Pos(lineNo, ch), "line",
1147
1188
  lineObj, measurement);
1148
1189
  wrongLine = true;
1149
- if (innerOff > sp.bottom) return Math.max(0, sp.left - cWidth);
1150
- else if (innerOff < sp.top) return sp.left + cWidth;
1190
+ if (innerOff > sp.bottom) return sp.left - adjust;
1191
+ else if (innerOff < sp.top) return sp.left + adjust;
1151
1192
  else wrongLine = false;
1152
1193
  return sp.left;
1153
1194
  }
@@ -1237,7 +1278,7 @@ window.CodeMirror = (function() {
1237
1278
 
1238
1279
  if (op.updateMaxLine) computeMaxLength(cm);
1239
1280
  if (display.maxLineChanged && !cm.options.lineWrapping) {
1240
- var width = measureLine(cm, display.maxLine).width;
1281
+ var width = measureLineWidth(cm, display.maxLine);
1241
1282
  display.sizer.style.minWidth = Math.max(0, width + 3 + scrollerCutOff) + "px";
1242
1283
  display.maxLineChanged = false;
1243
1284
  var maxScrollLeft = Math.max(0, display.sizer.offsetLeft + display.sizer.offsetWidth - display.scroller.clientWidth);
@@ -1251,8 +1292,10 @@ window.CodeMirror = (function() {
1251
1292
  var coords = cursorCoords(cm, doc.sel.head);
1252
1293
  newScrollPos = calculateScrollPos(cm, coords.left, coords.top, coords.left, coords.bottom);
1253
1294
  }
1254
- if (op.changes.length || newScrollPos && newScrollPos.scrollTop != null)
1295
+ if (op.changes.length || newScrollPos && newScrollPos.scrollTop != null) {
1255
1296
  updated = updateDisplay(cm, op.changes, newScrollPos && newScrollPos.scrollTop);
1297
+ if (cm.display.scroller.offsetHeight) cm.doc.scrollTop = cm.display.scroller.scrollTop;
1298
+ }
1256
1299
  if (!updated && op.selectionChanged) updateSelection(cm);
1257
1300
  if (op.updateScrollPos) {
1258
1301
  display.scroller.scrollTop = display.scrollbarV.scrollTop = doc.scrollTop = newScrollPos.scrollTop;
@@ -1367,9 +1410,9 @@ window.CodeMirror = (function() {
1367
1410
  var updateInput = cm.curOp.updateInput;
1368
1411
  makeChange(cm.doc, {from: from, to: to, text: splitLines(text.slice(same)),
1369
1412
  origin: cm.state.pasteIncoming ? "paste" : "+input"}, "end");
1370
-
1413
+
1371
1414
  cm.curOp.updateInput = updateInput;
1372
- if (text.length > 1000) input.value = cm.display.prevInput = "";
1415
+ if (text.length > 1000 || text.indexOf("\n") > -1) input.value = cm.display.prevInput = "";
1373
1416
  else cm.display.prevInput = text;
1374
1417
  if (withOp) endOperation(cm);
1375
1418
  cm.state.pasteIncoming = false;
@@ -1413,15 +1456,17 @@ window.CodeMirror = (function() {
1413
1456
  if (!captureMiddleClick) on(d.scroller, "contextmenu", function(e) {onContextMenu(cm, e);});
1414
1457
 
1415
1458
  on(d.scroller, "scroll", function() {
1416
- setScrollTop(cm, d.scroller.scrollTop);
1417
- setScrollLeft(cm, d.scroller.scrollLeft, true);
1418
- signal(cm, "scroll", cm);
1459
+ if (d.scroller.clientHeight) {
1460
+ setScrollTop(cm, d.scroller.scrollTop);
1461
+ setScrollLeft(cm, d.scroller.scrollLeft, true);
1462
+ signal(cm, "scroll", cm);
1463
+ }
1419
1464
  });
1420
1465
  on(d.scrollbarV, "scroll", function() {
1421
- setScrollTop(cm, d.scrollbarV.scrollTop);
1466
+ if (d.scroller.clientHeight) setScrollTop(cm, d.scrollbarV.scrollTop);
1422
1467
  });
1423
1468
  on(d.scrollbarH, "scroll", function() {
1424
- setScrollLeft(cm, d.scrollbarH.scrollLeft);
1469
+ if (d.scroller.clientHeight) setScrollLeft(cm, d.scrollbarH.scrollLeft);
1425
1470
  });
1426
1471
 
1427
1472
  on(d.scroller, "mousewheel", function(e){onScrollWheel(cm, e);});
@@ -1447,7 +1492,7 @@ window.CodeMirror = (function() {
1447
1492
  for (var p = d.wrapper.parentNode; p && p != document.body; p = p.parentNode) {}
1448
1493
  if (p) setTimeout(unregister, 5000);
1449
1494
  else off(window, "resize", onResize);
1450
- }
1495
+ }
1451
1496
  setTimeout(unregister, 5000);
1452
1497
 
1453
1498
  on(d.input, "keyup", operation(cm, function(e) {
@@ -1472,7 +1517,7 @@ window.CodeMirror = (function() {
1472
1517
  }
1473
1518
  on(d.scroller, "paste", function(e){
1474
1519
  if (eventInWidget(d, e)) return;
1475
- focusInput(cm);
1520
+ focusInput(cm);
1476
1521
  fastPoll(cm);
1477
1522
  });
1478
1523
  on(d.input, "paste", function() {
@@ -1674,7 +1719,7 @@ window.CodeMirror = (function() {
1674
1719
  text[i] = reader.result;
1675
1720
  if (++read == n) {
1676
1721
  pos = clipPos(cm.doc, pos);
1677
- replaceRange(cm.doc, text.join(""), pos, "around", "paste");
1722
+ makeChange(cm.doc, {from: pos, to: pos, text: splitLines(text.join("\n")), origin: "paste"}, "around");
1678
1723
  }
1679
1724
  };
1680
1725
  reader.readAsText(file);
@@ -1730,13 +1775,13 @@ window.CodeMirror = (function() {
1730
1775
 
1731
1776
  function onDragStart(cm, e) {
1732
1777
  if (eventInWidget(cm.display, e)) return;
1733
-
1778
+
1734
1779
  var txt = cm.getSelection();
1735
1780
  e.dataTransfer.setData("Text", txt);
1736
1781
 
1737
1782
  // Use dummy image instead of default browsers image.
1738
1783
  // Recent Safari (~6.0.2) have a tendency to segfault when this happens, so we don't do it there.
1739
- if (e.dataTransfer.setDragImage && !safari) {
1784
+ if (e.dataTransfer.setDragImage) {
1740
1785
  var img = elt("img", null, null, "position: fixed; left: 0; top: 0;");
1741
1786
  if (opera) {
1742
1787
  img.width = img.height = 1;
@@ -1744,6 +1789,15 @@ window.CodeMirror = (function() {
1744
1789
  // Force a relayout, or Opera won't use our image for some obscure reason
1745
1790
  img._top = img.offsetTop;
1746
1791
  }
1792
+ if (safari) {
1793
+ if (cm.display.dragImg) {
1794
+ img = cm.display.dragImg;
1795
+ } else {
1796
+ cm.display.dragImg = img;
1797
+ img.src = "data:image/gif;base64,R0lGODlhAQABAAAAACH5BAEKAAEALAAAAAABAAEAAAICTAEAOw==";
1798
+ cm.display.wrapper.appendChild(img);
1799
+ }
1800
+ }
1747
1801
  e.dataTransfer.setDragImage(img, 0, 0);
1748
1802
  if (opera) img.parentNode.removeChild(img);
1749
1803
  }
@@ -1873,8 +1927,8 @@ window.CodeMirror = (function() {
1873
1927
 
1874
1928
  function allKeyMaps(cm) {
1875
1929
  var maps = cm.state.keyMaps.slice(0);
1930
+ if (cm.options.extraKeys) maps.push(cm.options.extraKeys);
1876
1931
  maps.push(cm.options.keyMap);
1877
- if (cm.options.extraKeys) maps.unshift(cm.options.extraKeys);
1878
1932
  return maps;
1879
1933
  }
1880
1934
 
@@ -2005,7 +2059,7 @@ window.CodeMirror = (function() {
2005
2059
  if (ie_lt9) display.scrollbarV.scrollTop = display.scroller.scrollTop = scrollPos;
2006
2060
  slowPoll(cm);
2007
2061
 
2008
- // Try to detect the user choosing select-all
2062
+ // Try to detect the user choosing select-all
2009
2063
  if (display.input.selectionStart != null && (!ie || ie_lt9)) {
2010
2064
  clearTimeout(detectingSelectAll);
2011
2065
  var extval = display.input.value = " " + (posEq(sel.from, sel.to) ? "" : display.input.value), i = 0;
@@ -2063,7 +2117,7 @@ window.CodeMirror = (function() {
2063
2117
  head: clipPostChange(doc, change, hint.head)};
2064
2118
 
2065
2119
  if (hint == "start") return {anchor: change.from, head: change.from};
2066
-
2120
+
2067
2121
  var end = changeEnd(change);
2068
2122
  if (hint == "around") return {anchor: change.from, head: end};
2069
2123
  if (hint == "end") return {anchor: end, head: end};
@@ -2145,6 +2199,8 @@ window.CodeMirror = (function() {
2145
2199
  }
2146
2200
 
2147
2201
  function makeChangeFromHistory(doc, type) {
2202
+ if (doc.cm && doc.cm.state.suppressEdits) return;
2203
+
2148
2204
  var hist = doc.history;
2149
2205
  var event = (type == "undo" ? hist.done : hist.undone).pop();
2150
2206
  if (!event) return;
@@ -2205,6 +2261,8 @@ window.CodeMirror = (function() {
2205
2261
  text: [change.text[0]], origin: change.origin};
2206
2262
  }
2207
2263
 
2264
+ change.removed = getBetween(doc, change.from, change.to);
2265
+
2208
2266
  if (!selAfter) selAfter = computeSelAfterChange(doc, change, null);
2209
2267
  if (doc.cm) makeChangeSingleDocInEditor(doc.cm, change, spans, selAfter);
2210
2268
  else updateDoc(doc, change, spans, selAfter);
@@ -2246,8 +2304,12 @@ window.CodeMirror = (function() {
2246
2304
  var lendiff = change.text.length - (to.line - from.line) - 1;
2247
2305
  // Remember that these lines changed, for updating the display
2248
2306
  regChange(cm, from.line, to.line + 1, lendiff);
2307
+
2249
2308
  if (hasHandler(cm, "change")) {
2250
- var changeObj = {from: from, to: to, text: change.text, origin: change.origin};
2309
+ var changeObj = {from: from, to: to,
2310
+ text: change.text,
2311
+ removed: change.removed,
2312
+ origin: change.origin};
2251
2313
  if (cm.curOp.textChanged) {
2252
2314
  for (var cur = cm.curOp.textChanged; cur.next; cur = cur.next) {}
2253
2315
  cur.next = changeObj;
@@ -2360,16 +2422,20 @@ window.CodeMirror = (function() {
2360
2422
  var dir = bias || 1;
2361
2423
  doc.cantEdit = false;
2362
2424
  search: for (;;) {
2363
- var line = getLine(doc, curPos.line), toClear;
2425
+ var line = getLine(doc, curPos.line);
2364
2426
  if (line.markedSpans) {
2365
2427
  for (var i = 0; i < line.markedSpans.length; ++i) {
2366
2428
  var sp = line.markedSpans[i], m = sp.marker;
2367
2429
  if ((sp.from == null || (m.inclusiveLeft ? sp.from <= curPos.ch : sp.from < curPos.ch)) &&
2368
2430
  (sp.to == null || (m.inclusiveRight ? sp.to >= curPos.ch : sp.to > curPos.ch))) {
2369
- if (mayClear && m.clearOnEnter) {
2370
- (toClear || (toClear = [])).push(m);
2371
- continue;
2372
- } else if (!m.atomic) continue;
2431
+ if (mayClear) {
2432
+ signal(m, "beforeCursorEnter");
2433
+ if (m.explicitlyCleared) {
2434
+ if (!line.markedSpans) break;
2435
+ else {--i; continue;}
2436
+ }
2437
+ }
2438
+ if (!m.atomic) continue;
2373
2439
  var newPos = m.find()[dir < 0 ? "from" : "to"];
2374
2440
  if (posEq(newPos, curPos)) {
2375
2441
  newPos.ch += dir;
@@ -2396,7 +2462,6 @@ window.CodeMirror = (function() {
2396
2462
  continue search;
2397
2463
  }
2398
2464
  }
2399
- if (toClear) for (var i = 0; i < toClear.length; ++i) toClear[i].clear();
2400
2465
  }
2401
2466
  return curPos;
2402
2467
  }
@@ -2407,9 +2472,9 @@ window.CodeMirror = (function() {
2407
2472
  function scrollCursorIntoView(cm) {
2408
2473
  var coords = scrollPosIntoView(cm, cm.doc.sel.head);
2409
2474
  if (!cm.state.focused) return;
2410
- var display = cm.display, box = getRect(display.sizer), doScroll = null;
2411
- if (coords.top + box.top < 0) doScroll = true;
2412
- else if (coords.bottom + box.top > (window.innerHeight || document.documentElement.clientHeight)) doScroll = false;
2475
+ var display = cm.display, box = getRect(display.sizer), doScroll = null, pTop = paddingTop(cm.display);
2476
+ if (coords.top + pTop + box.top < 0) doScroll = true;
2477
+ else if (coords.bottom + pTop + box.top > (window.innerHeight || document.documentElement.clientHeight)) doScroll = false;
2413
2478
  if (doScroll != null && !phantom) {
2414
2479
  var hidden = display.cursor.style.display == "none";
2415
2480
  if (hidden) {
@@ -2422,10 +2487,11 @@ window.CodeMirror = (function() {
2422
2487
  }
2423
2488
  }
2424
2489
 
2425
- function scrollPosIntoView(cm, pos) {
2490
+ function scrollPosIntoView(cm, pos, margin) {
2491
+ if (margin == null) margin = 0;
2426
2492
  for (;;) {
2427
2493
  var changed = false, coords = cursorCoords(cm, pos);
2428
- var scrollPos = calculateScrollPos(cm, coords.left, coords.top, coords.left, coords.bottom);
2494
+ var scrollPos = calculateScrollPos(cm, coords.left, coords.top - margin, coords.left, coords.bottom + margin);
2429
2495
  var startTop = cm.doc.scrollTop, startLeft = cm.doc.scrollLeft;
2430
2496
  if (scrollPos.scrollTop != null) {
2431
2497
  setScrollTop(cm, scrollPos.scrollTop);
@@ -2449,7 +2515,7 @@ window.CodeMirror = (function() {
2449
2515
  var display = cm.display, pt = paddingTop(display);
2450
2516
  y1 += pt; y2 += pt;
2451
2517
  var screen = display.scroller.clientHeight - scrollerCutOff, screentop = display.scroller.scrollTop, result = {};
2452
- var docBottom = cm.doc.height + 2 * pt;
2518
+ var docBottom = cm.doc.height + paddingVert(display);
2453
2519
  var atTop = y1 < pt + 10, atBottom = y2 + pt > docBottom - 10;
2454
2520
  if (y1 < screentop) result.scrollTop = atTop ? 0 : Math.max(0, y1);
2455
2521
  else if (y2 > screentop + screen) result.scrollTop = (atBottom ? docBottom : y2) - screen;
@@ -2467,6 +2533,17 @@ window.CodeMirror = (function() {
2467
2533
  return result;
2468
2534
  }
2469
2535
 
2536
+ function updateScrollPos(cm, left, top) {
2537
+ cm.curOp.updateScrollPos = {scrollLeft: left, scrollTop: top};
2538
+ }
2539
+
2540
+ function addToScrollPos(cm, left, top) {
2541
+ var pos = cm.curOp.updateScrollPos || (cm.curOp.updateScrollPos = {scrollLeft: cm.doc.scrollLeft, scrollTop: cm.doc.scrollTop});
2542
+ var scroll = cm.display.scroller;
2543
+ pos.scrollTop = Math.max(0, Math.min(scroll.scrollHeight - scroll.clientHeight, pos.scrollTop + top));
2544
+ pos.scrollLeft = Math.max(0, Math.min(scroll.scrollWidth - scroll.clientWidth, pos.scrollLeft + left));
2545
+ }
2546
+
2470
2547
  // API UTILITIES
2471
2548
 
2472
2549
  function indentLine(cm, n, how, aggressive) {
@@ -2540,13 +2617,21 @@ window.CodeMirror = (function() {
2540
2617
 
2541
2618
  if (unit == "char") moveOnce();
2542
2619
  else if (unit == "column") moveOnce(true);
2543
- else if (unit == "word") {
2544
- var sawWord = false;
2545
- for (;;) {
2546
- if (dir < 0) if (!moveOnce()) break;
2547
- if (isWordChar(lineObj.text.charAt(ch))) sawWord = true;
2548
- else if (sawWord) {if (dir < 0) {dir = 1; moveOnce();} break;}
2549
- if (dir > 0) if (!moveOnce()) break;
2620
+ else if (unit == "word" || unit == "group") {
2621
+ var sawType = null, group = unit == "group";
2622
+ for (var first = true;; first = false) {
2623
+ if (dir < 0 && !moveOnce(!first)) break;
2624
+ var cur = lineObj.text.charAt(ch) || "\n";
2625
+ var type = isWordChar(cur) ? "w"
2626
+ : !group ? null
2627
+ : /\s/.test(cur) ? null
2628
+ : "p";
2629
+ if (sawType && sawType != type) {
2630
+ if (dir < 0) {dir = 1; moveOnce();}
2631
+ break;
2632
+ }
2633
+ if (type) sawType = type;
2634
+ if (dir > 0 && !moveOnce(!first)) break;
2550
2635
  }
2551
2636
  }
2552
2637
  var result = skipAtomic(doc, Pos(line, ch), dir, true);
@@ -2558,7 +2643,7 @@ window.CodeMirror = (function() {
2558
2643
  var doc = cm.doc, x = pos.left, y;
2559
2644
  if (unit == "page") {
2560
2645
  var pageSize = Math.min(cm.display.wrapper.clientHeight, window.innerHeight || document.documentElement.clientHeight);
2561
- y = pos.top + dir * pageSize;
2646
+ y = pos.top + dir * (pageSize - (dir < 0 ? 1.5 : .5) * textHeight(cm.display));
2562
2647
  } else if (unit == "line") {
2563
2648
  y = dir > 0 ? pos.bottom + 3 : pos.top - 3;
2564
2649
  }
@@ -2576,9 +2661,9 @@ window.CodeMirror = (function() {
2576
2661
  if (line) {
2577
2662
  if (pos.after === false || end == line.length) --start; else ++end;
2578
2663
  var startChar = line.charAt(start);
2579
- var check = isWordChar(startChar) ? isWordChar :
2580
- /\s/.test(startChar) ? function(ch) {return /\s/.test(ch);} :
2581
- function(ch) {return !/\s/.test(ch) && !isWordChar(ch);};
2664
+ var check = isWordChar(startChar) ? isWordChar
2665
+ : /\s/.test(startChar) ? function(ch) {return /\s/.test(ch);}
2666
+ : function(ch) {return !/\s/.test(ch) && !isWordChar(ch);};
2582
2667
  while (start > 0 && check(line.charAt(start - 1))) --start;
2583
2668
  while (end < line.length && check(line.charAt(end))) ++end;
2584
2669
  }
@@ -2608,8 +2693,8 @@ window.CodeMirror = (function() {
2608
2693
  getOption: function(option) {return this.options[option];},
2609
2694
  getDoc: function() {return this.doc;},
2610
2695
 
2611
- addKeyMap: function(map) {
2612
- this.state.keyMaps.push(map);
2696
+ addKeyMap: function(map, bottom) {
2697
+ this.state.keyMaps[bottom ? "push" : "unshift"](map);
2613
2698
  },
2614
2699
  removeKeyMap: function(map) {
2615
2700
  var maps = this.state.keyMaps;
@@ -2691,14 +2776,13 @@ window.CodeMirror = (function() {
2691
2776
  return charCoords(this, clipPos(this.doc, pos), mode || "page");
2692
2777
  },
2693
2778
 
2694
- coordsChar: function(coords) {
2695
- var off = getRect(this.display.lineSpace);
2696
- var scrollY = window.pageYOffset || (document.documentElement || document.body).scrollTop;
2697
- var scrollX = window.pageXOffset || (document.documentElement || document.body).scrollLeft;
2698
- return coordsChar(this, coords.left - off.left - scrollX, coords.top - off.top - scrollY);
2779
+ coordsChar: function(coords, mode) {
2780
+ coords = fromCoordSystem(this, coords, mode || "page");
2781
+ return coordsChar(this, coords.left, coords.top);
2699
2782
  },
2700
2783
 
2701
2784
  defaultTextHeight: function() { return textHeight(this.display); },
2785
+ defaultCharWidth: function() { return charWidth(this.display); },
2702
2786
 
2703
2787
  setGutterMarker: operation(null, function(line, gutterID, value) {
2704
2788
  return changeLine(this, line, function(line) {
@@ -2851,8 +2935,7 @@ window.CodeMirror = (function() {
2851
2935
  if (sel.goalColumn != null) pos.left = sel.goalColumn;
2852
2936
  var target = findPosV(this, pos, dir, unit);
2853
2937
 
2854
- if (unit == "page")
2855
- this.display.scrollbarV.scrollTop += charCoords(this, target, "div").top - pos.top;
2938
+ if (unit == "page") addToScrollPos(this, 0, charCoords(this, target, "div").top - pos.top);
2856
2939
  extendSelection(this.doc, target, target, dir);
2857
2940
  sel.goalColumn = pos.left;
2858
2941
  }),
@@ -2863,9 +2946,10 @@ window.CodeMirror = (function() {
2863
2946
  else
2864
2947
  this.display.cursor.className = this.display.cursor.className.replace(" CodeMirror-overwrite", "");
2865
2948
  },
2949
+ hasFocus: function() { return this.state.focused; },
2866
2950
 
2867
2951
  scrollTo: operation(null, function(x, y) {
2868
- this.curOp.updateScrollPos = {scrollLeft: x, scrollTop: y};
2952
+ updateScrollPos(this, x, y);
2869
2953
  }),
2870
2954
  getScrollInfo: function() {
2871
2955
  var scroller = this.display.scroller, co = scrollerCutOff;
@@ -2874,13 +2958,13 @@ window.CodeMirror = (function() {
2874
2958
  clientHeight: scroller.clientHeight - co, clientWidth: scroller.clientWidth - co};
2875
2959
  },
2876
2960
 
2877
- scrollIntoView: function(pos) {
2961
+ scrollIntoView: function(pos, margin) {
2878
2962
  if (typeof pos == "number") pos = Pos(pos, 0);
2879
2963
  if (!pos || pos.line != null) {
2880
2964
  pos = pos ? clipPos(this.doc, pos) : this.doc.sel.head;
2881
- scrollPosIntoView(this, pos);
2965
+ scrollPosIntoView(this, pos, margin);
2882
2966
  } else {
2883
- scrollIntoView(this, pos.left, pos.top, pos.right, pos.bottom);
2967
+ scrollIntoView(this, pos.left, pos.top - margin, pos.right, pos.bottom + margin);
2884
2968
  }
2885
2969
  },
2886
2970
 
@@ -2900,7 +2984,7 @@ window.CodeMirror = (function() {
2900
2984
 
2901
2985
  refresh: operation(null, function() {
2902
2986
  clearCaches(this);
2903
- this.curOp.updateScrollPos = {scrollTop: this.doc.scrollTop, scrollLeft: this.doc.scrollLeft};
2987
+ updateScrollPos(this, this.doc.scrollLeft, this.doc.scrollTop);
2904
2988
  regChange(this);
2905
2989
  }),
2906
2990
 
@@ -2909,7 +2993,7 @@ window.CodeMirror = (function() {
2909
2993
  old.cm = null;
2910
2994
  attachDoc(this, doc);
2911
2995
  clearCaches(this);
2912
- this.curOp.updateScrollPos = {scrollTop: doc.scrollTop, scrollLeft: doc.scrollLeft};
2996
+ updateScrollPos(this, doc.scrollLeft, doc.scrollTop);
2913
2997
  return old;
2914
2998
  }),
2915
2999
 
@@ -2981,7 +3065,7 @@ window.CodeMirror = (function() {
2981
3065
  option("firstLineNumber", 1, guttersChanged, true);
2982
3066
  option("lineNumberFormatter", function(integer) {return integer;}, guttersChanged, true);
2983
3067
  option("showCursorWhenSelecting", false, updateSelection, true);
2984
-
3068
+
2985
3069
  option("readOnly", false, function(cm, val) {
2986
3070
  if (val == "nocursor") {onBlur(cm); cm.display.input.blur();}
2987
3071
  else if (!val) resetInput(cm, true);
@@ -3133,6 +3217,14 @@ window.CodeMirror = (function() {
3133
3217
  goLineEnd: function(cm) {
3134
3218
  cm.extendSelection(lineEnd(cm, cm.getCursor().line));
3135
3219
  },
3220
+ goLineRight: function(cm) {
3221
+ var top = cm.charCoords(cm.getCursor(), "div").top + 5;
3222
+ cm.extendSelection(cm.coordsChar({left: cm.display.lineDiv.offsetWidth + 100, top: top}, "div"));
3223
+ },
3224
+ goLineLeft: function(cm) {
3225
+ var top = cm.charCoords(cm.getCursor(), "div").top + 5;
3226
+ cm.extendSelection(cm.coordsChar({left: 0, top: top}, "div"));
3227
+ },
3136
3228
  goLineUp: function(cm) {cm.moveV(-1, "line");},
3137
3229
  goLineDown: function(cm) {cm.moveV(1, "line");},
3138
3230
  goPageUp: function(cm) {cm.moveV(-1, "page");},
@@ -3142,11 +3234,15 @@ window.CodeMirror = (function() {
3142
3234
  goColumnLeft: function(cm) {cm.moveH(-1, "column");},
3143
3235
  goColumnRight: function(cm) {cm.moveH(1, "column");},
3144
3236
  goWordLeft: function(cm) {cm.moveH(-1, "word");},
3237
+ goGroupRight: function(cm) {cm.moveH(1, "group");},
3238
+ goGroupLeft: function(cm) {cm.moveH(-1, "group");},
3145
3239
  goWordRight: function(cm) {cm.moveH(1, "word");},
3146
3240
  delCharBefore: function(cm) {cm.deleteH(-1, "char");},
3147
3241
  delCharAfter: function(cm) {cm.deleteH(1, "char");},
3148
3242
  delWordBefore: function(cm) {cm.deleteH(-1, "word");},
3149
3243
  delWordAfter: function(cm) {cm.deleteH(1, "word");},
3244
+ delGroupBefore: function(cm) {cm.deleteH(-1, "group");},
3245
+ delGroupAfter: function(cm) {cm.deleteH(1, "group");},
3150
3246
  indentAuto: function(cm) {cm.indentSelection("smart");},
3151
3247
  indentMore: function(cm) {cm.indentSelection("add");},
3152
3248
  indentLess: function(cm) {cm.indentSelection("subtract");},
@@ -3184,17 +3280,17 @@ window.CodeMirror = (function() {
3184
3280
  keyMap.pcDefault = {
3185
3281
  "Ctrl-A": "selectAll", "Ctrl-D": "deleteLine", "Ctrl-Z": "undo", "Shift-Ctrl-Z": "redo", "Ctrl-Y": "redo",
3186
3282
  "Ctrl-Home": "goDocStart", "Alt-Up": "goDocStart", "Ctrl-End": "goDocEnd", "Ctrl-Down": "goDocEnd",
3187
- "Ctrl-Left": "goWordLeft", "Ctrl-Right": "goWordRight", "Alt-Left": "goLineStart", "Alt-Right": "goLineEnd",
3188
- "Ctrl-Backspace": "delWordBefore", "Ctrl-Delete": "delWordAfter", "Ctrl-S": "save", "Ctrl-F": "find",
3283
+ "Ctrl-Left": "goGroupLeft", "Ctrl-Right": "goGroupRight", "Alt-Left": "goLineStart", "Alt-Right": "goLineEnd",
3284
+ "Ctrl-Backspace": "delGroupBefore", "Ctrl-Delete": "delGroupAfter", "Ctrl-S": "save", "Ctrl-F": "find",
3189
3285
  "Ctrl-G": "findNext", "Shift-Ctrl-G": "findPrev", "Shift-Ctrl-F": "replace", "Shift-Ctrl-R": "replaceAll",
3190
3286
  "Ctrl-[": "indentLess", "Ctrl-]": "indentMore",
3191
3287
  fallthrough: "basic"
3192
3288
  };
3193
3289
  keyMap.macDefault = {
3194
3290
  "Cmd-A": "selectAll", "Cmd-D": "deleteLine", "Cmd-Z": "undo", "Shift-Cmd-Z": "redo", "Cmd-Y": "redo",
3195
- "Cmd-Up": "goDocStart", "Cmd-End": "goDocEnd", "Cmd-Down": "goDocEnd", "Alt-Left": "goWordLeft",
3196
- "Alt-Right": "goWordRight", "Cmd-Left": "goLineStart", "Cmd-Right": "goLineEnd", "Alt-Backspace": "delWordBefore",
3197
- "Ctrl-Alt-Backspace": "delWordAfter", "Alt-Delete": "delWordAfter", "Cmd-S": "save", "Cmd-F": "find",
3291
+ "Cmd-Up": "goDocStart", "Cmd-End": "goDocEnd", "Cmd-Down": "goDocEnd", "Alt-Left": "goGroupLeft",
3292
+ "Alt-Right": "goGroupRight", "Cmd-Left": "goLineStart", "Cmd-Right": "goLineEnd", "Alt-Backspace": "delGroupBefore",
3293
+ "Ctrl-Alt-Backspace": "delGroupAfter", "Alt-Delete": "delGroupAfter", "Cmd-S": "save", "Cmd-F": "find",
3198
3294
  "Cmd-G": "findNext", "Shift-Cmd-G": "findPrev", "Cmd-Alt-F": "replace", "Shift-Cmd-Alt-F": "replaceAll",
3199
3295
  "Cmd-[": "indentLess", "Cmd-]": "indentMore",
3200
3296
  fallthrough: ["basic", "emacsy"]
@@ -3262,6 +3358,8 @@ window.CodeMirror = (function() {
3262
3358
  options.value = textarea.value;
3263
3359
  if (!options.tabindex && textarea.tabindex)
3264
3360
  options.tabindex = textarea.tabindex;
3361
+ if (!options.placeholder && textarea.placeholder)
3362
+ options.placeholder = textarea.placeholder;
3265
3363
  // Set autofocus to true if this textarea is focused, or if it has
3266
3364
  // autofocus and no other element is focused.
3267
3365
  if (options.autofocus == null) {
@@ -3274,17 +3372,19 @@ window.CodeMirror = (function() {
3274
3372
 
3275
3373
  function save() {textarea.value = cm.getValue();}
3276
3374
  if (textarea.form) {
3277
- // Deplorable hack to make the submit method do the right thing.
3278
3375
  on(textarea.form, "submit", save);
3279
- var form = textarea.form, realSubmit = form.submit;
3280
- try {
3281
- var wrappedSubmit = form.submit = function() {
3282
- save();
3283
- form.submit = realSubmit;
3284
- form.submit();
3285
- form.submit = wrappedSubmit;
3286
- };
3287
- } catch(e) {}
3376
+ // Deplorable hack to make the submit method do the right thing.
3377
+ if (!options.leaveSubmitMethodAlone) {
3378
+ var form = textarea.form, realSubmit = form.submit;
3379
+ try {
3380
+ var wrappedSubmit = form.submit = function() {
3381
+ save();
3382
+ form.submit = realSubmit;
3383
+ form.submit();
3384
+ form.submit = wrappedSubmit;
3385
+ };
3386
+ } catch(e) {}
3387
+ }
3288
3388
  }
3289
3389
 
3290
3390
  textarea.style.display = "none";
@@ -3316,6 +3416,7 @@ window.CodeMirror = (function() {
3316
3416
  this.pos = this.start = 0;
3317
3417
  this.string = string;
3318
3418
  this.tabSize = tabSize || 8;
3419
+ this.lastColumnPos = this.lastColumnValue = 0;
3319
3420
  }
3320
3421
 
3321
3422
  StringStream.prototype = {
@@ -3348,12 +3449,19 @@ window.CodeMirror = (function() {
3348
3449
  if (found > -1) {this.pos = found; return true;}
3349
3450
  },
3350
3451
  backUp: function(n) {this.pos -= n;},
3351
- column: function() {return countColumn(this.string, this.start, this.tabSize);},
3452
+ column: function() {
3453
+ if (this.lastColumnPos < this.start) {
3454
+ this.lastColumnValue = countColumn(this.string, this.start, this.tabSize, this.lastColumnPos, this.lastColumnValue);
3455
+ this.lastColumnPos = this.start;
3456
+ }
3457
+ return this.lastColumnValue;
3458
+ },
3352
3459
  indentation: function() {return countColumn(this.string, null, this.tabSize);},
3353
3460
  match: function(pattern, consume, caseInsensitive) {
3354
3461
  if (typeof pattern == "string") {
3355
3462
  var cased = function(str) {return caseInsensitive ? str.toLowerCase() : str;};
3356
- if (cased(this.string).indexOf(cased(pattern), this.pos) == this.pos) {
3463
+ var substr = this.string.substr(this.pos, pattern.length);
3464
+ if (cased(substr) == cased(pattern)) {
3357
3465
  if (consume !== false) this.pos += pattern.length;
3358
3466
  return true;
3359
3467
  }
@@ -3433,7 +3541,6 @@ window.CodeMirror = (function() {
3433
3541
  inclusiveLeft: this.inclusiveLeft, inclusiveRight: this.inclusiveRight,
3434
3542
  atomic: this.atomic,
3435
3543
  collapsed: this.collapsed,
3436
- clearOnEnter: this.clearOnEnter,
3437
3544
  replacedWith: copyWidget ? repl && repl.cloneNode(true) : repl,
3438
3545
  readOnly: this.readOnly,
3439
3546
  startStyle: this.startStyle, endStyle: this.endStyle};
@@ -3488,6 +3595,8 @@ window.CodeMirror = (function() {
3488
3595
  if (lineIsHidden(doc, line)) updateLineHeight(line, 0);
3489
3596
  });
3490
3597
 
3598
+ if (marker.clearOnEnter) on(marker, "beforeCursorEnter", function() { marker.clear(); });
3599
+
3491
3600
  if (marker.readOnly) {
3492
3601
  sawReadOnlySpans = true;
3493
3602
  if (doc.history.done.length || doc.history.undone.length)
@@ -3540,7 +3649,9 @@ window.CodeMirror = (function() {
3540
3649
  options = copyObj(options);
3541
3650
  options.shared = false;
3542
3651
  var markers = [markText(doc, from, to, options, type)], primary = markers[0];
3652
+ var widget = options.replacedWith;
3543
3653
  linkedDocs(doc, function(doc) {
3654
+ if (widget) options.replacedWith = widget.cloneNode(true);
3544
3655
  markers.push(markText(doc, clipPos(doc, from), clipPos(doc, to), options, type));
3545
3656
  for (var i = 0; i < doc.linked.length; ++i)
3546
3657
  if (doc.linked[i].isParent) return;
@@ -3814,9 +3925,7 @@ window.CodeMirror = (function() {
3814
3925
  if (!lineIsHidden(cm.doc, line) || widget.showIfHidden) {
3815
3926
  var aboveVisible = heightAtLine(cm, line) < cm.display.scroller.scrollTop;
3816
3927
  updateLineHeight(line, line.height + widgetHeight(widget));
3817
- if (aboveVisible)
3818
- cm.curOp.updateScrollPos = {scrollTop: cm.doc.scrollTop + widget.height,
3819
- scrollLeft: cm.doc.scrollLeft};
3928
+ if (aboveVisible) addToScrollPos(cm, 0, widget.height);
3820
3929
  }
3821
3930
  return true;
3822
3931
  });
@@ -3843,7 +3952,6 @@ window.CodeMirror = (function() {
3843
3952
  attachMarkedSpans(line, markedSpans);
3844
3953
  var estHeight = estimateHeight ? estimateHeight(line) : 1;
3845
3954
  if (estHeight != line.height) updateLineHeight(line, estHeight);
3846
- signalLater(line, "change");
3847
3955
  }
3848
3956
 
3849
3957
  function cleanUpLine(line) {
@@ -3855,7 +3963,8 @@ window.CodeMirror = (function() {
3855
3963
  // array, which contains alternating fragments of text and CSS
3856
3964
  // classes.
3857
3965
  function runMode(cm, text, mode, state, f) {
3858
- var flattenSpans = cm.options.flattenSpans;
3966
+ var flattenSpans = mode.flattenSpans;
3967
+ if (flattenSpans == null) flattenSpans = cm.options.flattenSpans;
3859
3968
  var curText = "", curStyle = null;
3860
3969
  var stream = new StringStream(text, cm.options.tabSize);
3861
3970
  if (text == "" && mode.blankLine) mode.blankLine(state);
@@ -3957,6 +4066,8 @@ window.CodeMirror = (function() {
3957
4066
  builder.measure = line == realLine && measure;
3958
4067
  builder.pos = 0;
3959
4068
  builder.addToken = builder.measure ? buildTokenMeasure : buildToken;
4069
+ if ((ie || webkit) && cm.getOption("lineWrapping"))
4070
+ builder.addToken = buildTokenSplitSpaces(builder.addToken);
3960
4071
  if (measure && sawBefore && line != realLine && !builder.addedOne) {
3961
4072
  measure[0] = builder.pre.appendChild(zeroWidthElement(cm.display.measure));
3962
4073
  builder.addedOne = true;
@@ -3989,10 +4100,11 @@ window.CodeMirror = (function() {
3989
4100
  }
3990
4101
  }
3991
4102
 
4103
+ signal(cm, "renderLine", cm, realLine, builder.pre);
3992
4104
  return builder.pre;
3993
4105
  }
3994
4106
 
3995
- var tokenSpecialChars = /[\t\u0000-\u0019\u200b\u2028\u2029\uFEFF]/g;
4107
+ var tokenSpecialChars = /[\t\u0000-\u0019\u00ad\u200b\u2028\u2029\uFEFF]/g;
3996
4108
  function buildToken(builder, text, style, startStyle, endStyle) {
3997
4109
  if (!text) return;
3998
4110
  if (!tokenSpecialChars.test(text)) {
@@ -4032,23 +4144,42 @@ window.CodeMirror = (function() {
4032
4144
  }
4033
4145
 
4034
4146
  function buildTokenMeasure(builder, text, style, startStyle, endStyle) {
4147
+ var wrapping = builder.cm.options.lineWrapping;
4035
4148
  for (var i = 0; i < text.length; ++i) {
4036
4149
  var ch = text.charAt(i), start = i == 0;
4037
4150
  if (ch >= "\ud800" && ch < "\udbff" && i < text.length - 1) {
4038
4151
  ch = text.slice(i, i + 2);
4039
4152
  ++i;
4040
- } else if (i && builder.cm.options.lineWrapping &&
4153
+ } else if (i && wrapping &&
4041
4154
  spanAffectsWrapping.test(text.slice(i - 1, i + 1))) {
4042
4155
  builder.pre.appendChild(elt("wbr"));
4043
4156
  }
4044
- builder.measure[builder.pos] =
4157
+ var span = builder.measure[builder.pos] =
4045
4158
  buildToken(builder, ch, style,
4046
4159
  start && startStyle, i == text.length - 1 && endStyle);
4160
+ // In IE single-space nodes wrap differently than spaces
4161
+ // embedded in larger text nodes, except when set to
4162
+ // white-space: normal (issue #1268).
4163
+ if (ie && wrapping && ch == " " && i && !/\s/.test(text.charAt(i - 1)) &&
4164
+ i < text.length - 1 && !/\s/.test(text.charAt(i + 1)))
4165
+ span.style.whiteSpace = "normal";
4047
4166
  builder.pos += ch.length;
4048
4167
  }
4049
4168
  if (text.length) builder.addedOne = true;
4050
4169
  }
4051
4170
 
4171
+ function buildTokenSplitSpaces(inner) {
4172
+ function split(old) {
4173
+ var out = " ";
4174
+ for (var i = 0; i < old.length - 2; ++i) out += i % 2 ? " " : "\u00a0";
4175
+ out += " ";
4176
+ return out;
4177
+ }
4178
+ return function(builder, text, style, startStyle, endStyle) {
4179
+ return inner(builder, text.replace(/ {3,}/, split), style, startStyle, endStyle);
4180
+ };
4181
+ }
4182
+
4052
4183
  function buildCollapsedSpan(builder, size, widget) {
4053
4184
  if (widget) {
4054
4185
  if (!builder.display) widget = widget.cloneNode(true);
@@ -4125,6 +4256,10 @@ window.CodeMirror = (function() {
4125
4256
 
4126
4257
  function updateDoc(doc, change, markedSpans, selAfter, estimateHeight) {
4127
4258
  function spansFor(n) {return markedSpans ? markedSpans[n] : null;}
4259
+ function update(line, text, spans) {
4260
+ updateLine(line, text, spans, estimateHeight);
4261
+ signalLater(line, "change", line, change);
4262
+ }
4128
4263
 
4129
4264
  var from = change.from, to = change.to, text = change.text;
4130
4265
  var firstLine = getLine(doc, from.line), lastLine = getLine(doc, to.line);
@@ -4136,27 +4271,25 @@ window.CodeMirror = (function() {
4136
4271
  // sure line objects move the way they are supposed to.
4137
4272
  for (var i = 0, e = text.length - 1, added = []; i < e; ++i)
4138
4273
  added.push(makeLine(text[i], spansFor(i), estimateHeight));
4139
- updateLine(lastLine, lastLine.text, lastSpans, estimateHeight);
4274
+ update(lastLine, lastLine.text, lastSpans);
4140
4275
  if (nlines) doc.remove(from.line, nlines);
4141
4276
  if (added.length) doc.insert(from.line, added);
4142
4277
  } else if (firstLine == lastLine) {
4143
4278
  if (text.length == 1) {
4144
- updateLine(firstLine, firstLine.text.slice(0, from.ch) + lastText + firstLine.text.slice(to.ch),
4145
- lastSpans, estimateHeight);
4279
+ update(firstLine, firstLine.text.slice(0, from.ch) + lastText + firstLine.text.slice(to.ch), lastSpans);
4146
4280
  } else {
4147
4281
  for (var added = [], i = 1, e = text.length - 1; i < e; ++i)
4148
4282
  added.push(makeLine(text[i], spansFor(i), estimateHeight));
4149
4283
  added.push(makeLine(lastText + firstLine.text.slice(to.ch), lastSpans, estimateHeight));
4150
- updateLine(firstLine, firstLine.text.slice(0, from.ch) + text[0], spansFor(0), estimateHeight);
4284
+ update(firstLine, firstLine.text.slice(0, from.ch) + text[0], spansFor(0));
4151
4285
  doc.insert(from.line + 1, added);
4152
4286
  }
4153
4287
  } else if (text.length == 1) {
4154
- updateLine(firstLine, firstLine.text.slice(0, from.ch) + text[0] + lastLine.text.slice(to.ch),
4155
- spansFor(0), estimateHeight);
4288
+ update(firstLine, firstLine.text.slice(0, from.ch) + text[0] + lastLine.text.slice(to.ch), spansFor(0));
4156
4289
  doc.remove(from.line + 1, nlines);
4157
4290
  } else {
4158
- updateLine(firstLine, firstLine.text.slice(0, from.ch) + text[0], spansFor(0), estimateHeight);
4159
- updateLine(lastLine, lastText + lastLine.text.slice(to.ch), lastSpans, estimateHeight);
4291
+ update(firstLine, firstLine.text.slice(0, from.ch) + text[0], spansFor(0));
4292
+ update(lastLine, lastText + lastLine.text.slice(to.ch), lastSpans);
4160
4293
  for (var i = 1, e = text.length - 1, added = []; i < e; ++i)
4161
4294
  added.push(makeLine(text[i], spansFor(i), estimateHeight));
4162
4295
  if (nlines > 1) doc.remove(from.line + 1, nlines - 1);
@@ -4300,7 +4433,7 @@ window.CodeMirror = (function() {
4300
4433
  var Doc = CodeMirror.Doc = function(text, mode, firstLine) {
4301
4434
  if (!(this instanceof Doc)) return new Doc(text, mode, firstLine);
4302
4435
  if (firstLine == null) firstLine = 0;
4303
-
4436
+
4304
4437
  BranchChunk.call(this, [new LeafChunk([makeLine("", null)])]);
4305
4438
  this.first = firstLine;
4306
4439
  this.scrollTop = this.scrollLeft = 0;
@@ -4412,7 +4545,7 @@ window.CodeMirror = (function() {
4412
4545
  this.history.lastOp = this.history.lastOrigin = null;
4413
4546
  },
4414
4547
  isClean: function () {return this.history.dirtyCounter == 0;},
4415
-
4548
+
4416
4549
  getHistory: function() {
4417
4550
  return {done: copyHistoryArray(this.history.done),
4418
4551
  undone: copyHistoryArray(this.history.undone)};
@@ -4707,7 +4840,7 @@ window.CodeMirror = (function() {
4707
4840
  while (hist.done.length > hist.undoDepth)
4708
4841
  hist.done.shift();
4709
4842
  if (hist.dirtyCounter < 0)
4710
- // The user has made a change after undoing past the last clean state.
4843
+ // The user has made a change after undoing past the last clean state.
4711
4844
  // We can never get back to a clean state now until markClean() is called.
4712
4845
  hist.dirtyCounter = NaN;
4713
4846
  else
@@ -4920,12 +5053,12 @@ window.CodeMirror = (function() {
4920
5053
 
4921
5054
  // Counts the column offset in a string, taking tabs into account.
4922
5055
  // Used mostly to find indentation.
4923
- function countColumn(string, end, tabSize) {
5056
+ function countColumn(string, end, tabSize, startIndex, startValue) {
4924
5057
  if (end == null) {
4925
5058
  end = string.search(/[^\s\u00a0]/);
4926
5059
  if (end == -1) end = string.length;
4927
5060
  }
4928
- for (var i = 0, n = 0; i < end; ++i) {
5061
+ for (var i = startIndex || 0, n = startValue || 0; i < end; ++i) {
4929
5062
  if (string.charAt(i) == "\t") n += tabSize - (n % tabSize);
4930
5063
  else ++n;
4931
5064
  }
@@ -5005,9 +5138,8 @@ window.CodeMirror = (function() {
5005
5138
  }
5006
5139
 
5007
5140
  function removeChildren(e) {
5008
- // IE will break all parent-child relations in subnodes when setting innerHTML
5009
- if (!ie) e.innerHTML = "";
5010
- else while (e.firstChild) e.removeChild(e.firstChild);
5141
+ for (var count = e.childNodes.length; count > 0; --count)
5142
+ e.removeChild(e.firstChild);
5011
5143
  return e;
5012
5144
  }
5013
5145
 
@@ -5047,8 +5179,8 @@ window.CodeMirror = (function() {
5047
5179
  // various browsers.
5048
5180
  var spanAffectsWrapping = /^$/; // Won't match any two-character string
5049
5181
  if (gecko) spanAffectsWrapping = /$'/;
5050
- else if (safari) spanAffectsWrapping = /\-[^ \-?]|\?[^ !'\"\),.\-\/:;\?\]\}]/;
5051
- else if (chrome) spanAffectsWrapping = /\-[^ \-\.?]|\?[^ \-\.?\]\}:;!'\"\),\/]|[\.!\"#&%\)*+,:;=>\]|\}~][\(\{\[<]|\$'/;
5182
+ else if (safari && !/Version\/([6-9]|\d\d)\b/.test(navigator.userAgent)) spanAffectsWrapping = /\-[^ \-?]|\?[^ !'\"\),.\-\/:;\?\]\}]/;
5183
+ else if (webkit) spanAffectsWrapping = /[~!#%&*)=+}\]|\"\.>,:;][({[<]|-[^\-?\.]|\?[\w~`@#$%\^&*(_=+{[|><]/;
5052
5184
 
5053
5185
  var knownScrollbarWidth;
5054
5186
  function scrollbarWidth(measure) {
@@ -5378,7 +5510,7 @@ window.CodeMirror = (function() {
5378
5510
 
5379
5511
  // THE END
5380
5512
 
5381
- CodeMirror.version = "3.1";
5513
+ CodeMirror.version = "3.11";
5382
5514
 
5383
5515
  return CodeMirror;
5384
5516
  })();