A place to cache linked articles (think custom and personal wayback machine)
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

index.html 10KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171
  1. <!doctype html><!-- This is a valid HTML5 document. -->
  2. <!-- Screen readers, SEO, extensions and so on. -->
  3. <html lang="fr">
  4. <!-- Has to be within the first 1024 bytes, hence before the <title>
  5. See: https://www.w3.org/TR/2012/CR-html5-20121217/document-metadata.html#charset -->
  6. <meta charset="utf-8">
  7. <!-- Why no `X-UA-Compatible` meta: https://stackoverflow.com/a/6771584 -->
  8. <!-- The viewport meta is quite crowded and we are responsible for that.
  9. See: https://codepen.io/tigt/post/meta-viewport-for-2015 -->
  10. <meta name="viewport" content="width=device-width,initial-scale=1">
  11. <!-- Required to make a valid HTML5 document. -->
  12. <title>The most important feature of Sublime Text (archive) — David Larlet</title>
  13. <meta name="description" content="Publication mise en cache pour en conserver une trace.">
  14. <!-- That good ol' feed, subscribe :). -->
  15. <link rel="alternate" type="application/atom+xml" title="Feed" href="/david/log/">
  16. <!-- Generated from https://realfavicongenerator.net/ such a mess. -->
  17. <link rel="apple-touch-icon" sizes="180x180" href="/static/david/icons2/apple-touch-icon.png">
  18. <link rel="icon" type="image/png" sizes="32x32" href="/static/david/icons2/favicon-32x32.png">
  19. <link rel="icon" type="image/png" sizes="16x16" href="/static/david/icons2/favicon-16x16.png">
  20. <link rel="manifest" href="/static/david/icons2/site.webmanifest">
  21. <link rel="mask-icon" href="/static/david/icons2/safari-pinned-tab.svg" color="#07486c">
  22. <link rel="shortcut icon" href="/static/david/icons2/favicon.ico">
  23. <meta name="msapplication-TileColor" content="#f0f0ea">
  24. <meta name="msapplication-config" content="/static/david/icons2/browserconfig.xml">
  25. <meta name="theme-color" content="#f0f0ea">
  26. <!-- Documented, feel free to shoot an email. -->
  27. <link rel="stylesheet" href="/static/david/css/style_2020-06-19.css">
  28. <!-- See https://www.zachleat.com/web/comprehensive-webfonts/ for the trade-off. -->
  29. <link rel="preload" href="/static/david/css/fonts/triplicate_t4_poly_regular.woff2" as="font" type="font/woff2" media="(prefers-color-scheme: light), (prefers-color-scheme: no-preference)" crossorigin>
  30. <link rel="preload" href="/static/david/css/fonts/triplicate_t4_poly_bold.woff2" as="font" type="font/woff2" media="(prefers-color-scheme: light), (prefers-color-scheme: no-preference)" crossorigin>
  31. <link rel="preload" href="/static/david/css/fonts/triplicate_t4_poly_italic.woff2" as="font" type="font/woff2" media="(prefers-color-scheme: light), (prefers-color-scheme: no-preference)" crossorigin>
  32. <link rel="preload" href="/static/david/css/fonts/triplicate_t3_regular.woff2" as="font" type="font/woff2" media="(prefers-color-scheme: dark)" crossorigin>
  33. <link rel="preload" href="/static/david/css/fonts/triplicate_t3_bold.woff2" as="font" type="font/woff2" media="(prefers-color-scheme: dark)" crossorigin>
  34. <link rel="preload" href="/static/david/css/fonts/triplicate_t3_italic.woff2" as="font" type="font/woff2" media="(prefers-color-scheme: dark)" crossorigin>
  35. <script type="text/javascript">
  36. function toggleTheme(themeName) {
  37. document.documentElement.classList.toggle(
  38. 'forced-dark',
  39. themeName === 'dark'
  40. )
  41. document.documentElement.classList.toggle(
  42. 'forced-light',
  43. themeName === 'light'
  44. )
  45. }
  46. const selectedTheme = localStorage.getItem('theme')
  47. if (selectedTheme !== 'undefined') {
  48. toggleTheme(selectedTheme)
  49. }
  50. </script>
  51. <meta name="robots" content="noindex, nofollow">
  52. <meta content="origin-when-cross-origin" name="referrer">
  53. <!-- Canonical URL for SEO purposes -->
  54. <link rel="canonical" href="https://tonsky.me/blog/sublime/">
  55. <body class="remarkdown h1-underline h2-underline h3-underline hr-center ul-star pre-tick">
  56. <article>
  57. <header>
  58. <h1>The most important feature of Sublime Text</h1>
  59. </header>
  60. <nav>
  61. <p class="center">
  62. <a href="/david/" title="Aller à l’accueil">🏠</a> •
  63. <a href="https://tonsky.me/blog/sublime/" title="Lien vers le contenu original">Source originale</a>
  64. </p>
  65. </nav>
  66. <hr>
  67. <main>
  68. <p>…is that it doesn’t change.</p>
  69. <p>In the modern world, everything changes at a crazy pace. We get new OSes and new phones every year, Google opens and closes its products monthly, many physical devices get announced, produced, and disappear in an interval shorter than the Sublime Text release cycle. I have two problems with that.</p>
  70. <p>First, new features just keep being added, because how else would you justify releases? VS Code releases every month with new stuff! They are well past the point of shipping the essentials (and have been for a couple of years now), but releases are still been shipped. Because they have a team, that team has a huge budget to spare, and there’s no power stopping them from shipping anything, no matter important or not. There’s no filter.</p>
  71. <p>You might think that VS Code can be turned into Sublime by turning everything off. Well, yes, but you’ll have to do it every month because they add new stuff every month, and new stuff wants your attention, so they enable it for you and promote it for you.</p>
  72. <p>Sublime fights this by being developed by just two people who don’t have much free time on their hands. As a result, every detail in ST is essential, and everything that is not is just not there. Yes, some new frameworks that came out yesterday might not be supported, and some obscure integrations might not exist, but the upside is that it keeps the ST experience clean and focused. That makes me much happier than VS Code that tries to please everyone but gets everyone tired instead.</p>
  73. <p>The second problem is that when things change, some aspects get worse, and some disappear completely. I am horrified each year with Apple events — which essential features that I rely on heavily will they break/remove this year? Even if something is not removed, compatibility is always getting worse. This extension relies on this version of VS Code, and the other one on that. We are sorry, the developer of this extension did not update it for the current version. Even though things get better in general, some things always get broken/changed/removed along the way. Given the speed of change and the number of features every developer depends on (different for everyone), someone gets screwed with every new release. It’s only a matter of time when it will be your turn.</p>
  74. <p>Sublime, on the other hand, changes very slowly. The current version, ST 3, is the same version that I used a year, two years, five years ago. And ST 2, released twelve years ago, is very very close to what I am using today. ST 4 is currently in alpha, and I honestly can’t tell the difference. The upside? I know what I am getting. If it fits me now, it will fit me ten years from now. I can <em>rely</em> on it. I get used to it once and I can spend the rest of my life focusing on my work instead of learning a new tool every month. I don’t risk losing it one day because it changed too much. ST will always stay ST, and if it’s perfect, I am happy it doesn’t change.</p>
  75. <p>God bless Sublime.</p>
  76. </main>
  77. </article>
  78. <hr>
  79. <footer>
  80. <p>
  81. <a href="/david/" title="Aller à l’accueil">🏠</a> •
  82. <a href="/david/log/" title="Accès au flux RSS">🤖</a> •
  83. <a href="http://larlet.com" title="Go to my English profile" data-instant>🇨🇦</a> •
  84. <a href="mailto:david%40larlet.fr" title="Envoyer un courriel">📮</a> •
  85. <abbr title="Hébergeur : Alwaysdata, 62 rue Tiquetonne 75002 Paris, +33184162340">🧚</abbr>
  86. </p>
  87. <template id="theme-selector">
  88. <form>
  89. <fieldset>
  90. <legend>Thème</legend>
  91. <label>
  92. <input type="radio" value="auto" name="chosen-color-scheme" checked> Auto
  93. </label>
  94. <label>
  95. <input type="radio" value="dark" name="chosen-color-scheme"> Foncé
  96. </label>
  97. <label>
  98. <input type="radio" value="light" name="chosen-color-scheme"> Clair
  99. </label>
  100. </fieldset>
  101. </form>
  102. </template>
  103. </footer>
  104. <script type="text/javascript">
  105. function loadThemeForm(templateName) {
  106. const themeSelectorTemplate = document.querySelector(templateName)
  107. const form = themeSelectorTemplate.content.firstElementChild
  108. themeSelectorTemplate.replaceWith(form)
  109. form.addEventListener('change', (e) => {
  110. const chosenColorScheme = e.target.value
  111. localStorage.setItem('theme', chosenColorScheme)
  112. toggleTheme(chosenColorScheme)
  113. })
  114. const selectedTheme = localStorage.getItem('theme')
  115. if (selectedTheme && selectedTheme !== 'undefined') {
  116. form.querySelector(`[value="${selectedTheme}"]`).checked = true
  117. }
  118. }
  119. const prefersColorSchemeDark = '(prefers-color-scheme: dark)'
  120. window.addEventListener('load', () => {
  121. let hasDarkRules = false
  122. for (const styleSheet of Array.from(document.styleSheets)) {
  123. let mediaRules = []
  124. for (const cssRule of styleSheet.cssRules) {
  125. if (cssRule.type !== CSSRule.MEDIA_RULE) {
  126. continue
  127. }
  128. // WARNING: Safari does not have/supports `conditionText`.
  129. if (cssRule.conditionText) {
  130. if (cssRule.conditionText !== prefersColorSchemeDark) {
  131. continue
  132. }
  133. } else {
  134. if (cssRule.cssText.startsWith(prefersColorSchemeDark)) {
  135. continue
  136. }
  137. }
  138. mediaRules = mediaRules.concat(Array.from(cssRule.cssRules))
  139. }
  140. // WARNING: do not try to insert a Rule to a styleSheet you are
  141. // currently iterating on, otherwise the browser will be stuck
  142. // in a infinite loop…
  143. for (const mediaRule of mediaRules) {
  144. styleSheet.insertRule(mediaRule.cssText)
  145. hasDarkRules = true
  146. }
  147. }
  148. if (hasDarkRules) {
  149. loadThemeForm('#theme-selector')
  150. }
  151. })
  152. </script>
  153. </body>
  154. </html>