codemirror-rails 4.1 → 4.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (138) hide show
  1. checksums.yaml +4 -4
  2. data/lib/codemirror/rails/version.rb +2 -2
  3. data/vendor/assets/javascripts/codemirror.js +133 -58
  4. data/vendor/assets/javascripts/codemirror/addons/comment/comment.js +3 -0
  5. data/vendor/assets/javascripts/codemirror/addons/comment/continuecomment.js +3 -0
  6. data/vendor/assets/javascripts/codemirror/addons/dialog/dialog.js +3 -0
  7. data/vendor/assets/javascripts/codemirror/addons/display/fullscreen.js +3 -0
  8. data/vendor/assets/javascripts/codemirror/addons/display/placeholder.js +3 -0
  9. data/vendor/assets/javascripts/codemirror/addons/display/rulers.js +16 -6
  10. data/vendor/assets/javascripts/codemirror/addons/edit/closebrackets.js +3 -0
  11. data/vendor/assets/javascripts/codemirror/addons/edit/closetag.js +28 -3
  12. data/vendor/assets/javascripts/codemirror/addons/edit/continuelist.js +3 -0
  13. data/vendor/assets/javascripts/codemirror/addons/edit/matchbrackets.js +3 -0
  14. data/vendor/assets/javascripts/codemirror/addons/edit/matchtags.js +3 -0
  15. data/vendor/assets/javascripts/codemirror/addons/edit/trailingspace.js +3 -0
  16. data/vendor/assets/javascripts/codemirror/addons/fold/brace-fold.js +3 -0
  17. data/vendor/assets/javascripts/codemirror/addons/fold/comment-fold.js +3 -0
  18. data/vendor/assets/javascripts/codemirror/addons/fold/foldcode.js +36 -8
  19. data/vendor/assets/javascripts/codemirror/addons/fold/foldgutter.js +3 -0
  20. data/vendor/assets/javascripts/codemirror/addons/fold/indent-fold.js +3 -0
  21. data/vendor/assets/javascripts/codemirror/addons/fold/markdown-fold.js +3 -0
  22. data/vendor/assets/javascripts/codemirror/addons/fold/xml-fold.js +4 -1
  23. data/vendor/assets/javascripts/codemirror/addons/hint/anyword-hint.js +3 -0
  24. data/vendor/assets/javascripts/codemirror/addons/hint/css-hint.js +3 -0
  25. data/vendor/assets/javascripts/codemirror/addons/hint/html-hint.js +3 -0
  26. data/vendor/assets/javascripts/codemirror/addons/hint/javascript-hint.js +7 -2
  27. data/vendor/assets/javascripts/codemirror/addons/hint/python-hint.js +3 -0
  28. data/vendor/assets/javascripts/codemirror/addons/hint/show-hint.js +74 -36
  29. data/vendor/assets/javascripts/codemirror/addons/hint/sql-hint.js +3 -0
  30. data/vendor/assets/javascripts/codemirror/addons/hint/xml-hint.js +3 -0
  31. data/vendor/assets/javascripts/codemirror/addons/lint/coffeescript-lint.js +3 -0
  32. data/vendor/assets/javascripts/codemirror/addons/lint/css-lint.js +3 -0
  33. data/vendor/assets/javascripts/codemirror/addons/lint/javascript-lint.js +3 -0
  34. data/vendor/assets/javascripts/codemirror/addons/lint/json-lint.js +3 -0
  35. data/vendor/assets/javascripts/codemirror/addons/lint/lint.js +3 -0
  36. data/vendor/assets/javascripts/codemirror/addons/lint/yaml-lint.js +3 -0
  37. data/vendor/assets/javascripts/codemirror/addons/merge/merge.js +3 -0
  38. data/vendor/assets/javascripts/codemirror/addons/mode/loadmode.js +3 -0
  39. data/vendor/assets/javascripts/codemirror/addons/mode/multiplex.js +3 -0
  40. data/vendor/assets/javascripts/codemirror/addons/mode/overlay.js +12 -3
  41. data/vendor/assets/javascripts/codemirror/addons/runmode/colorize.js +3 -0
  42. data/vendor/assets/javascripts/codemirror/addons/runmode/runmode-standalone.js +4 -1
  43. data/vendor/assets/javascripts/codemirror/addons/runmode/runmode.js +4 -1
  44. data/vendor/assets/javascripts/codemirror/addons/runmode/runmode.node.js +4 -1
  45. data/vendor/assets/javascripts/codemirror/addons/scroll/scrollpastend.js +3 -0
  46. data/vendor/assets/javascripts/codemirror/addons/search/match-highlighter.js +6 -2
  47. data/vendor/assets/javascripts/codemirror/addons/search/search.js +3 -0
  48. data/vendor/assets/javascripts/codemirror/addons/search/searchcursor.js +3 -0
  49. data/vendor/assets/javascripts/codemirror/addons/selection/active-line.js +3 -0
  50. data/vendor/assets/javascripts/codemirror/addons/selection/mark-selection.js +3 -0
  51. data/vendor/assets/javascripts/codemirror/addons/tern/tern.js +23 -16
  52. data/vendor/assets/javascripts/codemirror/addons/tern/worker.js +3 -0
  53. data/vendor/assets/javascripts/codemirror/addons/wrap/hardwrap.js +3 -0
  54. data/vendor/assets/javascripts/codemirror/keymaps/emacs.js +4 -7
  55. data/vendor/assets/javascripts/codemirror/keymaps/sublime.js +11 -8
  56. data/vendor/assets/javascripts/codemirror/keymaps/vim.js +92 -33
  57. data/vendor/assets/javascripts/codemirror/modes/apl.js +3 -0
  58. data/vendor/assets/javascripts/codemirror/modes/asterisk.js +3 -0
  59. data/vendor/assets/javascripts/codemirror/modes/clike.js +3 -0
  60. data/vendor/assets/javascripts/codemirror/modes/clojure.js +3 -0
  61. data/vendor/assets/javascripts/codemirror/modes/cobol.js +3 -0
  62. data/vendor/assets/javascripts/codemirror/modes/coffeescript.js +3 -0
  63. data/vendor/assets/javascripts/codemirror/modes/commonlisp.js +3 -0
  64. data/vendor/assets/javascripts/codemirror/modes/css.js +13 -14
  65. data/vendor/assets/javascripts/codemirror/modes/cypher.js +146 -0
  66. data/vendor/assets/javascripts/codemirror/modes/d.js +3 -0
  67. data/vendor/assets/javascripts/codemirror/modes/diff.js +3 -0
  68. data/vendor/assets/javascripts/codemirror/modes/django.js +3 -0
  69. data/vendor/assets/javascripts/codemirror/modes/dtd.js +3 -0
  70. data/vendor/assets/javascripts/codemirror/modes/dylan.js +15 -0
  71. data/vendor/assets/javascripts/codemirror/modes/ecl.js +3 -0
  72. data/vendor/assets/javascripts/codemirror/modes/eiffel.js +3 -0
  73. data/vendor/assets/javascripts/codemirror/modes/erlang.js +3 -0
  74. data/vendor/assets/javascripts/codemirror/modes/fortran.js +3 -0
  75. data/vendor/assets/javascripts/codemirror/modes/gas.js +3 -0
  76. data/vendor/assets/javascripts/codemirror/modes/gfm.js +9 -1
  77. data/vendor/assets/javascripts/codemirror/modes/gherkin.js +3 -0
  78. data/vendor/assets/javascripts/codemirror/modes/go.js +3 -0
  79. data/vendor/assets/javascripts/codemirror/modes/groovy.js +3 -0
  80. data/vendor/assets/javascripts/codemirror/modes/haml.js +3 -0
  81. data/vendor/assets/javascripts/codemirror/modes/haskell.js +3 -0
  82. data/vendor/assets/javascripts/codemirror/modes/haxe.js +5 -1
  83. data/vendor/assets/javascripts/codemirror/modes/htmlembedded.js +3 -0
  84. data/vendor/assets/javascripts/codemirror/modes/htmlmixed.js +3 -0
  85. data/vendor/assets/javascripts/codemirror/modes/http.js +3 -0
  86. data/vendor/assets/javascripts/codemirror/modes/jade.js +569 -81
  87. data/vendor/assets/javascripts/codemirror/modes/javascript.js +5 -0
  88. data/vendor/assets/javascripts/codemirror/modes/jinja2.js +3 -0
  89. data/vendor/assets/javascripts/codemirror/modes/julia.js +3 -0
  90. data/vendor/assets/javascripts/codemirror/modes/livescript.js +17 -17
  91. data/vendor/assets/javascripts/codemirror/modes/lua.js +3 -0
  92. data/vendor/assets/javascripts/codemirror/modes/markdown.js +5 -3
  93. data/vendor/assets/javascripts/codemirror/modes/mirc.js +3 -0
  94. data/vendor/assets/javascripts/codemirror/modes/mllike.js +3 -0
  95. data/vendor/assets/javascripts/codemirror/modes/nginx.js +3 -0
  96. data/vendor/assets/javascripts/codemirror/modes/ntriples.js +3 -0
  97. data/vendor/assets/javascripts/codemirror/modes/octave.js +3 -0
  98. data/vendor/assets/javascripts/codemirror/modes/pascal.js +3 -0
  99. data/vendor/assets/javascripts/codemirror/modes/pegjs.js +3 -0
  100. data/vendor/assets/javascripts/codemirror/modes/perl.js +5 -0
  101. data/vendor/assets/javascripts/codemirror/modes/php.js +5 -2
  102. data/vendor/assets/javascripts/codemirror/modes/pig.js +3 -0
  103. data/vendor/assets/javascripts/codemirror/modes/properties.js +3 -0
  104. data/vendor/assets/javascripts/codemirror/modes/puppet.js +3 -0
  105. data/vendor/assets/javascripts/codemirror/modes/python.js +284 -328
  106. data/vendor/assets/javascripts/codemirror/modes/q.js +3 -0
  107. data/vendor/assets/javascripts/codemirror/modes/r.js +3 -0
  108. data/vendor/assets/javascripts/codemirror/modes/rpm.js +3 -0
  109. data/vendor/assets/javascripts/codemirror/modes/rst.js +3 -0
  110. data/vendor/assets/javascripts/codemirror/modes/ruby.js +3 -0
  111. data/vendor/assets/javascripts/codemirror/modes/rust.js +3 -0
  112. data/vendor/assets/javascripts/codemirror/modes/sass.js +3 -0
  113. data/vendor/assets/javascripts/codemirror/modes/scheme.js +3 -0
  114. data/vendor/assets/javascripts/codemirror/modes/shell.js +9 -2
  115. data/vendor/assets/javascripts/codemirror/modes/sieve.js +3 -0
  116. data/vendor/assets/javascripts/codemirror/modes/smalltalk.js +3 -0
  117. data/vendor/assets/javascripts/codemirror/modes/smarty.js +3 -0
  118. data/vendor/assets/javascripts/codemirror/modes/smartymixed.js +3 -0
  119. data/vendor/assets/javascripts/codemirror/modes/solr.js +3 -0
  120. data/vendor/assets/javascripts/codemirror/modes/sparql.js +3 -0
  121. data/vendor/assets/javascripts/codemirror/modes/sql.js +3 -0
  122. data/vendor/assets/javascripts/codemirror/modes/stex.js +3 -0
  123. data/vendor/assets/javascripts/codemirror/modes/tcl.js +3 -0
  124. data/vendor/assets/javascripts/codemirror/modes/tiddlywiki.js +3 -0
  125. data/vendor/assets/javascripts/codemirror/modes/tiki.js +3 -0
  126. data/vendor/assets/javascripts/codemirror/modes/toml.js +3 -0
  127. data/vendor/assets/javascripts/codemirror/modes/turtle.js +3 -0
  128. data/vendor/assets/javascripts/codemirror/modes/vb.js +3 -0
  129. data/vendor/assets/javascripts/codemirror/modes/vbscript.js +3 -0
  130. data/vendor/assets/javascripts/codemirror/modes/velocity.js +3 -0
  131. data/vendor/assets/javascripts/codemirror/modes/verilog.js +3 -0
  132. data/vendor/assets/javascripts/codemirror/modes/xml.js +4 -1
  133. data/vendor/assets/javascripts/codemirror/modes/xquery.js +3 -0
  134. data/vendor/assets/javascripts/codemirror/modes/yaml.js +3 -0
  135. data/vendor/assets/javascripts/codemirror/modes/z80.js +3 -0
  136. data/vendor/assets/stylesheets/codemirror/addons/tern/tern.css +1 -0
  137. data/vendor/assets/stylesheets/codemirror/themes/neo.css +40 -0
  138. metadata +4 -2
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: dd16e48b5a4bf97bb9b7d6e9fe4369007477156a
4
- data.tar.gz: e2cd3b0008e31a240d67416decca66fde5d62ec5
3
+ metadata.gz: a61f66e6dd0e16149f2c19e1adc9019a21a812ed
4
+ data.tar.gz: 7c7855b16003ce87a7a9f0b40f4d6d697e38dc16
5
5
  SHA512:
6
- metadata.gz: 1a4dbd28831a7db000009ca3abf95ecda5f30352e637c49b26936ea258fbb9f5f8f2a2d0ef086bb4b5aff3c69211253985b47205e289365e02838dfa3900e020
7
- data.tar.gz: 1006bd816e052f66e24cbfb00ac4500aca09d043b772880cd7b8445072f129fd27208a95172d9d53d6466fcf4a6f8b8052c22d62af167fb4c065c88ebb371d70
6
+ metadata.gz: 9ab0ee0506c895bda4c06534e4a334d34050aedc14c3133c9e1dc6f92356434ce52758206f53e10ed9257ff9a82520d5d38d478cdc751e5f7a4e261fec3693ad
7
+ data.tar.gz: cc3e80eae3e1950147c28b9a06c60b21ca944b40dd221d8d8236ef494fa6e58ec875da515daaec4fa2cee56265a45cadad61c0f4308e4859a3a3281e1608ab92
@@ -1,6 +1,6 @@
1
1
  module Codemirror
2
2
  module Rails
3
- VERSION = '4.1'
4
- CODEMIRROR_VERSION = '4.1'
3
+ VERSION = '4.2'
4
+ CODEMIRROR_VERSION = '4.2'
5
5
  end
6
6
  end
@@ -1,3 +1,6 @@
1
+ // CodeMirror, copyright (c) by Marijn Haverbeke and others
2
+ // Distributed under an MIT license: http://codemirror.net/LICENSE
3
+
1
4
  // This is CodeMirror (http://codemirror.net), a code editor
2
5
  // implemented in JavaScript on top of the browser's DOM.
3
6
  //
@@ -93,6 +96,7 @@
93
96
  if (ie_upto10) setTimeout(bind(resetInput, this, true), 20);
94
97
 
95
98
  registerEventHandlers(this);
99
+ ensureGlobalHandlers();
96
100
 
97
101
  var cm = this;
98
102
  runInOp(this, function() {
@@ -230,6 +234,10 @@
230
234
 
231
235
  // True when shift is held down.
232
236
  d.shift = false;
237
+
238
+ // Used to track whether anything happened since the context menu
239
+ // was opened.
240
+ d.selForContextMenu = null;
233
241
  }
234
242
 
235
243
  // STATE UPDATES
@@ -455,7 +463,7 @@
455
463
  // the the current scroll position). viewPort may contain top,
456
464
  // height, and ensure (see op.scrollToPos) properties.
457
465
  function visibleLines(display, doc, viewPort) {
458
- var top = viewPort && viewPort.top != null ? viewPort.top : display.scroller.scrollTop;
466
+ var top = viewPort && viewPort.top != null ? Math.max(0, viewPort.top) : display.scroller.scrollTop;
459
467
  top = Math.floor(top - paddingTop(display));
460
468
  var bottom = viewPort && viewPort.bottom != null ? viewPort.bottom : top + display.wrapper.clientHeight;
461
469
 
@@ -471,7 +479,7 @@
471
479
  return {from: lineAtHeight(doc, heightAtLine(getLine(doc, ensureTo)) - display.wrapper.clientHeight),
472
480
  to: ensureTo};
473
481
  }
474
- return {from: from, to: to};
482
+ return {from: from, to: Math.max(to, from + 1)};
475
483
  }
476
484
 
477
485
  // LINE NUMBERS
@@ -659,7 +667,6 @@
659
667
  cm.display.gutters.style.height = Math.max(measure.docHeight, measure.clientHeight - scrollerCutOff) + "px";
660
668
  }
661
669
 
662
-
663
670
  function checkForWebkitWidthBug(cm, measure) {
664
671
  // Work around Webkit bug where it sometimes reserves space for a
665
672
  // non-existing phantom scrollbar in the scroller (Issue #2420)
@@ -1142,7 +1149,8 @@
1142
1149
  if (hasHandler(doc, "beforeSelectionChange") || doc.cm && hasHandler(doc.cm, "beforeSelectionChange"))
1143
1150
  sel = filterSelectionChange(doc, sel);
1144
1151
 
1145
- var bias = cmp(sel.primary().head, doc.sel.primary().head) < 0 ? -1 : 1;
1152
+ var bias = options && options.bias ||
1153
+ (cmp(sel.primary().head, doc.sel.primary().head) < 0 ? -1 : 1);
1146
1154
  setSelectionInner(doc, skipAtomicInSelection(doc, sel, bias, true));
1147
1155
 
1148
1156
  if (!(options && options.scroll === false) && doc.cm)
@@ -1621,7 +1629,7 @@
1621
1629
  else
1622
1630
  rect = nullRect;
1623
1631
  } else {
1624
- rect = range(node, start, end).getBoundingClientRect();
1632
+ rect = range(node, start, end).getBoundingClientRect() || nullRect;
1625
1633
  }
1626
1634
  } else { // If it is a widget, simply get the box for the whole widget.
1627
1635
  if (start > 0) collapse = bias = "right";
@@ -1922,6 +1930,10 @@
1922
1930
  if (!updated && op.selectionChanged) updateSelection(cm);
1923
1931
  if (!updated && op.startHeight != cm.doc.height) updateScrollbars(cm);
1924
1932
 
1933
+ // Abort mouse wheel delta measurement, when scrolling explicitly
1934
+ if (display.wheelStartX != null && (op.scrollTop != null || op.scrollLeft != null || op.scrollToPos))
1935
+ display.wheelStartX = display.wheelStartY = null;
1936
+
1925
1937
  // Propagate the scroll position to the actual DOM scroller
1926
1938
  if (op.scrollTop != null && display.scroller.scrollTop != op.scrollTop) {
1927
1939
  var top = Math.max(0, Math.min(display.scroller.scrollHeight - display.scroller.clientHeight, op.scrollTop));
@@ -2135,7 +2147,8 @@
2135
2147
 
2136
2148
  function viewCuttingPoint(cm, oldN, newN, dir) {
2137
2149
  var index = findViewIndex(cm, oldN), diff, view = cm.display.view;
2138
- if (!sawCollapsedSpans) return {index: index, lineN: newN};
2150
+ if (!sawCollapsedSpans || newN == cm.doc.first + cm.doc.size)
2151
+ return {index: index, lineN: newN};
2139
2152
  for (var i = 0, n = cm.display.viewFrom; i < index; i++)
2140
2153
  n += view[i].size;
2141
2154
  if (n != oldN) {
@@ -2246,6 +2259,8 @@
2246
2259
  if (withOp) startOperation(cm);
2247
2260
  cm.display.shift = false;
2248
2261
 
2262
+ if (text.charCodeAt(0) == 0x200b && doc.sel == cm.display.selForContextMenu && !prevInput)
2263
+ prevInput = "\u200b";
2249
2264
  // Find the part of the input that is actually new
2250
2265
  var same = 0, l = Math.min(prevInput.length, text.length);
2251
2266
  while (same < l && prevInput.charCodeAt(same) == text.charCodeAt(same)) ++same;
@@ -2345,7 +2360,7 @@
2345
2360
  var pos = posFromMouse(cm, e);
2346
2361
  if (!pos || clickInGutter(cm, e) || eventInWidget(cm.display, e)) return;
2347
2362
  e_preventDefault(e);
2348
- var word = findWordAt(cm.doc, pos);
2363
+ var word = findWordAt(cm, pos);
2349
2364
  extendSelection(cm.doc, word.anchor, word.head);
2350
2365
  }));
2351
2366
  else
@@ -2386,26 +2401,6 @@
2386
2401
  // Prevent wrapper from ever scrolling
2387
2402
  on(d.wrapper, "scroll", function() { d.wrapper.scrollTop = d.wrapper.scrollLeft = 0; });
2388
2403
 
2389
- // When the window resizes, we need to refresh active editors.
2390
- var resizeTimer;
2391
- function onResize() {
2392
- if (resizeTimer == null) resizeTimer = setTimeout(function() {
2393
- resizeTimer = null;
2394
- // Might be a text scaling operation, clear size caches.
2395
- d.cachedCharWidth = d.cachedTextHeight = d.cachedPaddingH = knownScrollbarWidth = null;
2396
- cm.setSize();
2397
- }, 100);
2398
- }
2399
- on(window, "resize", onResize);
2400
- // The above handler holds on to the editor and its data
2401
- // structures. Here we poll to unregister it when the editor is no
2402
- // longer in the document, so that it can be garbage-collected.
2403
- function unregister() {
2404
- if (contains(document.body, d.wrapper)) setTimeout(unregister, 5000);
2405
- else off(window, "resize", onResize);
2406
- }
2407
- setTimeout(unregister, 5000);
2408
-
2409
2404
  on(d.input, "keyup", operation(cm, onKeyUp));
2410
2405
  on(d.input, "input", function() {
2411
2406
  if (ie && !ie_upto8 && cm.display.inputHasSelection) cm.display.inputHasSelection = null;
@@ -2482,6 +2477,14 @@
2482
2477
  });
2483
2478
  }
2484
2479
 
2480
+ // Called when the window resizes
2481
+ function onResize(cm) {
2482
+ // Might be a text scaling operation, clear size caches.
2483
+ var d = cm.display;
2484
+ d.cachedCharWidth = d.cachedTextHeight = d.cachedPaddingH = null;
2485
+ cm.setSize();
2486
+ }
2487
+
2485
2488
  // MOUSE EVENTS
2486
2489
 
2487
2490
  // Return true when the given mouse event happened in a widget
@@ -2572,17 +2575,17 @@
2572
2575
  lastClick = {time: now, pos: start};
2573
2576
  }
2574
2577
 
2575
- var sel = cm.doc.sel, addNew = mac ? e.metaKey : e.ctrlKey;
2576
- if (cm.options.dragDrop && dragAndDrop && !addNew && !isReadOnly(cm) &&
2578
+ var sel = cm.doc.sel, modifier = mac ? e.metaKey : e.ctrlKey;
2579
+ if (cm.options.dragDrop && dragAndDrop && !isReadOnly(cm) &&
2577
2580
  type == "single" && sel.contains(start) > -1 && sel.somethingSelected())
2578
- leftButtonStartDrag(cm, e, start);
2581
+ leftButtonStartDrag(cm, e, start, modifier);
2579
2582
  else
2580
- leftButtonSelect(cm, e, start, type, addNew);
2583
+ leftButtonSelect(cm, e, start, type, modifier);
2581
2584
  }
2582
2585
 
2583
2586
  // Start a text drag. When it ends, see if any dragging actually
2584
2587
  // happen, and treat as a click if it didn't.
2585
- function leftButtonStartDrag(cm, e, start) {
2588
+ function leftButtonStartDrag(cm, e, start, modifier) {
2586
2589
  var display = cm.display;
2587
2590
  var dragEnd = operation(cm, function(e2) {
2588
2591
  if (webkit) display.scroller.draggable = false;
@@ -2591,7 +2594,8 @@
2591
2594
  off(display.scroller, "drop", dragEnd);
2592
2595
  if (Math.abs(e.clientX - e2.clientX) + Math.abs(e.clientY - e2.clientY) < 10) {
2593
2596
  e_preventDefault(e2);
2594
- extendSelection(cm.doc, start);
2597
+ if (!modifier)
2598
+ extendSelection(cm.doc, start);
2595
2599
  focusInput(cm);
2596
2600
  // Work around unexplainable focus problem in IE9 (#2127)
2597
2601
  if (ie_upto10 && !ie_upto8)
@@ -2629,7 +2633,7 @@
2629
2633
  start = posFromMouse(cm, e, true, true);
2630
2634
  ourIndex = -1;
2631
2635
  } else if (type == "double") {
2632
- var word = findWordAt(doc, start);
2636
+ var word = findWordAt(cm, start);
2633
2637
  if (cm.display.shift || doc.extend)
2634
2638
  ourRange = extendRange(doc, ourRange, word.anchor, word.head);
2635
2639
  else
@@ -2675,13 +2679,15 @@
2675
2679
  ranges.push(new Range(Pos(line, leftPos), Pos(line, findColumn(text, right, tabSize))));
2676
2680
  }
2677
2681
  if (!ranges.length) ranges.push(new Range(start, start));
2678
- setSelection(doc, normalizeSelection(startSel.ranges.slice(0, ourIndex).concat(ranges), ourIndex), sel_mouse);
2682
+ setSelection(doc, normalizeSelection(startSel.ranges.slice(0, ourIndex).concat(ranges), ourIndex),
2683
+ {origin: "*mouse", scroll: false});
2684
+ cm.scrollIntoView(pos);
2679
2685
  } else {
2680
2686
  var oldRange = ourRange;
2681
2687
  var anchor = oldRange.anchor, head = pos;
2682
2688
  if (type != "single") {
2683
2689
  if (type == "double")
2684
- var range = findWordAt(doc, pos);
2690
+ var range = findWordAt(cm, pos);
2685
2691
  else
2686
2692
  var range = new Range(Pos(pos.line, 0), clipPos(doc, Pos(pos.line + 1, 0)));
2687
2693
  if (cmp(range.anchor, anchor) > 0) {
@@ -2813,7 +2819,8 @@
2813
2819
  try {
2814
2820
  var text = e.dataTransfer.getData("Text");
2815
2821
  if (text) {
2816
- var selected = cm.state.draggingText && cm.listSelections();
2822
+ if (cm.state.draggingText && !(mac ? e.metaKey : e.ctrlKey))
2823
+ var selected = cm.listSelections();
2817
2824
  setSelectionNoUndo(cm.doc, simpleSelection(pos, pos));
2818
2825
  if (selected) for (var i = 0; i < selected.length; ++i)
2819
2826
  replaceRange(cm.doc, "", selected[i].anchor, selected[i].head, "drag");
@@ -3110,7 +3117,7 @@
3110
3117
  // The prevInput test prevents this from firing when a context
3111
3118
  // menu is closed (since the resetInput would kill the
3112
3119
  // select-all detection hack)
3113
- if (!cm.curOp && cm.display.selForContextMenu == cm.doc.sel) {
3120
+ if (!cm.curOp && cm.display.selForContextMenu != cm.doc.sel) {
3114
3121
  resetInput(cm);
3115
3122
  if (webkit) setTimeout(bind(resetInput, cm, true), 0); // Issue #1730
3116
3123
  }
@@ -3130,7 +3137,6 @@
3130
3137
 
3131
3138
  // CONTEXT MENU HANDLING
3132
3139
 
3133
- var detectingSelectAll;
3134
3140
  // To make the context menu work, we need to briefly unhide the
3135
3141
  // textarea (making it as unobtrusive as possible) to let the
3136
3142
  // right-click take effect on it.
@@ -3159,6 +3165,7 @@
3159
3165
  // Adds "Select all" to context menu in FF
3160
3166
  if (!cm.somethingSelected()) display.input.value = display.prevInput = " ";
3161
3167
  display.selForContextMenu = cm.doc.sel;
3168
+ clearTimeout(display.detectingSelectAll);
3162
3169
 
3163
3170
  // Select-all will be greyed out if there's nothing to select, so
3164
3171
  // this adds a zero-width space so that we can later check whether
@@ -3169,6 +3176,9 @@
3169
3176
  var extval = display.input.value = "\u200b" + (selected ? display.input.value : "");
3170
3177
  display.prevInput = selected ? "" : "\u200b";
3171
3178
  display.input.selectionStart = 1; display.input.selectionEnd = extval.length;
3179
+ // Re-set this, in case some other handler touched the
3180
+ // selection in the meantime.
3181
+ display.selForContextMenu = cm.doc.sel;
3172
3182
  }
3173
3183
  }
3174
3184
  function rehide() {
@@ -3180,14 +3190,13 @@
3180
3190
  // Try to detect the user choosing select-all
3181
3191
  if (display.input.selectionStart != null) {
3182
3192
  if (!ie || ie_upto8) prepareSelectAllHack();
3183
- clearTimeout(detectingSelectAll);
3184
3193
  var i = 0, poll = function() {
3185
3194
  if (display.selForContextMenu == cm.doc.sel && display.input.selectionStart == 0)
3186
3195
  operation(cm, commands.selectAll)(cm);
3187
- else if (i++ < 10) detectingSelectAll = setTimeout(poll, 500);
3196
+ else if (i++ < 10) display.detectingSelectAll = setTimeout(poll, 500);
3188
3197
  else resetInput(cm);
3189
3198
  };
3190
- detectingSelectAll = setTimeout(poll, 200);
3199
+ display.detectingSelectAll = setTimeout(poll, 200);
3191
3200
  }
3192
3201
  }
3193
3202
 
@@ -3383,7 +3392,7 @@
3383
3392
 
3384
3393
  var after = i ? computeSelAfterChange(doc, change, null) : lst(source);
3385
3394
  makeChangeSingleDoc(doc, change, after, mergeOldSpans(doc, change));
3386
- if (doc.cm) ensureCursorVisible(doc.cm);
3395
+ if (!i && doc.cm) doc.cm.scrollIntoView(change);
3387
3396
  var rebased = [];
3388
3397
 
3389
3398
  // Propagate to the linked documents
@@ -3400,12 +3409,17 @@
3400
3409
  // Sub-views need their line numbers shifted when text is added
3401
3410
  // above or below them in the parent document.
3402
3411
  function shiftDoc(doc, distance) {
3412
+ if (distance == 0) return;
3403
3413
  doc.first += distance;
3404
3414
  doc.sel = new Selection(map(doc.sel.ranges, function(range) {
3405
3415
  return new Range(Pos(range.anchor.line + distance, range.anchor.ch),
3406
3416
  Pos(range.head.line + distance, range.head.ch));
3407
3417
  }), doc.sel.primIndex);
3408
- if (doc.cm) regChange(doc.cm, doc.first, doc.first - distance, distance);
3418
+ if (doc.cm) {
3419
+ regChange(doc.cm, doc.first, doc.first - distance, distance);
3420
+ for (var d = doc.cm.display, l = d.viewFrom; l < d.viewTo; l++)
3421
+ regLineChange(doc.cm, l, "gutter");
3422
+ }
3409
3423
  }
3410
3424
 
3411
3425
  // More lower-level change function, handling only a single document
@@ -3497,6 +3511,7 @@
3497
3511
  if (changeHandler) signalLater(cm, "change", cm, obj);
3498
3512
  if (changesHandler) (cm.curOp.changeObjs || (cm.curOp.changeObjs = [])).push(obj);
3499
3513
  }
3514
+ cm.display.selForContextMenu = null;
3500
3515
  }
3501
3516
 
3502
3517
  function replaceRange(doc, code, from, to, origin) {
@@ -3764,10 +3779,11 @@
3764
3779
  else if (unit == "column") moveOnce(true);
3765
3780
  else if (unit == "word" || unit == "group") {
3766
3781
  var sawType = null, group = unit == "group";
3782
+ var helper = doc.cm && doc.cm.getHelper(pos, "wordChars");
3767
3783
  for (var first = true;; first = false) {
3768
3784
  if (dir < 0 && !moveOnce(!first)) break;
3769
3785
  var cur = lineObj.text.charAt(ch) || "\n";
3770
- var type = isWordChar(cur) ? "w"
3786
+ var type = isWordChar(cur, helper) ? "w"
3771
3787
  : group && cur == "\n" ? "n"
3772
3788
  : !group || /\s/.test(cur) ? null
3773
3789
  : "p";
@@ -3807,13 +3823,15 @@
3807
3823
  }
3808
3824
 
3809
3825
  // Find the word at the given position (as returned by coordsChar).
3810
- function findWordAt(doc, pos) {
3811
- var line = getLine(doc, pos.line).text;
3826
+ function findWordAt(cm, pos) {
3827
+ var doc = cm.doc, line = getLine(doc, pos.line).text;
3812
3828
  var start = pos.ch, end = pos.ch;
3813
3829
  if (line) {
3830
+ var helper = cm.getHelper(pos, "wordChars");
3814
3831
  if ((pos.xRel < 0 || end == line.length) && start) --start; else ++end;
3815
3832
  var startChar = line.charAt(start);
3816
- var check = isWordChar(startChar) ? isWordChar
3833
+ var check = isWordChar(startChar, helper)
3834
+ ? function(ch) { return isWordChar(ch, helper); }
3817
3835
  : /\s/.test(startChar) ? function(ch) {return /\s/.test(ch);}
3818
3836
  : function(ch) {return !/\s/.test(ch) && !isWordChar(ch);};
3819
3837
  while (start > 0 && check(line.charAt(start - 1))) --start;
@@ -4618,13 +4636,25 @@
4618
4636
  },
4619
4637
  transposeChars: function(cm) {
4620
4638
  runInOp(cm, function() {
4621
- var ranges = cm.listSelections();
4639
+ var ranges = cm.listSelections(), newSel = [];
4622
4640
  for (var i = 0; i < ranges.length; i++) {
4623
4641
  var cur = ranges[i].head, line = getLine(cm.doc, cur.line).text;
4624
- if (cur.ch > 0 && cur.ch < line.length - 1)
4625
- cm.replaceRange(line.charAt(cur.ch) + line.charAt(cur.ch - 1),
4626
- Pos(cur.line, cur.ch - 1), Pos(cur.line, cur.ch + 1));
4642
+ if (line) {
4643
+ if (cur.ch == line.length) cur = new Pos(cur.line, cur.ch - 1);
4644
+ if (cur.ch > 0) {
4645
+ cur = new Pos(cur.line, cur.ch + 1);
4646
+ cm.replaceRange(line.charAt(cur.ch - 1) + line.charAt(cur.ch - 2),
4647
+ Pos(cur.line, cur.ch - 2), cur, "+transpose");
4648
+ } else if (cur.line > cm.doc.first) {
4649
+ var prev = getLine(cm.doc, cur.line - 1).text;
4650
+ if (prev)
4651
+ cm.replaceRange(line.charAt(0) + "\n" + prev.charAt(prev.length - 1),
4652
+ Pos(cur.line - 1, prev.length - 1), Pos(cur.line, 1), "+transpose");
4653
+ }
4654
+ }
4655
+ newSel.push(new Range(cur, cur));
4627
4656
  }
4657
+ cm.setSelections(newSel);
4628
4658
  });
4629
4659
  },
4630
4660
  newlineAndIndent: function(cm) {
@@ -5584,10 +5614,11 @@
5584
5614
  }
5585
5615
 
5586
5616
  function readToken(mode, stream, state) {
5587
- var style = mode.token(stream, state);
5588
- if (stream.pos <= stream.start)
5589
- throw new Error("Mode " + mode.name + " failed to advance stream.");
5590
- return style;
5617
+ for (var i = 0; i < 10; i++) {
5618
+ var style = mode.token(stream, state);
5619
+ if (stream.pos > stream.start) return style;
5620
+ }
5621
+ throw new Error("Mode " + mode.name + " failed to advance stream.");
5591
5622
  }
5592
5623
 
5593
5624
  // Run the given mode's parser over a line, calling f for each token.
@@ -5749,6 +5780,8 @@
5749
5780
  }
5750
5781
 
5751
5782
  signal(cm, "renderLine", cm, lineView.line, builder.pre);
5783
+ if (builder.pre.className)
5784
+ builder.textClass = joinClasses(builder.pre.className, builder.textClass || "");
5752
5785
  return builder;
5753
5786
  }
5754
5787
 
@@ -7053,10 +7086,15 @@
7053
7086
  }
7054
7087
 
7055
7088
  var nonASCIISingleCaseWordChar = /[\u00df\u3040-\u309f\u30a0-\u30ff\u3400-\u4db5\u4e00-\u9fcc\uac00-\ud7af]/;
7056
- var isWordChar = CodeMirror.isWordChar = function(ch) {
7089
+ var isWordCharBasic = CodeMirror.isWordChar = function(ch) {
7057
7090
  return /\w/.test(ch) || ch > "\x80" &&
7058
7091
  (ch.toUpperCase() != ch.toLowerCase() || nonASCIISingleCaseWordChar.test(ch));
7059
7092
  };
7093
+ function isWordChar(ch, helper) {
7094
+ if (!helper) return isWordCharBasic(ch);
7095
+ if (helper.source.indexOf("\\w") > -1 && isWordCharBasic(ch)) return true;
7096
+ return helper.test(ch);
7097
+ }
7060
7098
 
7061
7099
  function isEmpty(obj) {
7062
7100
  for (var n in obj) if (obj.hasOwnProperty(n) && obj[n]) return false;
@@ -7138,6 +7176,43 @@
7138
7176
  return b;
7139
7177
  }
7140
7178
 
7179
+ // WINDOW-WIDE EVENTS
7180
+
7181
+ // These must be handled carefully, because naively registering a
7182
+ // handler for each editor will cause the editors to never be
7183
+ // garbage collected.
7184
+
7185
+ function forEachCodeMirror(f) {
7186
+ if (!document.body.getElementsByClassName) return;
7187
+ var byClass = document.body.getElementsByClassName("CodeMirror");
7188
+ for (var i = 0; i < byClass.length; i++) {
7189
+ var cm = byClass[i].CodeMirror;
7190
+ if (cm) f(cm);
7191
+ }
7192
+ }
7193
+
7194
+ var globalsRegistered = false;
7195
+ function ensureGlobalHandlers() {
7196
+ if (globalsRegistered) return;
7197
+ registerGlobalHandlers();
7198
+ globalsRegistered = true;
7199
+ }
7200
+ function registerGlobalHandlers() {
7201
+ // When the window resizes, we need to refresh active editors.
7202
+ var resizeTimer;
7203
+ on(window, "resize", function() {
7204
+ if (resizeTimer == null) resizeTimer = setTimeout(function() {
7205
+ resizeTimer = null;
7206
+ knownScrollbarWidth = null;
7207
+ forEachCodeMirror(onResize);
7208
+ }, 100);
7209
+ });
7210
+ // When the window loses focus, we want to show the editor as blurred
7211
+ on(window, "blur", function() {
7212
+ forEachCodeMirror(onBlur);
7213
+ });
7214
+ }
7215
+
7141
7216
  // FEATURE DETECTION
7142
7217
 
7143
7218
  // Detect drag-and-drop
@@ -7520,7 +7595,7 @@
7520
7595
 
7521
7596
  // THE END
7522
7597
 
7523
- CodeMirror.version = "4.1.0";
7598
+ CodeMirror.version = "4.2.0";
7524
7599
 
7525
7600
  return CodeMirror;
7526
7601
  });