codemirror-rails 4.2 → 4.3

Sign up to get free protection for your applications and to get access to all the features.
Files changed (162) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +1 -1
  3. data/.travis.yml +10 -0
  4. data/codemirror-rails.gemspec +3 -4
  5. data/gemfiles/Gemfile.rails-3.2 +5 -0
  6. data/gemfiles/Gemfile.rails-4.0 +4 -0
  7. data/gemfiles/Gemfile.rails-4.1 +4 -0
  8. data/lib/codemirror/rails/version.rb +2 -2
  9. data/test/{dummy → dummy-3.2.x}/README.rdoc +0 -0
  10. data/test/{dummy → dummy-3.2.x}/Rakefile +0 -0
  11. data/test/{dummy → dummy-3.2.x}/app/assets/javascripts/application.js +0 -0
  12. data/test/{dummy → dummy-3.2.x}/app/assets/stylesheets/application.css +0 -0
  13. data/test/{dummy → dummy-3.2.x}/app/controllers/application_controller.rb +0 -0
  14. data/test/{dummy → dummy-3.2.x}/app/helpers/application_helper.rb +0 -0
  15. data/test/{dummy → dummy-3.2.x}/app/mailers/.gitkeep +0 -0
  16. data/test/{dummy → dummy-3.2.x}/app/models/.gitkeep +0 -0
  17. data/test/{dummy → dummy-3.2.x}/app/views/layouts/application.html.erb +0 -0
  18. data/test/{dummy → dummy-3.2.x}/config.ru +0 -0
  19. data/test/{dummy → dummy-3.2.x}/config/application.rb +0 -0
  20. data/test/{dummy → dummy-3.2.x}/config/boot.rb +0 -0
  21. data/test/{dummy → dummy-3.2.x}/config/database.yml +0 -0
  22. data/test/{dummy → dummy-3.2.x}/config/environment.rb +0 -0
  23. data/test/{dummy → dummy-3.2.x}/config/environments/development.rb +0 -0
  24. data/test/{dummy → dummy-3.2.x}/config/environments/production.rb +0 -0
  25. data/test/{dummy → dummy-3.2.x}/config/environments/test.rb +0 -0
  26. data/test/{dummy → dummy-3.2.x}/config/initializers/backtrace_silencers.rb +0 -0
  27. data/test/{dummy → dummy-3.2.x}/config/initializers/inflections.rb +0 -0
  28. data/test/{dummy → dummy-3.2.x}/config/initializers/mime_types.rb +0 -0
  29. data/test/{dummy → dummy-3.2.x}/config/initializers/secret_token.rb +0 -0
  30. data/test/{dummy → dummy-3.2.x}/config/initializers/session_store.rb +0 -0
  31. data/test/{dummy → dummy-3.2.x}/config/initializers/wrap_parameters.rb +0 -0
  32. data/test/{dummy → dummy-3.2.x}/config/locales/en.yml +0 -0
  33. data/test/{dummy → dummy-3.2.x}/config/routes.rb +0 -0
  34. data/test/{dummy → dummy-3.2.x}/db/.gitkeep +0 -0
  35. data/test/{dummy → dummy-3.2.x}/lib/assets/.gitkeep +0 -0
  36. data/test/{dummy → dummy-3.2.x}/log/.gitkeep +0 -0
  37. data/test/{dummy → dummy-3.2.x}/public/404.html +0 -0
  38. data/test/{dummy → dummy-3.2.x}/public/422.html +0 -0
  39. data/test/{dummy → dummy-3.2.x}/public/500.html +0 -0
  40. data/test/{dummy → dummy-3.2.x}/public/favicon.ico +0 -0
  41. data/test/{dummy → dummy-3.2.x}/script/rails +0 -0
  42. data/test/dummy-4.0.x/README.rdoc +28 -0
  43. data/test/dummy-4.0.x/Rakefile +6 -0
  44. data/test/dummy-4.0.x/app/assets/images/.keep +0 -0
  45. data/test/dummy-4.0.x/app/assets/javascripts/application.js +13 -0
  46. data/test/dummy-4.0.x/app/assets/stylesheets/application.css +13 -0
  47. data/test/dummy-4.0.x/app/controllers/application_controller.rb +5 -0
  48. data/test/dummy-4.0.x/app/controllers/concerns/.keep +0 -0
  49. data/test/dummy-4.0.x/app/helpers/application_helper.rb +2 -0
  50. data/test/dummy-4.0.x/app/mailers/.keep +0 -0
  51. data/test/dummy-4.0.x/app/models/.keep +0 -0
  52. data/test/dummy-4.0.x/app/models/concerns/.keep +0 -0
  53. data/test/dummy-4.0.x/app/views/layouts/application.html.erb +14 -0
  54. data/test/dummy-4.0.x/bin/bundle +3 -0
  55. data/test/dummy-4.0.x/bin/rails +4 -0
  56. data/test/dummy-4.0.x/bin/rake +4 -0
  57. data/test/dummy-4.0.x/config.ru +4 -0
  58. data/test/dummy-4.0.x/config/application.rb +23 -0
  59. data/test/dummy-4.0.x/config/boot.rb +5 -0
  60. data/test/dummy-4.0.x/config/database.yml +25 -0
  61. data/test/dummy-4.0.x/config/environment.rb +5 -0
  62. data/test/dummy-4.0.x/config/environments/development.rb +29 -0
  63. data/test/dummy-4.0.x/config/environments/production.rb +80 -0
  64. data/test/dummy-4.0.x/config/environments/test.rb +36 -0
  65. data/test/dummy-4.0.x/config/initializers/backtrace_silencers.rb +7 -0
  66. data/test/dummy-4.0.x/config/initializers/filter_parameter_logging.rb +4 -0
  67. data/test/dummy-4.0.x/config/initializers/inflections.rb +16 -0
  68. data/test/dummy-4.0.x/config/initializers/mime_types.rb +5 -0
  69. data/test/dummy-4.0.x/config/initializers/secret_token.rb +12 -0
  70. data/test/dummy-4.0.x/config/initializers/session_store.rb +3 -0
  71. data/test/dummy-4.0.x/config/initializers/wrap_parameters.rb +14 -0
  72. data/test/dummy-4.0.x/config/locales/en.yml +23 -0
  73. data/test/dummy-4.0.x/config/routes.rb +56 -0
  74. data/test/dummy-4.0.x/lib/assets/.keep +0 -0
  75. data/test/dummy-4.0.x/log/.keep +0 -0
  76. data/test/dummy-4.0.x/public/404.html +58 -0
  77. data/test/dummy-4.0.x/public/422.html +58 -0
  78. data/test/dummy-4.0.x/public/500.html +57 -0
  79. data/test/dummy-4.0.x/public/favicon.ico +0 -0
  80. data/test/dummy-4.1.x/README.rdoc +28 -0
  81. data/test/dummy-4.1.x/Rakefile +6 -0
  82. data/test/dummy-4.1.x/app/assets/images/.keep +0 -0
  83. data/test/dummy-4.1.x/app/assets/javascripts/application.js +13 -0
  84. data/test/dummy-4.1.x/app/assets/stylesheets/application.css +15 -0
  85. data/test/dummy-4.1.x/app/controllers/application_controller.rb +5 -0
  86. data/test/dummy-4.1.x/app/controllers/concerns/.keep +0 -0
  87. data/test/dummy-4.1.x/app/helpers/application_helper.rb +2 -0
  88. data/test/dummy-4.1.x/app/mailers/.keep +0 -0
  89. data/test/dummy-4.1.x/app/models/.keep +0 -0
  90. data/test/dummy-4.1.x/app/models/concerns/.keep +0 -0
  91. data/test/dummy-4.1.x/app/views/layouts/application.html.erb +14 -0
  92. data/test/dummy-4.1.x/bin/bundle +3 -0
  93. data/test/dummy-4.1.x/bin/rails +4 -0
  94. data/test/dummy-4.1.x/bin/rake +4 -0
  95. data/test/dummy-4.1.x/config.ru +4 -0
  96. data/test/dummy-4.1.x/config/application.rb +23 -0
  97. data/test/dummy-4.1.x/config/boot.rb +5 -0
  98. data/test/dummy-4.1.x/config/database.yml +25 -0
  99. data/test/dummy-4.1.x/config/environment.rb +5 -0
  100. data/test/dummy-4.1.x/config/environments/development.rb +37 -0
  101. data/test/dummy-4.1.x/config/environments/production.rb +82 -0
  102. data/test/dummy-4.1.x/config/environments/test.rb +39 -0
  103. data/test/dummy-4.1.x/config/initializers/assets.rb +8 -0
  104. data/test/dummy-4.1.x/config/initializers/backtrace_silencers.rb +7 -0
  105. data/test/dummy-4.1.x/config/initializers/cookies_serializer.rb +3 -0
  106. data/test/dummy-4.1.x/config/initializers/filter_parameter_logging.rb +4 -0
  107. data/test/dummy-4.1.x/config/initializers/inflections.rb +16 -0
  108. data/test/dummy-4.1.x/config/initializers/mime_types.rb +4 -0
  109. data/test/dummy-4.1.x/config/initializers/session_store.rb +3 -0
  110. data/test/dummy-4.1.x/config/initializers/wrap_parameters.rb +14 -0
  111. data/test/dummy-4.1.x/config/locales/en.yml +23 -0
  112. data/test/dummy-4.1.x/config/routes.rb +56 -0
  113. data/test/dummy-4.1.x/config/secrets.yml +22 -0
  114. data/test/dummy-4.1.x/lib/assets/.keep +0 -0
  115. data/test/dummy-4.1.x/log/.keep +0 -0
  116. data/test/dummy-4.1.x/public/404.html +67 -0
  117. data/test/dummy-4.1.x/public/422.html +67 -0
  118. data/test/dummy-4.1.x/public/500.html +66 -0
  119. data/test/dummy-4.1.x/public/favicon.ico +0 -0
  120. data/test/integration/codemirror_rails_integration_test.rb +6 -4
  121. data/test/test_helper.rb +10 -7
  122. data/vendor/assets/javascripts/codemirror.js +131 -94
  123. data/vendor/assets/javascripts/codemirror/addons/dialog/dialog.js +8 -4
  124. data/vendor/assets/javascripts/codemirror/addons/display/rulers.js +1 -1
  125. data/vendor/assets/javascripts/codemirror/addons/edit/continuelist.js +1 -1
  126. data/vendor/assets/javascripts/codemirror/addons/fold/foldgutter.js +1 -1
  127. data/vendor/assets/javascripts/codemirror/addons/hint/xml-hint.js +7 -0
  128. data/vendor/assets/javascripts/codemirror/addons/selection/active-line.js +3 -1
  129. data/vendor/assets/javascripts/codemirror/addons/tern/tern.js +3 -2
  130. data/vendor/assets/javascripts/codemirror/keymaps/vim.js +301 -88
  131. data/vendor/assets/javascripts/codemirror/modes/clike.js +6 -6
  132. data/vendor/assets/javascripts/codemirror/modes/css.js +3 -3
  133. data/vendor/assets/javascripts/codemirror/modes/cypher.js +1 -1
  134. data/vendor/assets/javascripts/codemirror/modes/javascript.js +29 -9
  135. data/vendor/assets/javascripts/codemirror/modes/python.js +3 -1
  136. data/vendor/assets/stylesheets/codemirror.css +29 -0
  137. data/vendor/assets/stylesheets/codemirror/addons/fold/foldgutter.css +0 -1
  138. data/vendor/assets/stylesheets/codemirror/themes/3024-day.css +4 -0
  139. data/vendor/assets/stylesheets/codemirror/themes/3024-night.css +3 -0
  140. data/vendor/assets/stylesheets/codemirror/themes/ambiance.css +4 -1
  141. data/vendor/assets/stylesheets/codemirror/themes/base16-dark.css +2 -0
  142. data/vendor/assets/stylesheets/codemirror/themes/base16-light.css +2 -0
  143. data/vendor/assets/stylesheets/codemirror/themes/blackboard.css +2 -0
  144. data/vendor/assets/stylesheets/codemirror/themes/cobalt.css +2 -0
  145. data/vendor/assets/stylesheets/codemirror/themes/erlang-dark.css +2 -0
  146. data/vendor/assets/stylesheets/codemirror/themes/lesser-dark.css +2 -0
  147. data/vendor/assets/stylesheets/codemirror/themes/mbo.css +4 -2
  148. data/vendor/assets/stylesheets/codemirror/themes/midnight.css +2 -0
  149. data/vendor/assets/stylesheets/codemirror/themes/monokai.css +2 -0
  150. data/vendor/assets/stylesheets/codemirror/themes/neo.css +3 -0
  151. data/vendor/assets/stylesheets/codemirror/themes/night.css +2 -0
  152. data/vendor/assets/stylesheets/codemirror/themes/paraiso-dark.css +2 -0
  153. data/vendor/assets/stylesheets/codemirror/themes/paraiso-light.css +2 -0
  154. data/vendor/assets/stylesheets/codemirror/themes/pastel-on-dark.css +2 -0
  155. data/vendor/assets/stylesheets/codemirror/themes/rubyblue.css +2 -0
  156. data/vendor/assets/stylesheets/codemirror/themes/solarized.css +3 -0
  157. data/vendor/assets/stylesheets/codemirror/themes/the-matrix.css +2 -0
  158. data/vendor/assets/stylesheets/codemirror/themes/tomorrow-night-eighties.css +2 -0
  159. data/vendor/assets/stylesheets/codemirror/themes/twilight.css +2 -0
  160. data/vendor/assets/stylesheets/codemirror/themes/vibrant-ink.css +2 -0
  161. data/vendor/assets/stylesheets/codemirror/themes/xq-dark.css +2 -0
  162. metadata +135 -73
@@ -0,0 +1,22 @@
1
+ # Be sure to restart your server when you modify this file.
2
+
3
+ # Your secret key is used for verifying the integrity of signed cookies.
4
+ # If you change this key, all old signed cookies will become invalid!
5
+
6
+ # Make sure the secret is at least 30 characters and all random,
7
+ # no regular words or you'll be exposed to dictionary attacks.
8
+ # You can use `rake secret` to generate a secure secret key.
9
+
10
+ # Make sure the secrets in this file are kept private
11
+ # if you're sharing your code publicly.
12
+
13
+ development:
14
+ secret_key_base: f0e4e041743de2d6246bfe53493e444c3aa63a0b2bc348c660346f8a9fa36a38aae2b0d4afef263ca1cb597c2aa7d2cf660ef1bb813ac80f35602b99212aa59d
15
+
16
+ test:
17
+ secret_key_base: b7df7801dddcc9790549d4753167aea56483b33322e835eb629e88e6228229f55046a5261c2d22507cb84a5b7d05208115e721f3799cf1ff11b78ec98b654582
18
+
19
+ # Do not keep production secrets in the repository,
20
+ # instead read values from the environment.
21
+ production:
22
+ secret_key_base: <%= ENV["SECRET_KEY_BASE"] %>
File without changes
File without changes
@@ -0,0 +1,67 @@
1
+ <!DOCTYPE html>
2
+ <html>
3
+ <head>
4
+ <title>The page you were looking for doesn't exist (404)</title>
5
+ <meta name="viewport" content="width=device-width,initial-scale=1">
6
+ <style>
7
+ body {
8
+ background-color: #EFEFEF;
9
+ color: #2E2F30;
10
+ text-align: center;
11
+ font-family: arial, sans-serif;
12
+ margin: 0;
13
+ }
14
+
15
+ div.dialog {
16
+ width: 95%;
17
+ max-width: 33em;
18
+ margin: 4em auto 0;
19
+ }
20
+
21
+ div.dialog > div {
22
+ border: 1px solid #CCC;
23
+ border-right-color: #999;
24
+ border-left-color: #999;
25
+ border-bottom-color: #BBB;
26
+ border-top: #B00100 solid 4px;
27
+ border-top-left-radius: 9px;
28
+ border-top-right-radius: 9px;
29
+ background-color: white;
30
+ padding: 7px 12% 0;
31
+ box-shadow: 0 3px 8px rgba(50, 50, 50, 0.17);
32
+ }
33
+
34
+ h1 {
35
+ font-size: 100%;
36
+ color: #730E15;
37
+ line-height: 1.5em;
38
+ }
39
+
40
+ div.dialog > p {
41
+ margin: 0 0 1em;
42
+ padding: 1em;
43
+ background-color: #F7F7F7;
44
+ border: 1px solid #CCC;
45
+ border-right-color: #999;
46
+ border-left-color: #999;
47
+ border-bottom-color: #999;
48
+ border-bottom-left-radius: 4px;
49
+ border-bottom-right-radius: 4px;
50
+ border-top-color: #DADADA;
51
+ color: #666;
52
+ box-shadow: 0 3px 8px rgba(50, 50, 50, 0.17);
53
+ }
54
+ </style>
55
+ </head>
56
+
57
+ <body>
58
+ <!-- This file lives in public/404.html -->
59
+ <div class="dialog">
60
+ <div>
61
+ <h1>The page you were looking for doesn't exist.</h1>
62
+ <p>You may have mistyped the address or the page may have moved.</p>
63
+ </div>
64
+ <p>If you are the application owner check the logs for more information.</p>
65
+ </div>
66
+ </body>
67
+ </html>
@@ -0,0 +1,67 @@
1
+ <!DOCTYPE html>
2
+ <html>
3
+ <head>
4
+ <title>The change you wanted was rejected (422)</title>
5
+ <meta name="viewport" content="width=device-width,initial-scale=1">
6
+ <style>
7
+ body {
8
+ background-color: #EFEFEF;
9
+ color: #2E2F30;
10
+ text-align: center;
11
+ font-family: arial, sans-serif;
12
+ margin: 0;
13
+ }
14
+
15
+ div.dialog {
16
+ width: 95%;
17
+ max-width: 33em;
18
+ margin: 4em auto 0;
19
+ }
20
+
21
+ div.dialog > div {
22
+ border: 1px solid #CCC;
23
+ border-right-color: #999;
24
+ border-left-color: #999;
25
+ border-bottom-color: #BBB;
26
+ border-top: #B00100 solid 4px;
27
+ border-top-left-radius: 9px;
28
+ border-top-right-radius: 9px;
29
+ background-color: white;
30
+ padding: 7px 12% 0;
31
+ box-shadow: 0 3px 8px rgba(50, 50, 50, 0.17);
32
+ }
33
+
34
+ h1 {
35
+ font-size: 100%;
36
+ color: #730E15;
37
+ line-height: 1.5em;
38
+ }
39
+
40
+ div.dialog > p {
41
+ margin: 0 0 1em;
42
+ padding: 1em;
43
+ background-color: #F7F7F7;
44
+ border: 1px solid #CCC;
45
+ border-right-color: #999;
46
+ border-left-color: #999;
47
+ border-bottom-color: #999;
48
+ border-bottom-left-radius: 4px;
49
+ border-bottom-right-radius: 4px;
50
+ border-top-color: #DADADA;
51
+ color: #666;
52
+ box-shadow: 0 3px 8px rgba(50, 50, 50, 0.17);
53
+ }
54
+ </style>
55
+ </head>
56
+
57
+ <body>
58
+ <!-- This file lives in public/422.html -->
59
+ <div class="dialog">
60
+ <div>
61
+ <h1>The change you wanted was rejected.</h1>
62
+ <p>Maybe you tried to change something you didn't have access to.</p>
63
+ </div>
64
+ <p>If you are the application owner check the logs for more information.</p>
65
+ </div>
66
+ </body>
67
+ </html>
@@ -0,0 +1,66 @@
1
+ <!DOCTYPE html>
2
+ <html>
3
+ <head>
4
+ <title>We're sorry, but something went wrong (500)</title>
5
+ <meta name="viewport" content="width=device-width,initial-scale=1">
6
+ <style>
7
+ body {
8
+ background-color: #EFEFEF;
9
+ color: #2E2F30;
10
+ text-align: center;
11
+ font-family: arial, sans-serif;
12
+ margin: 0;
13
+ }
14
+
15
+ div.dialog {
16
+ width: 95%;
17
+ max-width: 33em;
18
+ margin: 4em auto 0;
19
+ }
20
+
21
+ div.dialog > div {
22
+ border: 1px solid #CCC;
23
+ border-right-color: #999;
24
+ border-left-color: #999;
25
+ border-bottom-color: #BBB;
26
+ border-top: #B00100 solid 4px;
27
+ border-top-left-radius: 9px;
28
+ border-top-right-radius: 9px;
29
+ background-color: white;
30
+ padding: 7px 12% 0;
31
+ box-shadow: 0 3px 8px rgba(50, 50, 50, 0.17);
32
+ }
33
+
34
+ h1 {
35
+ font-size: 100%;
36
+ color: #730E15;
37
+ line-height: 1.5em;
38
+ }
39
+
40
+ div.dialog > p {
41
+ margin: 0 0 1em;
42
+ padding: 1em;
43
+ background-color: #F7F7F7;
44
+ border: 1px solid #CCC;
45
+ border-right-color: #999;
46
+ border-left-color: #999;
47
+ border-bottom-color: #999;
48
+ border-bottom-left-radius: 4px;
49
+ border-bottom-right-radius: 4px;
50
+ border-top-color: #DADADA;
51
+ color: #666;
52
+ box-shadow: 0 3px 8px rgba(50, 50, 50, 0.17);
53
+ }
54
+ </style>
55
+ </head>
56
+
57
+ <body>
58
+ <!-- This file lives in public/500.html -->
59
+ <div class="dialog">
60
+ <div>
61
+ <h1>We're sorry, but something went wrong.</h1>
62
+ </div>
63
+ <p>If you are the application owner check the logs for more information.</p>
64
+ </div>
65
+ </body>
66
+ </html>
File without changes
@@ -2,12 +2,14 @@ require 'test_helper'
2
2
 
3
3
  describe 'codemiror-rails integration' do
4
4
  it 'provides codemirror.js on the asset pipeline' do
5
- visit '/assets/codemirror.js'
6
- page.text.must_include 'window.CodeMirror'
5
+ asset_file('codemirror.js').must_include 'function CodeMirror'
7
6
  end
8
7
 
9
8
  it 'provides codemirror css on the asset pipeline' do
10
- visit '/assets/codemirror.css'
11
- page.text.must_include '.CodeMirror'
9
+ asset_file('codemirror.css').must_include '.CodeMirror'
10
+ end
11
+
12
+ def asset_file(name)
13
+ Dummy::Application.assets[name].to_s
12
14
  end
13
15
  end
data/test/test_helper.rb CHANGED
@@ -1,13 +1,16 @@
1
1
  ENV['RAILS_ENV'] = 'test'
2
2
 
3
- require File.expand_path('../dummy/config/environment.rb', __FILE__)
3
+ require 'rails/version'
4
+ case "#{Rails::VERSION::MAJOR}.#{Rails::VERSION::MINOR}"
5
+ when '3.2'
6
+ require File.expand_path('../dummy-3.2.x/config/environment', __FILE__)
7
+ when '4.0'
8
+ require File.expand_path('../dummy-4.0.x/config/environment', __FILE__)
9
+ when '4.1'
10
+ require File.expand_path('../dummy-4.1.x/config/environment', __FILE__)
11
+ end
12
+
4
13
  require 'rails/test_help'
5
14
  require 'minitest/autorun'
6
- require 'capybara/rails'
7
15
 
8
16
  Rails.backtrace_cleaner.remove_silencers!
9
-
10
- class IntegrationTest < MiniTest::Spec
11
- include Capybara::DSL
12
- register_spec_type(/integration$/, self)
13
- end
@@ -25,11 +25,9 @@
25
25
  var gecko = /gecko\/\d/i.test(navigator.userAgent);
26
26
  // ie_uptoN means Internet Explorer version N or lower
27
27
  var ie_upto10 = /MSIE \d/.test(navigator.userAgent);
28
- var ie_upto7 = ie_upto10 && (document.documentMode == null || document.documentMode < 8);
29
- var ie_upto8 = ie_upto10 && (document.documentMode == null || document.documentMode < 9);
30
- var ie_upto9 = ie_upto10 && (document.documentMode == null || document.documentMode < 10);
31
- var ie_11up = /Trident\/([7-9]|\d{2,})\./.test(navigator.userAgent);
28
+ var ie_11up = /Trident\/(?:[7-9]|\d{2,})\..*rv:(\d+)/.exec(navigator.userAgent);
32
29
  var ie = ie_upto10 || ie_11up;
30
+ var ie_version = ie && (ie_upto10 ? document.documentMode || 6 : ie_11up[1]);
33
31
  var webkit = /WebKit\//.test(navigator.userAgent);
34
32
  var qtwebkit = webkit && /Qt\/\d+\.\d+/.test(navigator.userAgent);
35
33
  var chrome = /Chrome\//.test(navigator.userAgent);
@@ -50,7 +48,7 @@
50
48
  if (presto_version && presto_version >= 15) { presto = false; webkit = true; }
51
49
  // Some browsers use the wrong event properties to signal cmd/ctrl on OS X
52
50
  var flipCtrlCmd = mac && (qtwebkit || presto && (presto_version == null || presto_version < 12.11));
53
- var captureRightClick = gecko || (ie && !ie_upto8);
51
+ var captureRightClick = gecko || (ie && ie_version >= 9);
54
52
 
55
53
  // Optimize some code when these features are not used.
56
54
  var sawReadOnlySpans = false, sawCollapsedSpans = false;
@@ -93,7 +91,7 @@
93
91
 
94
92
  // Override magic textarea content restore that IE sometimes does
95
93
  // on our hidden textarea on reload
96
- if (ie_upto10) setTimeout(bind(resetInput, this, true), 20);
94
+ if (ie && ie_version < 11) setTimeout(bind(resetInput, this, true), 20);
97
95
 
98
96
  registerEventHandlers(this);
99
97
  ensureGlobalHandlers();
@@ -177,14 +175,14 @@
177
175
  d.scrollbarFiller, d.gutterFiller, d.scroller], "CodeMirror");
178
176
 
179
177
  // Work around IE7 z-index bug (not perfect, hence IE7 not really being supported)
180
- if (ie_upto7) { d.gutters.style.zIndex = -1; d.scroller.style.paddingRight = 0; }
178
+ if (ie && ie_version < 8) { d.gutters.style.zIndex = -1; d.scroller.style.paddingRight = 0; }
181
179
  // Needed to hide big blue blinking cursor on Mobile Safari
182
180
  if (ios) input.style.width = "0px";
183
181
  if (!webkit) d.scroller.draggable = true;
184
182
  // Needed to handle Tab key in KHTML
185
183
  if (khtml) { d.inputDiv.style.height = "1px"; d.inputDiv.style.position = "absolute"; }
186
184
  // Need to set a minimum width to see the scrollbar on IE7 (but must not set it on IE8).
187
- if (ie_upto7) d.scrollbarH.style.minHeight = d.scrollbarV.style.minWidth = "18px";
185
+ if (ie && ie_version < 8) d.scrollbarH.style.minHeight = d.scrollbarV.style.minWidth = "18px";
188
186
 
189
187
  if (place.appendChild) place.appendChild(d.wrapper);
190
188
  else place(d.wrapper);
@@ -394,6 +392,10 @@
394
392
 
395
393
  // SCROLLBARS
396
394
 
395
+ function hScrollbarTakesSpace(cm) {
396
+ return cm.display.scroller.clientHeight - cm.display.wrapper.clientHeight < scrollerCutOff - 3;
397
+ }
398
+
397
399
  // Prepare DOM reads needed to update the scrollbars. Done in one
398
400
  // shot to minimize update/measure roundtrips.
399
401
  function measureForScrollbars(cm) {
@@ -402,6 +404,7 @@
402
404
  clientHeight: scroll.clientHeight,
403
405
  barHeight: cm.display.scrollbarV.clientHeight,
404
406
  scrollWidth: scroll.scrollWidth, clientWidth: scroll.clientWidth,
407
+ hScrollbarTakesSpace: hScrollbarTakesSpace(cm),
405
408
  barWidth: cm.display.scrollbarH.clientWidth,
406
409
  docHeight: Math.round(cm.doc.height + paddingVert(cm.display))
407
410
  };
@@ -411,13 +414,17 @@
411
414
  // content.
412
415
  function updateScrollbars(cm, measure) {
413
416
  if (!measure) measure = measureForScrollbars(cm);
414
- var d = cm.display;
417
+ var d = cm.display, sWidth = scrollbarWidth(d.measure);
415
418
  var scrollHeight = measure.docHeight + scrollerCutOff;
416
419
  var needsH = measure.scrollWidth > measure.clientWidth;
420
+ if (needsH && measure.scrollWidth <= measure.clientWidth + 1 &&
421
+ sWidth > 0 && !measure.hScrollbarTakesSpace)
422
+ needsH = false; // (Issue #2562)
417
423
  var needsV = scrollHeight > measure.clientHeight;
424
+
418
425
  if (needsV) {
419
426
  d.scrollbarV.style.display = "block";
420
- d.scrollbarV.style.bottom = needsH ? scrollbarWidth(d.measure) + "px" : "0";
427
+ d.scrollbarV.style.bottom = needsH ? sWidth + "px" : "0";
421
428
  // A bug in IE8 can cause this value to be negative, so guard it.
422
429
  d.scrollbarV.firstChild.style.height =
423
430
  Math.max(0, scrollHeight - measure.clientHeight + (measure.barHeight || d.scrollbarV.clientHeight)) + "px";
@@ -427,7 +434,7 @@
427
434
  }
428
435
  if (needsH) {
429
436
  d.scrollbarH.style.display = "block";
430
- d.scrollbarH.style.right = needsV ? scrollbarWidth(d.measure) + "px" : "0";
437
+ d.scrollbarH.style.right = needsV ? sWidth + "px" : "0";
431
438
  d.scrollbarH.firstChild.style.width =
432
439
  (measure.scrollWidth - measure.clientWidth + (measure.barWidth || d.scrollbarH.clientWidth)) + "px";
433
440
  } else {
@@ -436,16 +443,16 @@
436
443
  }
437
444
  if (needsH && needsV) {
438
445
  d.scrollbarFiller.style.display = "block";
439
- d.scrollbarFiller.style.height = d.scrollbarFiller.style.width = scrollbarWidth(d.measure) + "px";
446
+ d.scrollbarFiller.style.height = d.scrollbarFiller.style.width = sWidth + "px";
440
447
  } else d.scrollbarFiller.style.display = "";
441
448
  if (needsH && cm.options.coverGutterNextToScrollbar && cm.options.fixedGutter) {
442
449
  d.gutterFiller.style.display = "block";
443
- d.gutterFiller.style.height = scrollbarWidth(d.measure) + "px";
450
+ d.gutterFiller.style.height = sWidth + "px";
444
451
  d.gutterFiller.style.width = d.gutters.offsetWidth + "px";
445
452
  } else d.gutterFiller.style.display = "";
446
453
 
447
454
  if (!cm.state.checkedOverlayScrollbar && measure.clientHeight > 0) {
448
- if (scrollbarWidth(d.measure) === 0) {
455
+ if (sWidth === 0) {
449
456
  var w = mac && !mac_geMountainLion ? "12px" : "18px";
450
457
  d.scrollbarV.style.minWidth = d.scrollbarH.style.minHeight = w;
451
458
  var barMouseDown = function(e) {
@@ -560,6 +567,10 @@
560
567
  updateScrollbars(cm, barMeasure);
561
568
  if (webkit && cm.options.lineWrapping)
562
569
  checkForWebkitWidthBug(cm, barMeasure); // (Issue #2420)
570
+ if (webkit && barMeasure.scrollWidth > barMeasure.clientWidth &&
571
+ barMeasure.scrollWidth < barMeasure.clientWidth + 1 &&
572
+ !hScrollbarTakesSpace(cm))
573
+ updateScrollbars(cm); // (Issue #2562)
563
574
  if (first && cm.options.lineWrapping && oldWidth != cm.display.scroller.clientWidth) {
564
575
  forced = true;
565
576
  continue;
@@ -597,6 +608,7 @@
597
608
 
598
609
  // Bail out if the visible area is already rendered and nothing changed.
599
610
  if (!forced && visible.from >= display.viewFrom && visible.to <= display.viewTo &&
611
+ (display.updateLineNumbers == null || display.updateLineNumbers >= display.viewTo) &&
600
612
  countDirtyView(cm) == 0)
601
613
  return;
602
614
 
@@ -684,7 +696,7 @@
684
696
  for (var i = 0; i < display.view.length; i++) {
685
697
  var cur = display.view[i], height;
686
698
  if (cur.hidden) continue;
687
- if (ie_upto7) {
699
+ if (ie && ie_version < 8) {
688
700
  var bot = cur.node.offsetTop + cur.node.offsetHeight;
689
701
  height = bot - prevBottom;
690
702
  prevBottom = bot;
@@ -793,7 +805,7 @@
793
805
  if (lineView.text.parentNode)
794
806
  lineView.text.parentNode.replaceChild(lineView.node, lineView.text);
795
807
  lineView.node.appendChild(lineView.text);
796
- if (ie_upto7) lineView.node.style.zIndex = 2;
808
+ if (ie && ie_version < 8) lineView.node.style.zIndex = 2;
797
809
  }
798
810
  return lineView.node;
799
811
  }
@@ -1277,7 +1289,7 @@
1277
1289
 
1278
1290
  // Draws a cursor for the given range
1279
1291
  function drawSelectionCursor(cm, range, output) {
1280
- var pos = cursorCoords(cm, range.head, "div");
1292
+ var pos = cursorCoords(cm, range.head, "div", null, null, !cm.options.singleCursorHeightPerLine);
1281
1293
 
1282
1294
  var cursor = output.appendChild(elt("div", "\u00a0", "CodeMirror-cursor"));
1283
1295
  cursor.style.left = pos.left + "px";
@@ -1379,6 +1391,8 @@
1379
1391
  display.blinker = setInterval(function() {
1380
1392
  display.cursorDiv.style.visibility = (on = !on) ? "" : "hidden";
1381
1393
  }, cm.options.cursorBlinkRate);
1394
+ else if (cm.options.cursorBlinkRate < 0)
1395
+ display.cursorDiv.style.visibility = "hidden";
1382
1396
  }
1383
1397
 
1384
1398
  // HIGHLIGHT WORKER
@@ -1401,9 +1415,11 @@
1401
1415
  var oldStyles = line.styles;
1402
1416
  var highlighted = highlightLine(cm, line, state, true);
1403
1417
  line.styles = highlighted.styles;
1404
- if (highlighted.classes) line.styleClasses = highlighted.classes;
1405
- else if (line.styleClasses) line.styleClasses = null;
1406
- var ischange = !oldStyles || oldStyles.length != line.styles.length;
1418
+ var oldCls = line.styleClasses, newCls = highlighted.classes;
1419
+ if (newCls) line.styleClasses = newCls;
1420
+ else if (oldCls) line.styleClasses = null;
1421
+ var ischange = !oldStyles || oldStyles.length != line.styles.length ||
1422
+ oldCls != newCls && (!oldCls || !newCls || oldCls.bgClass != newCls.bgClass || oldCls.textClass != newCls.textClass);
1407
1423
  for (var i = 0; !ischange && i < oldStyles.length; ++i) ischange = oldStyles[i] != line.styles[i];
1408
1424
  if (ischange) regLineChange(cm, doc.frontier, "text");
1409
1425
  line.stateAfter = copyState(doc.mode, state);
@@ -1559,7 +1575,7 @@
1559
1575
 
1560
1576
  // Given a prepared measurement object, measures the position of an
1561
1577
  // actual character (or fetches it from the cache).
1562
- function measureCharPrepared(cm, prepared, ch, bias) {
1578
+ function measureCharPrepared(cm, prepared, ch, bias, varHeight) {
1563
1579
  if (prepared.before) ch = -1;
1564
1580
  var key = ch + (bias || ""), found;
1565
1581
  if (prepared.cache.hasOwnProperty(key)) {
@@ -1574,7 +1590,9 @@
1574
1590
  found = measureCharInner(cm, prepared, ch, bias);
1575
1591
  if (!found.bogus) prepared.cache[key] = found;
1576
1592
  }
1577
- return {left: found.left, right: found.right, top: found.top, bottom: found.bottom};
1593
+ return {left: found.left, right: found.right,
1594
+ top: varHeight ? found.rtop : found.top,
1595
+ bottom: varHeight ? found.rbottom : found.bottom};
1578
1596
  }
1579
1597
 
1580
1598
  var nullRect = {left: 0, right: 0, top: 0, bottom: 0};
@@ -1620,7 +1638,7 @@
1620
1638
  if (node.nodeType == 3) { // If it is a text node, use a range to retrieve the coordinates.
1621
1639
  while (start && isExtendingChar(prepared.line.text.charAt(mStart + start))) --start;
1622
1640
  while (mStart + end < mEnd && isExtendingChar(prepared.line.text.charAt(mStart + end))) ++end;
1623
- if (ie_upto8 && start == 0 && end == mEnd - mStart) {
1641
+ if (ie && ie_version < 9 && start == 0 && end == mEnd - mStart) {
1624
1642
  rect = node.parentNode.getBoundingClientRect();
1625
1643
  } else if (ie && cm.options.lineWrapping) {
1626
1644
  var rects = range(node, start, end).getClientRects();
@@ -1639,7 +1657,7 @@
1639
1657
  else
1640
1658
  rect = node.getBoundingClientRect();
1641
1659
  }
1642
- if (ie_upto8 && !start && (!rect || !rect.left && !rect.right)) {
1660
+ if (ie && ie_version < 9 && !start && (!rect || !rect.left && !rect.right)) {
1643
1661
  var rSpan = node.parentNode.getClientRects()[0];
1644
1662
  if (rSpan)
1645
1663
  rect = {left: rSpan.left, right: rSpan.left + charWidth(cm.display), top: rSpan.top, bottom: rSpan.bottom};
@@ -1647,15 +1665,17 @@
1647
1665
  rect = nullRect;
1648
1666
  }
1649
1667
 
1650
- var top, bot = (rect.bottom + rect.top) / 2 - prepared.rect.top;
1668
+ var rtop = rect.top - prepared.rect.top, rbot = rect.bottom - prepared.rect.top;
1669
+ var mid = (rtop + rbot) / 2;
1651
1670
  var heights = prepared.view.measure.heights;
1652
1671
  for (var i = 0; i < heights.length - 1; i++)
1653
- if (bot < heights[i]) break;
1654
- top = i ? heights[i - 1] : 0; bot = heights[i];
1672
+ if (mid < heights[i]) break;
1673
+ var top = i ? heights[i - 1] : 0, bot = heights[i];
1655
1674
  var result = {left: (collapse == "right" ? rect.right : rect.left) - prepared.rect.left,
1656
1675
  right: (collapse == "left" ? rect.left : rect.right) - prepared.rect.left,
1657
1676
  top: top, bottom: bot};
1658
1677
  if (!rect.left && !rect.right) result.bogus = true;
1678
+ if (!cm.options.singleCursorHeightPerLine) { result.rtop = rtop; result.rbottom = rbot; }
1659
1679
  return result;
1660
1680
  }
1661
1681
 
@@ -1735,11 +1755,11 @@
1735
1755
  // Returns a box for a given cursor position, which may have an
1736
1756
  // 'other' property containing the position of the secondary cursor
1737
1757
  // on a bidi boundary.
1738
- function cursorCoords(cm, pos, context, lineObj, preparedMeasure) {
1758
+ function cursorCoords(cm, pos, context, lineObj, preparedMeasure, varHeight) {
1739
1759
  lineObj = lineObj || getLine(cm.doc, pos.line);
1740
1760
  if (!preparedMeasure) preparedMeasure = prepareMeasureForLine(cm, lineObj);
1741
1761
  function get(ch, right) {
1742
- var m = measureCharPrepared(cm, preparedMeasure, ch, right ? "right" : "left");
1762
+ var m = measureCharPrepared(cm, preparedMeasure, ch, right ? "right" : "left", varHeight);
1743
1763
  if (right) m.left = m.right; else m.right = m.left;
1744
1764
  return intoCoordSystem(cm, lineObj, m, context);
1745
1765
  }
@@ -2250,7 +2270,7 @@
2250
2270
  // If nothing changed, bail.
2251
2271
  if (text == prevInput && !cm.somethingSelected()) return false;
2252
2272
  // Work around nonsensical selection resetting in IE9/10
2253
- if (ie && !ie_upto8 && cm.display.inputHasSelection === text) {
2273
+ if (ie && ie_version >= 9 && cm.display.inputHasSelection === text) {
2254
2274
  resetInput(cm);
2255
2275
  return false;
2256
2276
  }
@@ -2326,10 +2346,10 @@
2326
2346
  var content = minimal ? "-" : selected || cm.getSelection();
2327
2347
  cm.display.input.value = content;
2328
2348
  if (cm.state.focused) selectInput(cm.display.input);
2329
- if (ie && !ie_upto8) cm.display.inputHasSelection = content;
2349
+ if (ie && ie_version >= 9) cm.display.inputHasSelection = content;
2330
2350
  } else if (!typing) {
2331
2351
  cm.display.prevInput = cm.display.input.value = "";
2332
- if (ie && !ie_upto8) cm.display.inputHasSelection = null;
2352
+ if (ie && ie_version >= 9) cm.display.inputHasSelection = null;
2333
2353
  }
2334
2354
  cm.display.inaccurateSelection = minimal;
2335
2355
  }
@@ -2354,7 +2374,7 @@
2354
2374
  var d = cm.display;
2355
2375
  on(d.scroller, "mousedown", operation(cm, onMouseDown));
2356
2376
  // Older IE's will not fire a second mousedown for a double click
2357
- if (ie_upto10)
2377
+ if (ie && ie_version < 11)
2358
2378
  on(d.scroller, "dblclick", operation(cm, function(e) {
2359
2379
  if (signalDOMEvent(cm, e)) return;
2360
2380
  var pos = posFromMouse(cm, e);
@@ -2403,7 +2423,7 @@
2403
2423
 
2404
2424
  on(d.input, "keyup", operation(cm, onKeyUp));
2405
2425
  on(d.input, "input", function() {
2406
- if (ie && !ie_upto8 && cm.display.inputHasSelection) cm.display.inputHasSelection = null;
2426
+ if (ie && ie_version >= 9 && cm.display.inputHasSelection) cm.display.inputHasSelection = null;
2407
2427
  fastPoll(cm);
2408
2428
  });
2409
2429
  on(d.input, "keydown", operation(cm, onKeyDown));
@@ -2433,8 +2453,12 @@
2433
2453
  if (webkit && !cm.state.fakedLastChar && !(new Date - cm.state.lastMiddleDown < 200)) {
2434
2454
  var start = d.input.selectionStart, end = d.input.selectionEnd;
2435
2455
  d.input.value += "$";
2436
- d.input.selectionStart = start;
2456
+ // The selection end needs to be set before the start, otherwise there
2457
+ // can be an intermediate non-empty selection between the two, which
2458
+ // can override the middle-click paste buffer on linux and cause the
2459
+ // wrong thing to get pasted.
2437
2460
  d.input.selectionEnd = end;
2461
+ d.input.selectionStart = start;
2438
2462
  cm.state.fakedLastChar = true;
2439
2463
  }
2440
2464
  cm.state.pasteIncoming = true;
@@ -2598,7 +2622,7 @@
2598
2622
  extendSelection(cm.doc, start);
2599
2623
  focusInput(cm);
2600
2624
  // Work around unexplainable focus problem in IE9 (#2127)
2601
- if (ie_upto10 && !ie_upto8)
2625
+ if (ie && ie_version == 9)
2602
2626
  setTimeout(function() {document.body.focus(); focusInput(cm);}, 20);
2603
2627
  }
2604
2628
  });
@@ -2741,7 +2765,7 @@
2741
2765
  }
2742
2766
 
2743
2767
  var move = operation(cm, function(e) {
2744
- if ((ie && !ie_upto9) ? !e.buttons : !e_button(e)) done(e);
2768
+ if (!e_button(e)) done(e);
2745
2769
  else extend(e);
2746
2770
  });
2747
2771
  var up = operation(cm, done);
@@ -3058,7 +3082,7 @@
3058
3082
  ensureFocus(cm);
3059
3083
  if (signalDOMEvent(cm, e)) return;
3060
3084
  // IE does strange things with escape.
3061
- if (ie_upto10 && e.keyCode == 27) e.returnValue = false;
3085
+ if (ie && ie_version < 11 && e.keyCode == 27) e.returnValue = false;
3062
3086
  var code = e.keyCode;
3063
3087
  cm.display.shift = code == 16 || e.shiftKey;
3064
3088
  var handled = handleKeyBinding(cm, e);
@@ -3096,13 +3120,13 @@
3096
3120
 
3097
3121
  function onKeyPress(e) {
3098
3122
  var cm = this;
3099
- if (signalDOMEvent(cm, e)) return;
3123
+ if (signalDOMEvent(cm, e) || e.ctrlKey || mac && e.metaKey) return;
3100
3124
  var keyCode = e.keyCode, charCode = e.charCode;
3101
3125
  if (presto && keyCode == lastStoppedKey) {lastStoppedKey = null; e_preventDefault(e); return;}
3102
3126
  if (((presto && (!e.which || e.which < 10)) || khtml) && handleKeyBinding(cm, e)) return;
3103
3127
  var ch = String.fromCharCode(charCode == null ? keyCode : charCode);
3104
3128
  if (handleCharBinding(cm, e, ch)) return;
3105
- if (ie && !ie_upto8) cm.display.inputHasSelection = null;
3129
+ if (ie && ie_version >= 9) cm.display.inputHasSelection = null;
3106
3130
  fastPoll(cm);
3107
3131
  }
3108
3132
 
@@ -3184,12 +3208,12 @@
3184
3208
  function rehide() {
3185
3209
  display.inputDiv.style.position = "relative";
3186
3210
  display.input.style.cssText = oldCSS;
3187
- if (ie_upto8) display.scrollbarV.scrollTop = display.scroller.scrollTop = scrollPos;
3211
+ if (ie && ie_version < 9) display.scrollbarV.scrollTop = display.scroller.scrollTop = scrollPos;
3188
3212
  slowPoll(cm);
3189
3213
 
3190
3214
  // Try to detect the user choosing select-all
3191
3215
  if (display.input.selectionStart != null) {
3192
- if (!ie || ie_upto8) prepareSelectAllHack();
3216
+ if (!ie || (ie && ie_version < 9)) prepareSelectAllHack();
3193
3217
  var i = 0, poll = function() {
3194
3218
  if (display.selForContextMenu == cm.doc.sel && display.input.selectionStart == 0)
3195
3219
  operation(cm, commands.selectAll)(cm);
@@ -3200,7 +3224,7 @@
3200
3224
  }
3201
3225
  }
3202
3226
 
3203
- if (ie && !ie_upto8) prepareSelectAllHack();
3227
+ if (ie && ie_version >= 9) prepareSelectAllHack();
3204
3228
  if (captureRightClick) {
3205
3229
  e_stop(e);
3206
3230
  var mouseup = function() {
@@ -3711,12 +3735,12 @@
3711
3735
  // Utility for applying a change to a line by handle or number,
3712
3736
  // returning the number and optionally registering the line as
3713
3737
  // changed.
3714
- function changeLine(cm, handle, changeType, op) {
3715
- var no = handle, line = handle, doc = cm.doc;
3738
+ function changeLine(doc, handle, changeType, op) {
3739
+ var no = handle, line = handle;
3716
3740
  if (typeof handle == "number") line = getLine(doc, clipLine(doc, handle));
3717
3741
  else no = lineNo(handle);
3718
3742
  if (no == null) return null;
3719
- if (op(line, no)) regLineChange(cm, no, changeType);
3743
+ if (op(line, no) && doc.cm) regLineChange(doc.cm, no, changeType);
3720
3744
  return line;
3721
3745
  }
3722
3746
 
@@ -4031,7 +4055,7 @@
4031
4055
  defaultCharWidth: function() { return charWidth(this.display); },
4032
4056
 
4033
4057
  setGutterMarker: methodOp(function(line, gutterID, value) {
4034
- return changeLine(this, line, "gutter", function(line) {
4058
+ return changeLine(this.doc, line, "gutter", function(line) {
4035
4059
  var markers = line.gutterMarkers || (line.gutterMarkers = {});
4036
4060
  markers[gutterID] = value;
4037
4061
  if (!value && isEmpty(markers)) line.gutterMarkers = null;
@@ -4051,32 +4075,6 @@
4051
4075
  });
4052
4076
  }),
4053
4077
 
4054
- addLineClass: methodOp(function(handle, where, cls) {
4055
- return changeLine(this, handle, "class", function(line) {
4056
- var prop = where == "text" ? "textClass" : where == "background" ? "bgClass" : "wrapClass";
4057
- if (!line[prop]) line[prop] = cls;
4058
- else if (new RegExp("(?:^|\\s)" + cls + "(?:$|\\s)").test(line[prop])) return false;
4059
- else line[prop] += " " + cls;
4060
- return true;
4061
- });
4062
- }),
4063
-
4064
- removeLineClass: methodOp(function(handle, where, cls) {
4065
- return changeLine(this, handle, "class", function(line) {
4066
- var prop = where == "text" ? "textClass" : where == "background" ? "bgClass" : "wrapClass";
4067
- var cur = line[prop];
4068
- if (!cur) return false;
4069
- else if (cls == null) line[prop] = null;
4070
- else {
4071
- var found = cur.match(new RegExp("(?:^|\\s+)" + cls + "(?:$|\\s+)"));
4072
- if (!found) return false;
4073
- var end = found.index + found[0].length;
4074
- line[prop] = cur.slice(0, found.index) + (!found.index || end == cur.length ? "" : " ") + cur.slice(end) || null;
4075
- }
4076
- return true;
4077
- });
4078
- }),
4079
-
4080
4078
  addLineWidget: methodOp(function(handle, node, options) {
4081
4079
  return addLineWidget(this, handle, node, options);
4082
4080
  }),
@@ -4252,14 +4250,21 @@
4252
4250
  }),
4253
4251
 
4254
4252
  setSize: methodOp(function(width, height) {
4253
+ var cm = this;
4255
4254
  function interpret(val) {
4256
4255
  return typeof val == "number" || /^\d+$/.test(String(val)) ? val + "px" : val;
4257
4256
  }
4258
- if (width != null) this.display.wrapper.style.width = interpret(width);
4259
- if (height != null) this.display.wrapper.style.height = interpret(height);
4260
- if (this.options.lineWrapping) clearLineMeasurementCache(this);
4261
- this.curOp.forceUpdate = true;
4262
- signal(this, "refresh", this);
4257
+ if (width != null) cm.display.wrapper.style.width = interpret(width);
4258
+ if (height != null) cm.display.wrapper.style.height = interpret(height);
4259
+ if (cm.options.lineWrapping) clearLineMeasurementCache(this);
4260
+ var lineNo = cm.display.viewFrom;
4261
+ cm.doc.iter(lineNo, cm.display.viewTo, function(line) {
4262
+ if (line.widgets) for (var i = 0; i < line.widgets.length; i++)
4263
+ if (line.widgets[i].noHScroll) { regLineChange(cm, lineNo, "widget"); break; }
4264
+ ++lineNo;
4265
+ });
4266
+ cm.curOp.forceUpdate = true;
4267
+ signal(cm, "refresh", this);
4263
4268
  }),
4264
4269
 
4265
4270
  operation: function(f){return runInOp(this, f);},
@@ -4379,7 +4384,8 @@
4379
4384
 
4380
4385
  option("cursorBlinkRate", 530);
4381
4386
  option("cursorScrollMargin", 0);
4382
- option("cursorHeight", 1);
4387
+ option("cursorHeight", 1, updateSelection, true);
4388
+ option("singleCursorHeightPerLine", true, updateSelection, true);
4383
4389
  option("workTime", 100);
4384
4390
  option("workDelay", 100);
4385
4391
  option("flattenSpans", true, resetModeState, true);
@@ -4569,7 +4575,8 @@
4569
4575
  goDocStart: function(cm) {cm.extendSelection(Pos(cm.firstLine(), 0));},
4570
4576
  goDocEnd: function(cm) {cm.extendSelection(Pos(cm.lastLine()));},
4571
4577
  goLineStart: function(cm) {
4572
- cm.extendSelectionsBy(function(range) { return lineStart(cm, range.head.line); }, sel_move);
4578
+ cm.extendSelectionsBy(function(range) { return lineStart(cm, range.head.line); },
4579
+ {origin: "+move", bias: 1});
4573
4580
  },
4574
4581
  goLineStartSmart: function(cm) {
4575
4582
  cm.extendSelectionsBy(function(range) {
@@ -4582,10 +4589,11 @@
4582
4589
  return Pos(start.line, inWS ? 0 : firstNonWS);
4583
4590
  }
4584
4591
  return start;
4585
- }, sel_move);
4592
+ }, {origin: "+move", bias: 1});
4586
4593
  },
4587
4594
  goLineEnd: function(cm) {
4588
- cm.extendSelectionsBy(function(range) { return lineEnd(cm, range.head.line); }, sel_move);
4595
+ cm.extendSelectionsBy(function(range) { return lineEnd(cm, range.head.line); },
4596
+ {origin: "+move", bias: -1});
4589
4597
  },
4590
4598
  goLineRight: function(cm) {
4591
4599
  cm.extendSelectionsBy(function(range) {
@@ -5417,8 +5425,8 @@
5417
5425
  var fromCmp = cmp(found.from, from) || extraLeft(sp.marker) - extraLeft(marker);
5418
5426
  var toCmp = cmp(found.to, to) || extraRight(sp.marker) - extraRight(marker);
5419
5427
  if (fromCmp >= 0 && toCmp <= 0 || fromCmp <= 0 && toCmp >= 0) continue;
5420
- if (fromCmp <= 0 && (cmp(found.to, from) || extraRight(sp.marker) - extraLeft(marker)) > 0 ||
5421
- fromCmp >= 0 && (cmp(found.from, to) || extraLeft(sp.marker) - extraRight(marker)) < 0)
5428
+ if (fromCmp <= 0 && (cmp(found.to, from) > 0 || (sp.marker.inclusiveRight && marker.inclusiveLeft)) ||
5429
+ fromCmp >= 0 && (cmp(found.from, to) < 0 || (sp.marker.inclusiveLeft && marker.inclusiveRight)))
5422
5430
  return true;
5423
5431
  }
5424
5432
  }
@@ -5536,15 +5544,19 @@
5536
5544
 
5537
5545
  function widgetHeight(widget) {
5538
5546
  if (widget.height != null) return widget.height;
5539
- if (!contains(document.body, widget.node))
5540
- removeChildrenAndAdd(widget.cm.display.measure, elt("div", [widget.node], null, "position: relative"));
5547
+ if (!contains(document.body, widget.node)) {
5548
+ var parentStyle = "position: relative;";
5549
+ if (widget.coverGutter)
5550
+ parentStyle += "margin-left: -" + widget.cm.getGutterElement().offsetWidth + "px;";
5551
+ removeChildrenAndAdd(widget.cm.display.measure, elt("div", [widget.node], null, parentStyle));
5552
+ }
5541
5553
  return widget.height = widget.node.offsetHeight;
5542
5554
  }
5543
5555
 
5544
5556
  function addLineWidget(cm, handle, node, options) {
5545
5557
  var widget = new LineWidget(cm, node, options);
5546
5558
  if (widget.noHScroll) cm.display.alignWidgets = true;
5547
- changeLine(cm, handle, "widget", function(line) {
5559
+ changeLine(cm.doc, handle, "widget", function(line) {
5548
5560
  var widgets = line.widgets || (line.widgets = []);
5549
5561
  if (widget.insertAt == null) widgets.push(widget);
5550
5562
  else widgets.splice(Math.min(widgets.length - 1, Math.max(0, widget.insertAt)), 0, widget);
@@ -5800,7 +5812,7 @@
5800
5812
  builder.col += text.length;
5801
5813
  var content = document.createTextNode(text);
5802
5814
  builder.map.push(builder.pos, builder.pos + text.length, content);
5803
- if (ie_upto8) mustWrap = true;
5815
+ if (ie && ie_version < 9) mustWrap = true;
5804
5816
  builder.pos += text.length;
5805
5817
  } else {
5806
5818
  var content = document.createDocumentFragment(), pos = 0;
@@ -5810,7 +5822,7 @@
5810
5822
  var skipped = m ? m.index - pos : text.length - pos;
5811
5823
  if (skipped) {
5812
5824
  var txt = document.createTextNode(text.slice(pos, pos + skipped));
5813
- if (ie_upto8) content.appendChild(elt("span", [txt]));
5825
+ if (ie && ie_version < 9) content.appendChild(elt("span", [txt]));
5814
5826
  else content.appendChild(txt);
5815
5827
  builder.map.push(builder.pos, builder.pos + skipped, txt);
5816
5828
  builder.col += skipped;
@@ -5824,7 +5836,7 @@
5824
5836
  builder.col += tabWidth;
5825
5837
  } else {
5826
5838
  var txt = builder.cm.options.specialCharPlaceholder(m[0]);
5827
- if (ie_upto8) content.appendChild(elt("span", [txt]));
5839
+ if (ie && ie_version < 9) content.appendChild(elt("span", [txt]));
5828
5840
  else content.appendChild(txt);
5829
5841
  builder.col += 1;
5830
5842
  }
@@ -6349,6 +6361,31 @@
6349
6361
  hist.undone = copyHistoryArray(histData.undone.slice(0), null, true);
6350
6362
  },
6351
6363
 
6364
+ addLineClass: docMethodOp(function(handle, where, cls) {
6365
+ return changeLine(this, handle, "class", function(line) {
6366
+ var prop = where == "text" ? "textClass" : where == "background" ? "bgClass" : "wrapClass";
6367
+ if (!line[prop]) line[prop] = cls;
6368
+ else if (new RegExp("(?:^|\\s)" + cls + "(?:$|\\s)").test(line[prop])) return false;
6369
+ else line[prop] += " " + cls;
6370
+ return true;
6371
+ });
6372
+ }),
6373
+ removeLineClass: docMethodOp(function(handle, where, cls) {
6374
+ return changeLine(this, handle, "class", function(line) {
6375
+ var prop = where == "text" ? "textClass" : where == "background" ? "bgClass" : "wrapClass";
6376
+ var cur = line[prop];
6377
+ if (!cur) return false;
6378
+ else if (cls == null) line[prop] = null;
6379
+ else {
6380
+ var found = cur.match(new RegExp("(?:^|\\s+)" + cls + "(?:$|\\s+)"));
6381
+ if (!found) return false;
6382
+ var end = found.index + found[0].length;
6383
+ line[prop] = cur.slice(0, found.index) + (!found.index || end == cur.length ? "" : " ") + cur.slice(end) || null;
6384
+ }
6385
+ return true;
6386
+ });
6387
+ }),
6388
+
6352
6389
  markText: function(from, to, options) {
6353
6390
  return markText(this, clipPos(this, from), clipPos(this, to), options, "range");
6354
6391
  },
@@ -7156,7 +7193,7 @@
7156
7193
  function activeElt() { return document.activeElement; }
7157
7194
  // Older versions of IE throws unspecified error when touching
7158
7195
  // document.activeElement in some cases (during loading, in iframe)
7159
- if (ie_upto10) activeElt = function() {
7196
+ if (ie && ie_version < 11) activeElt = function() {
7160
7197
  try { return document.activeElement; }
7161
7198
  catch(e) { return document.body; }
7162
7199
  };
@@ -7219,7 +7256,7 @@
7219
7256
  var dragAndDrop = function() {
7220
7257
  // There is *some* kind of drag-and-drop support in IE6-8, but I
7221
7258
  // couldn't get it to work yet.
7222
- if (ie_upto8) return false;
7259
+ if (ie && ie_version < 9) return false;
7223
7260
  var div = elt('div');
7224
7261
  return "draggable" in div || "dragDrop" in div;
7225
7262
  }();
@@ -7240,7 +7277,7 @@
7240
7277
  var test = elt("span", "\u200b");
7241
7278
  removeChildrenAndAdd(measure, elt("span", [test, document.createTextNode("x")]));
7242
7279
  if (measure.firstChild.offsetHeight != 0)
7243
- zwspSupported = test.offsetWidth <= 1 && test.offsetHeight > 2 && !ie_upto7;
7280
+ zwspSupported = test.offsetWidth <= 1 && test.offsetHeight > 2 && !(ie && ie_version < 8);
7244
7281
  }
7245
7282
  if (zwspSupported) return elt("span", "\u200b");
7246
7283
  else return elt("span", "\u00a0", null, "display: inline-block; width: 1px; margin-right: -1px");
@@ -7595,7 +7632,7 @@
7595
7632
 
7596
7633
  // THE END
7597
7634
 
7598
- CodeMirror.version = "4.2.0";
7635
+ CodeMirror.version = "4.3.0";
7599
7636
 
7600
7637
  return CodeMirror;
7601
7638
  });