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 40KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966
  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,minimum-scale=1,initial-scale=1,shrink-to-fit=no">
  11. <!-- Required to make a valid HTML5 document. -->
  12. <title>Bootstrap est une régression pour un développement Front-end de qualité (archive) — David Larlet</title>
  13. <!-- Generated from https://realfavicongenerator.net/ such a mess. -->
  14. <link rel="apple-touch-icon" sizes="180x180" href="/static/david/icons/apple-touch-icon.png">
  15. <link rel="icon" type="image/png" sizes="32x32" href="/static/david/icons/favicon-32x32.png">
  16. <link rel="icon" type="image/png" sizes="16x16" href="/static/david/icons/favicon-16x16.png">
  17. <link rel="manifest" href="/manifest.json">
  18. <link rel="mask-icon" href="/static/david/icons/safari-pinned-tab.svg" color="#5bbad5">
  19. <link rel="shortcut icon" href="/static/david/icons/favicon.ico">
  20. <meta name="apple-mobile-web-app-title" content="David Larlet">
  21. <meta name="application-name" content="David Larlet">
  22. <meta name="msapplication-TileColor" content="#da532c">
  23. <meta name="msapplication-config" content="/static/david/icons/browserconfig.xml">
  24. <meta name="theme-color" content="#f0f0ea">
  25. <!-- That good ol' feed, subscribe :p. -->
  26. <link rel=alternate type="application/atom+xml" title=Feed href="/david/log/">
  27. <meta name="robots" content="noindex, nofollow">
  28. <meta content="origin-when-cross-origin" name="referrer">
  29. <!-- Canonical URL for SEO purposes -->
  30. <link rel="canonical" href="http://blog.lesieur.name/bootstrap-est-une-regression-pour-un-developpement-front-end-de-qualite/">
  31. <style>
  32. /* http://meyerweb.com/eric/tools/css/reset/ */
  33. html, body, div, span,
  34. h1, h2, h3, h4, h5, h6, p, blockquote, pre,
  35. a, abbr, address, big, cite, code,
  36. del, dfn, em, img, ins,
  37. small, strike, strong, tt, var,
  38. dl, dt, dd, ol, ul, li,
  39. fieldset, form, label, legend,
  40. table, caption, tbody, tfoot, thead, tr, th, td,
  41. article, aside, canvas, details, embed,
  42. figure, figcaption, footer, header, hgroup,
  43. menu, nav, output, ruby, section, summary,
  44. time, mark, audio, video {
  45. margin: 0;
  46. padding: 0;
  47. border: 0;
  48. font-size: 100%;
  49. font: inherit;
  50. vertical-align: baseline;
  51. }
  52. /* HTML5 display-role reset for older browsers */
  53. article, aside, details, figcaption, figure,
  54. footer, header, hgroup, menu, nav, section { display: block; }
  55. body { line-height: 1; }
  56. blockquote, q { quotes: none; }
  57. blockquote:before, blockquote:after,
  58. q:before, q:after {
  59. content: '';
  60. content: none;
  61. }
  62. table {
  63. border-collapse: collapse;
  64. border-spacing: 0;
  65. }
  66. /* http://practicaltypography.com/equity.html */
  67. /* https://calendar.perfplanet.com/2016/no-font-face-bulletproof-syntax/ */
  68. /* https://www.filamentgroup.com/lab/js-web-fonts.html */
  69. @font-face {
  70. font-family: 'EquityTextB';
  71. src: url('/static/david/css/fonts/Equity-Text-B-Regular-webfont.woff2') format('woff2'),
  72. url('/static/david/css/fonts/Equity-Text-B-Regular-webfont.woff') format('woff');
  73. font-weight: 300;
  74. font-style: normal;
  75. font-display: swap;
  76. }
  77. @font-face {
  78. font-family: 'EquityTextB';
  79. src: url('/static/david/css/fonts/Equity-Text-B-Italic-webfont.woff2') format('woff2'),
  80. url('/static/david/css/fonts/Equity-Text-B-Italic-webfont.woff') format('woff');
  81. font-weight: 300;
  82. font-style: italic;
  83. font-display: swap;
  84. }
  85. @font-face {
  86. font-family: 'EquityTextB';
  87. src: url('/static/david/css/fonts/Equity-Text-B-Bold-webfont.woff2') format('woff2'),
  88. url('/static/david/css/fonts/Equity-Text-B-Bold-webfont.woff') format('woff');
  89. font-weight: 700;
  90. font-style: normal;
  91. font-display: swap;
  92. }
  93. @font-face {
  94. font-family: 'ConcourseT3';
  95. src: url('/static/david/css/fonts/concourse_t3_regular-webfont-20190806.woff2') format('woff2'),
  96. url('/static/david/css/fonts/concourse_t3_regular-webfont-20190806.woff') format('woff');
  97. font-weight: 300;
  98. font-style: normal;
  99. font-display: swap;
  100. }
  101. /* http://practice.typekit.com/lesson/caring-about-opentype-features/ */
  102. body {
  103. /* http://www.cssfontstack.com/ Palatino 99% Win 86% Mac */
  104. font-family: "EquityTextB", Palatino, serif;
  105. background-color: #f0f0ea;
  106. color: #07486c;
  107. font-kerning: normal;
  108. -moz-osx-font-smoothing: grayscale;
  109. -webkit-font-smoothing: subpixel-antialiased;
  110. text-rendering: optimizeLegibility;
  111. font-variant-ligatures: common-ligatures contextual;
  112. font-feature-settings: "kern", "liga", "clig", "calt";
  113. }
  114. pre, code, kbd, samp, var, tt {
  115. font-family: 'TriplicateT4c', monospace;
  116. }
  117. em {
  118. font-style: italic;
  119. color: #323a45;
  120. }
  121. strong {
  122. font-weight: bold;
  123. color: black;
  124. }
  125. nav {
  126. background-color: #323a45;
  127. color: #f0f0ea;
  128. display: flex;
  129. justify-content: space-around;
  130. padding: 1rem .5rem;
  131. }
  132. nav:last-child {
  133. border-bottom: 1vh solid #2d7474;
  134. }
  135. nav a {
  136. color: #f0f0ea;
  137. }
  138. nav abbr {
  139. border-bottom: 1px dotted white;
  140. }
  141. h1 {
  142. border-top: 1vh solid #2d7474;
  143. border-bottom: .2vh dotted #2d7474;
  144. background-color: #e3e1e1;
  145. color: #323a45;
  146. text-align: center;
  147. padding: 5rem 0 4rem 0;
  148. width: 100%;
  149. font-family: 'ConcourseT3';
  150. display: flex;
  151. flex-direction: column;
  152. }
  153. h1.single {
  154. padding-bottom: 10rem;
  155. }
  156. h1 span {
  157. position: absolute;
  158. top: 1vh;
  159. left: 20%;
  160. line-height: 0;
  161. }
  162. h1 span a {
  163. line-height: 1.7;
  164. padding: 1rem 1.2rem .6rem 1.2rem;
  165. border-radius: 0 0 6% 6%;
  166. background: #2d7474;
  167. font-size: 1.3rem;
  168. color: white;
  169. text-decoration: none;
  170. }
  171. h2 {
  172. margin: 4rem 0 1rem;
  173. border-top: .2vh solid #2d7474;
  174. padding-top: 1vh;
  175. }
  176. h3 {
  177. text-align: center;
  178. margin: 3rem 0 .75em;
  179. }
  180. hr {
  181. height: .4rem;
  182. width: .4rem;
  183. border-radius: .4rem;
  184. background: #07486c;
  185. margin: 2.5rem auto;
  186. }
  187. time {
  188. display: bloc;
  189. margin-left: 0 !important;
  190. }
  191. ul, ol {
  192. margin: 2rem;
  193. }
  194. ul {
  195. list-style-type: square;
  196. }
  197. a {
  198. text-decoration-skip-ink: auto;
  199. text-decoration-thickness: 0.05em;
  200. text-underline-offset: 0.09em;
  201. }
  202. article {
  203. max-width: 50rem;
  204. display: flex;
  205. flex-direction: column;
  206. margin: 2rem auto;
  207. }
  208. article.single {
  209. border-top: .2vh dotted #2d7474;
  210. margin: -6rem auto 1rem auto;
  211. background: #f0f0ea;
  212. padding: 2rem;
  213. }
  214. article p:last-child {
  215. margin-bottom: 1rem;
  216. }
  217. p {
  218. padding: 0 .5rem;
  219. margin-left: 3rem;
  220. }
  221. p + p,
  222. figure + p {
  223. margin-top: 2rem;
  224. }
  225. blockquote {
  226. background-color: #e3e1e1;
  227. border-left: .5vw solid #2d7474;
  228. display: flex;
  229. flex-direction: column;
  230. align-items: center;
  231. padding: 1rem;
  232. margin: 1.5rem;
  233. }
  234. blockquote cite {
  235. font-style: italic;
  236. }
  237. blockquote p {
  238. margin-left: 0;
  239. }
  240. figure {
  241. border-top: .2vh solid #2d7474;
  242. background-color: #e3e1e1;
  243. text-align: center;
  244. padding: 1.5rem 0;
  245. margin: 1rem 0 0;
  246. font-size: 1.5rem;
  247. width: 100%;
  248. }
  249. figure img {
  250. max-width: 250px;
  251. max-height: 250px;
  252. border: .5vw solid #323a45;
  253. padding: 1px;
  254. }
  255. figcaption {
  256. padding: 1rem;
  257. line-height: 1.4;
  258. }
  259. aside {
  260. display: flex;
  261. flex-direction: column;
  262. background-color: #e3e1e1;
  263. padding: 1rem 0;
  264. border-bottom: .2vh solid #07486c;
  265. }
  266. aside p {
  267. max-width: 50rem;
  268. margin: 0 auto;
  269. }
  270. /* https://fvsch.com/code/css-locks/ */
  271. p, li, pre, code, kbd, samp, var, tt, time, details, figcaption {
  272. font-size: 1rem;
  273. line-height: calc( 1.5em + 0.2 * 1rem );
  274. }
  275. h1 {
  276. font-size: 1.9rem;
  277. line-height: calc( 1.2em + 0.2 * 1rem );
  278. }
  279. h2 {
  280. font-size: 1.6rem;
  281. line-height: calc( 1.3em + 0.2 * 1rem );
  282. }
  283. h3 {
  284. font-size: 1.35rem;
  285. line-height: calc( 1.4em + 0.2 * 1rem );
  286. }
  287. @media (min-width: 20em) {
  288. /* The (100vw - 20rem) / (50 - 20) part
  289. resolves to 0-1rem, depending on the
  290. viewport width (between 20em and 50em). */
  291. p, li, pre, code, kbd, samp, var, tt, time, details, figcaption {
  292. font-size: calc( 1rem + .6 * (100vw - 20rem) / (50 - 20) );
  293. line-height: calc( 1.5em + 0.2 * (100vw - 50rem) / (20 - 50) );
  294. margin-left: 0;
  295. }
  296. h1 {
  297. font-size: calc( 1.9rem + 1.5 * (100vw - 20rem) / (50 - 20) );
  298. line-height: calc( 1.2em + 0.2 * (100vw - 50rem) / (20 - 50) );
  299. }
  300. h2 {
  301. font-size: calc( 1.5rem + 1.5 * (100vw - 20rem) / (50 - 20) );
  302. line-height: calc( 1.3em + 0.2 * (100vw - 50rem) / (20 - 50) );
  303. }
  304. h3 {
  305. font-size: calc( 1.35rem + 1.5 * (100vw - 20rem) / (50 - 20) );
  306. line-height: calc( 1.4em + 0.2 * (100vw - 50rem) / (20 - 50) );
  307. }
  308. }
  309. @media (min-width: 50em) {
  310. /* The right part of the addition *must* be a
  311. rem value. In this example we *could* change
  312. the whole declaration to font-size:2.5rem,
  313. but if our baseline value was not expressed
  314. in rem we would have to use calc. */
  315. p, li, pre, code, kbd, samp, var, tt, time, details, figcaption {
  316. font-size: calc( 1rem + .6 * 1rem );
  317. line-height: 1.5em;
  318. }
  319. p, li, pre, details {
  320. margin-left: 3rem;
  321. }
  322. h1 {
  323. font-size: calc( 1.9rem + 1.5 * 1rem );
  324. line-height: 1.2em;
  325. }
  326. h2 {
  327. font-size: calc( 1.5rem + 1.5 * 1rem );
  328. line-height: 1.3em;
  329. }
  330. h3 {
  331. font-size: calc( 1.35rem + 1.5 * 1rem );
  332. line-height: 1.4em;
  333. }
  334. figure img {
  335. max-width: 500px;
  336. max-height: 500px;
  337. }
  338. }
  339. figure.unsquared {
  340. margin-bottom: 1.5rem;
  341. }
  342. figure.unsquared img {
  343. height: inherit;
  344. }
  345. @media print {
  346. body { font-size: 100%; }
  347. a:after { content: " (" attr(href) ")"; }
  348. a, a:link, a:visited, a:after {
  349. text-decoration: underline;
  350. text-shadow: none !important;
  351. background-image: none !important;
  352. background: white;
  353. color: black;
  354. }
  355. abbr[title] { border-bottom: 0; }
  356. abbr[title]:after { content: " (" attr(title) ")"; }
  357. img { page-break-inside: avoid; }
  358. @page { margin: 2cm .5cm; }
  359. h1, h2, h3 { page-break-after: avoid; }
  360. p3 { orphans: 3; widows: 3; }
  361. img {
  362. max-width: 250px !important;
  363. max-height: 250px !important;
  364. }
  365. nav, aside { display: none; }
  366. }
  367. ul.with_columns {
  368. column-count: 1;
  369. }
  370. @media (min-width: 20em) {
  371. ul.with_columns {
  372. column-count: 2;
  373. }
  374. }
  375. @media (min-width: 50em) {
  376. ul.with_columns {
  377. column-count: 3;
  378. }
  379. }
  380. ul.with_two_columns {
  381. column-count: 1;
  382. }
  383. @media (min-width: 20em) {
  384. ul.with_two_columns {
  385. column-count: 1;
  386. }
  387. }
  388. @media (min-width: 50em) {
  389. ul.with_two_columns {
  390. column-count: 2;
  391. }
  392. }
  393. .gallery {
  394. display: flex;
  395. flex-wrap: wrap;
  396. justify-content: space-around;
  397. }
  398. .gallery figure img {
  399. margin-left: 1rem;
  400. margin-right: 1rem;
  401. }
  402. .gallery figure figcaption {
  403. font-family: 'ConcourseT3'
  404. }
  405. footer {
  406. font-family: 'ConcourseT3';
  407. display: flex;
  408. flex-direction: column;
  409. border-top: 3px solid white;
  410. padding: 4rem 0;
  411. background-color: #07486c;
  412. color: white;
  413. }
  414. footer > * {
  415. max-width: 50rem;
  416. margin: 0 auto;
  417. }
  418. footer a {
  419. color: #f1c40f;
  420. }
  421. footer .avatar {
  422. width: 200px;
  423. height: 200px;
  424. border-radius: 50%;
  425. float: left;
  426. -webkit-shape-outside: circle();
  427. shape-outside: circle();
  428. margin-right: 2rem;
  429. padding: 2px 5px 5px 2px;
  430. background: white;
  431. border-left: 1px solid #f1c40f;
  432. border-top: 1px solid #f1c40f;
  433. border-right: 5px solid #f1c40f;
  434. border-bottom: 5px solid #f1c40f;
  435. }
  436. </style>
  437. <h1>
  438. <span><a id="jumper" href="#jumpto" title="Un peu perdu ?">?</a></span>
  439. Bootstrap est une régression pour un développement Front-end de qualité (archive)
  440. <time>Pour la pérennité des contenus liés. Non-indexé, retrait sur simple email.</time>
  441. </h1>
  442. <section>
  443. <article>
  444. <h3><a href="http://blog.lesieur.name/bootstrap-est-une-regression-pour-un-developpement-front-end-de-qualite/">Source originale du contenu</a></h3>
  445. <p>Pourquoi je n&#39;utilise pas <a href="http://getbootstrap.com/" title="Le framework de développement Front-end responsive et mobile first le plus populaire du web">Bootstrap</a> ? Cela peut sembler une « évolution » de nos méthodes de travail Front-end, mais gare au loup et attention de ne pas tomber dans un travers que le W3C tente d&#39;enrayer au fur et à mesure des évolutions HTML et CSS.</p>
  446. <p>Commençons par le commencement. Qu&#39;est-ce que <a href="http://getbootstrap.com/" title="Le framework de développement Front-end responsive et mobile first le plus populaire du web">Bootstrap</a> ? Comme pleins d&#39;autres « Librairie » ou « Framework » CSS dans la même veine, <a href="http://getbootstrap.com/" title="Le framework de développement Front-end responsive et mobile first le plus populaire du web">Bootstrap</a> est un outil permettant d&#39;augmenter la productivité des développeurs Front-end le maîtrisant, dans le but de fournir le plus rapidement possible un rendu visuel ergonomique et si possible responsive.</p>
  447. <p>Mon problème ne vient pas tant de sa finalité qui est louable, mais belle et bien de la mise en œuvre technique qui permet d&#39;atteindre cette finalité. Pour être concis avant de développer : <a href="http://getbootstrap.com/" title="Le framework de développement Front-end responsive et mobile first le plus populaire du web">Bootstrap</a> est une régression pour un travail Front-end de qualité.</p>
  448. <p>Je ne compte persuader personne, et à défaut de convaincre, je vais au moins vous expliquer mon point de vue.</p>
  449. <h2 id="les-deux-approches-possibles-pour-de-l-int-gration-front-end">Les deux approches possibles pour de l&#39;intégration Front-end</h2>
  450. <h3 id="l-approche-s-mantique-visuelle-ou-celle-du-w3c-http-www-w3-org-">L&#39;approche Sémantique/Visuelle (ou celle du <a href="http://www.w3.org/">W3C</a>)</h3>
  451. <p>Cette approche considère que dans un fichier HTML, les balises doivent avoir du sens et être complétées (que ce soit par leurs genres, leurs noms, leurs ids ou leurs classes) de manière sémantique de façon à donner du sens au document.</p>
  452. <blockquote>
  453. <h4 id="exemple">Exemple</h4>
  454. <p>Si j&#39;ai deux éléments qui se suivent : le premier pourrait porter l&#39;attribut <samp>class=&quot;main&quot;</samp> et le second l&#39;attribut <samp>class=&quot;aside&quot;</samp>.</p>
  455. </blockquote>
  456. <p><strong>L&#39;attribut <samp>class</samp> est donc dans cette approche une extension de l&#39;attribut <samp>id</samp> (mais en version multiple) et le HTML garde un unique rôle : le rôle sémantique.</strong></p>
  457. <h3 id="l-approche-tout-en-un-ou-celle-de-bootstrap-amp-cie-">L&#39;approche « Tout en un » (ou celle de <a href="http://getbootstrap.com/" title="Le framework de développement Front-end responsive et mobile first le plus populaire du web">Bootstrap</a> &amp; cie)</h3>
  458. <p>Cette approche considère que dans un fichier HTML, les balises doivent représenter un visuel et être complétées de manière à laisser transparaître rapidement le résultat visuel.</p>
  459. <blockquote>
  460. <h4 id="exemple">Exemple</h4>
  461. <p>Si j&#39;ai deux éléments qui se suivent : le premier pourrait porter l&#39;attribut <samp>class=&quot;left&quot;</samp> et le second l&#39;attribut <samp>class=&quot;right&quot;</samp>.</p>
  462. </blockquote>
  463. <p><strong>L&#39;attribut <samp>class</samp> est donc dans cette approche une extension de l&#39;attribut <samp>style</samp> (mais une sorte de raccourci) où il n&#39;est pas nécessaire de lister les directives CSS en inline mais dans un fichier CSS séparé.</strong></p>
  464. <h2 id="comparaison-de-code-des-deux-approches">Comparaison de code des deux approches</h2>
  465. <p>Pour les plus curieux, voici techniquement la différence entres les codes :</p>
  466. <h3 id="s-mantique-et-visuel-s-par-">Sémantique et visuel séparé</h3>
  467. <p><strong>HTML :</strong></p>
  468. <pre class="prettyprint linenums"><code class="lang-html">&lt;header&gt;
  469. &lt;h1&gt;Le titre&lt;/h1&gt;
  470. &lt;nav&gt;
  471. &lt;ul&gt;
  472. &lt;li&gt;menu&lt;/li&gt;
  473. &lt;li&gt;menu&lt;/li&gt;
  474. &lt;li&gt;menu&lt;/li&gt;
  475. &lt;li&gt;menu&lt;/li&gt;
  476. &lt;/ul&gt;
  477. &lt;/nav&gt;
  478. &lt;/header&gt;
  479. &lt;section&gt;
  480. &lt;article&gt;
  481. &lt;p&gt;Le contenu&lt;br&gt;
  482. Le contenu&lt;br&gt;
  483. Le contenu&lt;/p&gt;
  484. &lt;/article&gt;
  485. &lt;aside&gt;Les à cotés&lt;/aside&gt;
  486. &lt;/section&gt;
  487. </code></pre>
  488. <p><strong>CSS :</strong></p>
  489. <pre class="prettyprint linenums"><code class="lang-css">/* Entrer le padding dans le calcul interne */
  490. h1,
  491. nav,
  492. article,
  493. aside {
  494. box-sizing: border-box;
  495. }
  496. /* Mettre le titre en gras */
  497. h1 {
  498. font-weight: bold;
  499. }
  500. /* Centrer les textes du menu */
  501. nav {
  502. text-align: center;
  503. }
  504. /* Retrait du comportement de liste standard */
  505. nav ul {
  506. padding-left: 0;
  507. }
  508. nav li {
  509. list-style-type: none;
  510. }
  511. /* À partir d&#39;une tablette */
  512. @media (min-width: 768px) {
  513. /* Empêcher les écoulements de flottants */
  514. header:after,
  515. section:after {
  516. content: &quot;&quot;;
  517. display: block;
  518. clear: both;
  519. }
  520. /* Flotter à gauche en 50% */
  521. h1,
  522. aside {
  523. float: left;
  524. width: 50%;
  525. }
  526. /* Flotter à droite en 50% */
  527. h1,
  528. article {
  529. float: right;
  530. width: 50%;
  531. }
  532. /* Remettre les menus en alignement standard */
  533. nav {
  534. text-align: left;
  535. }
  536. /* Mettre le menu en ligne */
  537. nav li {
  538. display: inline-block;
  539. }
  540. /* Placer le titre à droite */
  541. h1 {
  542. text-align: right;
  543. }
  544. }
  545. </code></pre>
  546. <p><strong>Rendu</strong></p>
  547. <blockquote>
  548. <div class="example-header">
  549. <div class="example-logo"><p>Le logo</p></div>
  550. <div class="example-menu">
  551. <ul>
  552. <li>menu</li>
  553. <li>menu</li>
  554. <li>menu</li>
  555. <li>menu</li>
  556. </ul><br> </div>
  557. </div>
  558. <div class="example-content">
  559. <div class="example-main">
  560. <p>Le contenu<br>
  561. Le contenu<br>
  562. Le contenu</p>
  563. </div>
  564. <div class="example-aside"><p>Les à coté</p></div>
  565. </div>
  566. </blockquote>
  567. <p><em>Note : vous pouvez rétrécir votre fenêtre sur périphérique desktop pour voir le résultat mobile.</em></p>
  568. <h3 id="framework-css-comme-bootstrap">Framework CSS comme Bootstrap</h3>
  569. <p><strong>HTML :</strong></p>
  570. <pre class="prettyprint linenums"><code class="lang-html">&lt;header class=&quot;container&quot;&gt;
  571. &lt;div class=&quot;row&quot;&gt;
  572. &lt;h1 class=&quot;col-sm-6 col-sm-push-6 text-right-sm&quot;&gt;
  573. &lt;strong&gt;Le titre&lt;/strong&gt;
  574. &lt;/h1&gt;
  575. &lt;nav class=&quot;col-sm-6 col-sm-pull-6 text-center-xs text-left-sm&quot;&gt;
  576. &lt;div class=&quot;navbar-collapse collapse in&quot;&gt;
  577. &lt;ul class=&quot;nav navbar-nav&quot;&gt;
  578. &lt;li&gt;Menu&lt;/li&gt;
  579. &lt;li&gt;Menu&lt;/li&gt;
  580. &lt;li&gt;Menu&lt;/li&gt;
  581. &lt;li&gt;Menu&lt;/li&gt;
  582. &lt;/ul&gt;
  583. &lt;/div&gt;
  584. &lt;/nav&gt;
  585. &lt;/div&gt;
  586. &lt;/header&gt;
  587. &lt;section class=&quot;container&quot;&gt;
  588. &lt;div class=&quot;row&quot;&gt;
  589. &lt;article class=&quot;col-sm-6 col-sm-push-6&quot;&gt;
  590. &lt;p&gt;Le contenu&lt;br&gt;
  591. Le contenu&lt;br&gt;
  592. Le contenu&lt;/p&gt;
  593. &lt;/article&gt;
  594. &lt;aside class=&quot;col-sm-6 col-sm-pull-6&quot;&gt;Les à coté&lt;/aside&gt;
  595. &lt;/div&gt;
  596. &lt;/section&gt;
  597. </code></pre>
  598. <p><strong>CSS :</strong></p>
  599. <pre class="prettyprint linenums"><code class="lang-html">&lt;!-- État de boite noire, ça marche tel que la doc l&#39;explique --&gt;
  600. &lt;link rel=&quot;stylesheet&quot; href=&quot;//netdna.bootstrapcdn.com/bootstrap/3.1.1/css/bootstrap.min.css&quot;&gt;
  601. </code></pre>
  602. <pre class="prettyprint linenums"><code class="lang-css">/* Parce que Bootstrap ne réalise pas tout ce que
  603. l&#39;on souhaite faire, on surcharge ensuite avec sa
  604. propre CSS en essayant de conserver
  605. la philosophie Bootstrap (pas simple) */
  606. /* Comportement par défaut */,
  607. .text-center-sm,
  608. .text-center-md,
  609. .text-center-lg,
  610. .text-right-sm,
  611. .text-right-md,
  612. .text-right-lg {
  613. text-align: inherit;
  614. }
  615. /* Style par défaut */
  616. .text-center-xs {
  617. text-align: center;
  618. }
  619. .text-right-xs {
  620. text-align: right;
  621. }
  622. /* Style pour tablette */
  623. @media (min-width: 768px) {
  624. .text-center-sm,
  625. .text-center-xs {
  626. text-align: center;
  627. }
  628. .text-right-sm,
  629. .text-right-xs {
  630. text-align: right;
  631. }
  632. }
  633. /* Style pour desktop */
  634. @media (min-width: 992px) {
  635. .text-center-md,
  636. .text-center-sm,
  637. .text-center-xs {
  638. text-align: center;
  639. }
  640. .text-right-md,
  641. .text-right-sm,
  642. .text-right-xs {
  643. text-align: right;
  644. }
  645. }
  646. /* Style pour grand desktop */
  647. @media (min-width: 1200px) {
  648. .text-center-lg,
  649. .text-center-md,
  650. .text-center-sm,
  651. .text-center-xs {
  652. text-align: center;
  653. }
  654. .text-right-lg,
  655. .text-right-md,
  656. .text-right-sm,
  657. .text-right-xs {
  658. text-align: right;
  659. }
  660. }
  661. </code></pre>
  662. <p><em>Note : une autre approche est de dupliquer un objet que <a href="http://getbootstrap.com/" title="Le framework de développement Front-end responsive et mobile first le plus populaire du web">Bootstrap</a> ne saurait pas facilement afficher dans des états différents en fonction de la taille du périphérique afin de n&#39;en afficher qu&#39;un des deux à la fois. Ce qui créé du contenu dupliqué.</em></p>
  663. <p><strong>Rendu</strong></p>
  664. <blockquote>
  665. <div class="example-header">
  666. <div class="example-logo"><p>Le logo</p></div>
  667. <div class="example-menu"><p>menu menu menu menu</p></div>
  668. </div>
  669. <div class="example-content">
  670. <div class="example-main">
  671. <p>Le contenu<br>
  672. Le contenu<br>
  673. Le contenu</p>
  674. </div>
  675. <div class="example-aside"><p>Les à coté</p></div>
  676. </div>
  677. </blockquote>
  678. <p><em>Note : vous pouvez rétrécir votre fenêtre sur périphérique desktop pour voir le résultat mobile.</em></p>
  679. <h2 id="pourquoi-l-approche-s-mantique-est-la-meilleure-selon-moi-">Pourquoi l&#39;approche sémantique est la meilleure (selon moi)</h2>
  680. <h3 id="la-raison-historique-de-la-s-paration-du-fond-et-de-la-forme">La raison historique ; de la séparation du fond et de la forme</h3>
  681. <p>Le W3C améliore les normes de structures HTML dans un but de séparation de la structure et du rendu. Voyons ça plus en détail :</p>
  682. <h4 id="d-abord-html">D&#39;abord HTML</h4>
  683. <p>Le HTML dans ses débuts embarquait des balises permettant de créer du fond (ou de structurer) tel que <samp>&lt;div&gt;</samp>, <samp>&lt;span&gt;</samp>, <samp>&lt;table&gt;</samp>, etc. et des balises permettant de créer de la forme (ou du rendu) tel que <samp>&lt;font&gt;</samp>, <samp>&lt;i&gt;</samp>, <samp>&lt;b&gt;</samp>, <samp>&lt;center&gt;</samp>, etc. Les deux étaient mélangés et c&#39;est bien dans le fichier HTML, au travers de sa structure que l&#39;on décidait qu&#39;un texte devrait être rouge, centré et avoir une taille de 20 pixel.</p>
  684. <h4 id="puis-le-xhtml">Puis le xHTML</h4>
  685. <p>Une évolution logique a donc été de supprimer (ou déprécier) les balises porteuses d&#39;un rendu visuel et de leur préférer un sens sémantique (tout en accordant une grande importance au CSS pour l&#39;habillage). Ainsi un texte centré ou rouge se créé via une feuille CSS et on ne considère plus un texte important comme <samp>&lt;b&gt;</samp> (bold) mais plutôt ayant un sens <samp>&lt;strong&gt;</samp> (fort). C&#39;est au développeur de choisir si finalement <samp>&lt;strong&gt;</samp> n&#39;a pas plutôt un rendu italique et souligné via CSS.</p>
  686. <p>Il y a donc une volonté du Web de séparer la structure et le rendu. Ce que je trouve assez logique.</p>
  687. <h4 id="on-continue-avec-le-html5">On continue avec le HTML5</h4>
  688. <p>Toujours dans ce soucis de structure sémantique, les balises en elles-mêmes se voit rajoutée du sens et c&#39;est pour cela que <samp>&lt;header&gt;</samp>, <samp>&lt;footer&gt;</samp>, <samp>&lt;section&gt;</samp>, <samp>&lt;article&gt;</samp>, <samp>&lt;aside&gt;</samp>, <samp>&lt;figure&gt;</samp>... font leur apparition.</p>
  689. <p>Cela signifie que l&#39;approche de <a href="http://getbootstrap.com/" title="Le framework de développement Front-end responsive et mobile first le plus populaire du web">Bootstrap</a> prend le contre-pied de cette idée de séparation et instaure selon moi une approche plus liée qui n&#39;est pas en accord avec la philosophie que je partage avec le W3C.</p>
  690. <h2 id="les-raisons-techniques">Les raisons techniques</h2>
  691. <h3 id="la-taille-du-fichier-html-g-n-r-">La taille du fichier HTML généré</h3>
  692. <p>Ajouter des classes à outrance pour habiller visuellement sa structure HTML surcharge anormalement le DOM d&#39;au moins trois manières :</p>
  693. <ul>
  694. <li>Obligation d&#39;imbriquer des éléments pour qu&#39;ils fonctionnent tels que <a href="http://getbootstrap.com/" title="Le framework de développement Front-end responsive et mobile first le plus populaire du web">Bootstrap</a> l&#39;a prévu.</li>
  695. <li>Multiplication du nombre de classes dans l&#39;attribut <samp>class</samp>.</li>
  696. <li>Duplication de contenu pour afficher/masquer simplement en fonction de la taille du périphérique.</li>
  697. </ul>
  698. <p>Cela défère le poids de la CSS vers le HTML. Or, autant les fichiers CSS peuvent être mis en cache, autant la structure HTML peut difficilement l&#39;être étant donné sa nature changeante en fonction du contrôleur qui la génère.</p>
  699. <h3 id="la-surcharge-css">La surcharge CSS</h3>
  700. <p><a href="http://getbootstrap.com/" title="Le framework de développement Front-end responsive et mobile first le plus populaire du web">Bootstrap</a> n&#39;est pas négligeable en taille. Cela impose un pré-chargement plus lourds au premier chargement de page (en supposant qu&#39;ensuite le fichier soit mis en cache). De manière assez amusante, plus Bootstrap &quot;supporte&quot; des périphériques petits avec de faibles débits à l&#39;utilisation (ajout de fichiers CSS et JS), plus il est lourd en poids...</p>
  701. <h3 id="la-ma-trise-de-l-outil">La maîtrise de l&#39;outil</h3>
  702. <p>L&#39;avantage offert par <a href="http://getbootstrap.com/" title="Le framework de développement Front-end responsive et mobile first le plus populaire du web">Bootstrap</a> est perdu dès l&#39;instant ou l&#39;outil est utilisé par des personnes ne le connaissant pas (rapidité d&#39;intégration). Pire encore, cela expose l&#39;intégration par de multiples personnes à mélanger l&#39;approche <a href="http://getbootstrap.com/" title="Le framework de développement Front-end responsive et mobile first le plus populaire du web">Bootstrap</a> à une approche sémantique.</p>
  703. <h3 id="maintenance-de-code-et-changement-de-design">Maintenance de code et changement de design</h3>
  704. <p>La structure étant intimement liée au Framework <a href="http://getbootstrap.com/" title="Le framework de développement Front-end responsive et mobile first le plus populaire du web">Bootstrap</a> et au visuel soumis, le code HTML est bon à revoir dans son architecture pour un changement de design. La structure étant liée aux contrôleurs, car créée par eux, c&#39;est le Back-end qui se retrouve impacté par un changement de design là ou seulement les CSS et les JS auraient du bouger (sans que le Back soit touché par du changement de design).</p>
  705. <h3 id="ne-pas-rendre-service-au-front-end-apprenant">Ne pas rendre service au Front-end apprenant</h3>
  706. <p>L&#39;approche « tout en un » masque le plus important : les mécanismes de fonctionnement des classes en elles-mêmes. Pourquoi -pour réaliser telles actions- elles utilisent ces attributs précisément ? Si cet état de boîte noire peut s&#39;avérer intéressant pour des débutants et un gain de temps pour les experts : cela maintient l&#39;écart entre les deux. Et, les seuls apprenant réellement à utiliser les nouveautés du CSS en comprenant les mécanismes sous-jacent sont ceux qui maintiennent <a href="http://getbootstrap.com/" title="Le framework de développement Front-end responsive et mobile first le plus populaire du web">Bootstrap</a> (ou équivalent) ou ceux qui ne l&#39;utilisent pas.</p>
  707. <h3 id="un-probl-me-de-seo-ou-de-performance-">Un problème de SEO ou de performance ?</h3>
  708. <p>Dupliquer du contenu de manière identique dans le DOM dans le seul but de l&#39;afficher à deux endroits différents de la grille <a href="http://getbootstrap.com/" title="Le framework de développement Front-end responsive et mobile first le plus populaire du web">Bootstrap</a> créer du contenu dupliqué au sein d&#39;une même page. Bien entendu, on peut éviter cela en laissant dans le DOM source le code destiné au mobile et en dupliquant en JavaScript celui-ci pour l&#39;afficher sur desktop en sacrifiant un peu de ressource JavaScript et en masquant tant bien que mal le phénomène de <a href="http://fr.wikipedia.org/wiki/FOUC">FOUC</a>.</p>
  709. <h2 id="pourquoi-utiliser-bootstrap-alors-">Pourquoi utiliser Bootstrap alors ?</h2>
  710. <h3 id="-utiliser-pour-">À utiliser pour :</h3>
  711. <ul>
  712. <li>Développer des « Proof of Concept » ou remplacer la création PSD par une création temps réel de façon rapide.</li>
  713. <li>Faire des sites à la pelle et avec de très petits budgets où le résultat en performance et en qualité reste un problème, mais où l&#39;argent fournit pour la réalisation manque.</li>
  714. <li>Habiller un Back-office personnalisé (ou une application web) qui n&#39;a pas fait l&#39;objet d&#39;une créa et que l&#39;on espère « user friendly » rapidement et simplement (une création purement fonctionnelle sans problèmes de performances à grande échelle ou de soucis de SEO).</li>
  715. </ul>
  716. <h3 id="-ne-pas-utiliser-pour-">À ne pas utiliser pour :</h3>
  717. <ul>
  718. <li>Des petits sites, car cela augmente bien souvent de 90% le poids du site, il vaut donc mieux ne pas le faire et perdre un peu de temps pour un gain en performance maintenance et sémantique.</li>
  719. <li>De grosses structures, car cela leurs font perdre la flexibilité du changement d&#39;UI sans impacter le Back-end, impose la formation de toutes les ressources Front-end travaillant sur le projet à Bootstrap et il résulte de la construction même des pages un impact SEO non négligeable due au poids du HTML, sa sémantique limitée et plus globalement au temps de chargement des pages.</li>
  720. </ul>
  721. <blockquote>
  722. <h4 id="semantic-ui">Semantic UI</h4>
  723. <p><strong><samp>Bonne idée :</samp></strong> Pour ma part, quitte à devoir être HTML-driven et non pas Stylesheet-driven pour l&#39;habillage CSS, autant utiliser des Framework tel que Semantic UI qui au moins garde la philosophie du composant qui explique ce qu&#39;il fait et non ce à quoi il ressemble.</p>
  724. <blockquote>
  725. <p><a href="http://semantic-ui.com/">Voir le projet Semantic UI</a></p>
  726. </blockquote>
  727. </blockquote>
  728. <h2 id="m-langer-les-deux-approches-pour-en-garder-les-avantages-">Mélanger les deux approches pour en garder les avantages ?</h2>
  729. <p>Si l&#39;on extrait les problèmes majeurs en considérant que nos ressources seront formées à utiliser <a href="http://getbootstrap.com/" title="Le framework de développement Front-end responsive et mobile first le plus populaire du web">Bootstrap</a> nous nous retrouvons avec les deux points suivants.</p>
  730. <h3 id="la-lourdeur-de-la-librairie">La lourdeur de la librairie</h3>
  731. <p>Que ce soit pour <a href="http://getbootstrap.com/" title="Le framework de développement Front-end responsive et mobile first le plus populaire du web">Bootstrap</a> ou pour une autre librairie, le premier chargement sera laborieux (avant que le fichier n&#39;ai été téléchargé une fois et mis en cache). On peut palier à ce problème en utilisant une version du script hébergé sur des serveurs comme c&#39;est le cas pour jQuery par exemple. Ainsi pour Bootstrap, on peut se faire servir par <a href="http://www.bootstrapcdn.com/" title="CDN for Bootstrap">http://www.bootstrapcdn.com/</a>. L&#39;avantage est que tous les sites utilisant le chargement par CDN Bootsrap participe à mettre en cache pour vous le fichier. Cela signifie que ce n&#39;est plus nécessairement votre première page ouverte qui ralentira le chargement du visiteur mais peut-être celle d&#39;un autre site.</p>
  732. <h3 id="remettre-les-classes-tout-en-un-de-nouveau-dans-la-css">Remettre les classes « tout en un » de nouveau dans la CSS</h3>
  733. <p>Finalement, ce qu&#39;il nous faudrait pour résoudre notre soucis et remettre la sémantique à l&#39;ordre du jour, c&#39;est d&#39;adresser dans la feuille CSS (et non dans la page HTML elle-même) notre suite de classe. Si nous pouvions par exemple transformer ceci :</p>
  734. <pre class="prettyprint linenums"><code class="lang-html">&lt;div class=&quot;clr&quot;&gt;
  735. &lt;div class=&quot;left hidden boxsizing w50&quot;&gt;
  736. Le logo
  737. &lt;/div&gt;
  738. &lt;/div&gt;
  739. </code></pre>
  740. <p>en ceci</p>
  741. <pre class="prettyprint linenums"><code class="lang-html">&lt;div class=&quot;header&quot;&gt;
  742. &lt;div class=&quot;logo&quot;&gt;
  743. Le logo
  744. &lt;/div&gt;
  745. &lt;/div&gt;
  746. </code></pre>
  747. <pre class="prettyprint linenums"><code class="lang-css">/* Fichier complet type Bootstrap */
  748. .header {
  749. .clr;
  750. }
  751. .logo {
  752. .left;
  753. .hidden;
  754. .boxsizing;
  755. .w50;
  756. }
  757. </code></pre>
  758. <p>le tour serait joué.</p>
  759. <p>C&#39;est exactement ce que permettent des approches comme <a href="http://sass-lang.com/" title="Sass - Syntactically Awesome Stylesheets">SASS</a> ou <a href="http://lesscss.org/" title="LESS &laquo; The Dynamic Stylesheet language">LESS</a>. Elles permettent d&#39;écrire de manière intuitive et non redondante des suites de sélecteurs CSS pour au final générer le fichier CSS qui va bien. Vous pouvez lire l&#39;article « <a href="http://blog.lesieur.name/utilisation-optimisee-de-framework-css-comme-bootstrap-avec-less/">Utilisation optimisée de Framework CSS comme Bootstrap avec Less</a> » pour comprendre comment cela fonctionne et de cette manière vous pourrez remplir vos classes HTML de manière sémantique tout en conservant vos habitudes d&#39;intégration avec <a href="http://getbootstrap.com/" title="Le framework de développement Front-end responsive et mobile first le plus populaire du web">Bootstrap</a> par exemple.</p>
  760. <h2 id="mon-retour-rapide-sur-l-utilisation-bootstrap">Mon retour rapide sur l&#39;utilisation Bootstrap</h2>
  761. <p>Je trouve que les types de sites réalisés avec Bootstrap se ressemble tous et qu&#39;il devient difficile de faire quelque chose s&#39;en éloignant sans finalement perdre du temps. <a href="http://getbootstrap.com/" title="Le framework de développement Front-end responsive et mobile first le plus populaire du web">Bootstrap</a> devient ici plus contraignant pour la patte créative également et on en vient parfois même à blâmer les agences de création digital car leurs créations ne sont pas « compliant » Bootstrap.</p>
  762. <p>Pour exemple voici des variations de design pour un HTML identique en CSS-driven :</p>
  763. <p><em><a href="http://www.nicolas-hoffmann.net/">Site de Nicolas Hoffmann</a></em></p>
  764. <ul>
  765. <li><a href="http://www.nicolas-hoffmann.net/source/changer_skin.php?theme=ND_mobfirst">ND Mobi First</a></li>
  766. <li><a href="http://www.nicolas-hoffmann.net/source/changer_skin.php?theme=ND_new_green">ND New Green</a></li>
  767. <li><a href="http://www.nicolas-hoffmann.net/source/changer_skin.php?theme=ND">ND</a></li>
  768. <li><a href="http://www.nicolas-hoffmann.net/source/changer_skin.php?theme=firefox">Firefox</a></li>
  769. </ul>
  770. <p>et la même chose pour un HTML identique avec Bootstrap</p>
  771. <p><em><a href="https://github.com/terryweiss/docstrap">Template pour documentation JSDoc</a></em></p>
  772. <ul>
  773. <li><a href="http://terryweiss.github.io/docstrap/themes/amelia/">Amelia</a></li>
  774. <li><a href="http://terryweiss.github.io/docstrap/themes/cyborg/">Cyborg</a></li>
  775. <li><a href="http://terryweiss.github.io/docstrap/themes/readable/">Readable</a></li>
  776. <li><a href="http://terryweiss.github.io/docstrap/themes/superhero/">DocStrap</a></li>
  777. </ul>
  778. <p>CQFD.</p>
  779. </article>
  780. </section>
  781. <nav id="jumpto">
  782. <p>
  783. <a href="/david/blog/">Accueil du blog</a> |
  784. <a href="http://blog.lesieur.name/bootstrap-est-une-regression-pour-un-developpement-front-end-de-qualite/">Source originale</a> |
  785. <a href="/david/stream/2019/">Accueil du flux</a>
  786. </p>
  787. </nav>
  788. <footer>
  789. <div>
  790. <img src="/static/david/david-larlet-avatar.jpg" loading="lazy" class="avatar" width="200" height="200">
  791. <p>
  792. Bonjour/Hi!
  793. Je suis <a href="/david/" title="Profil public">David&nbsp;Larlet</a>, je vis actuellement à Montréal et j’alimente cet espace depuis 15 ans. <br>
  794. Si tu as apprécié cette lecture, n’hésite pas à poursuivre ton exploration. Par exemple via les <a href="/david/blog/" title="Expériences bienveillantes">réflexions bimestrielles</a>, la <a href="/david/stream/2019/" title="Pensées (dés)articulées">veille hebdomadaire</a> ou en t’abonnant au <a href="/david/log/" title="S’abonner aux publications via RSS">flux RSS</a> (<a href="/david/blog/2019/flux-rss/" title="Tiens c’est quoi un flux RSS ?">so 2005</a>).
  795. </p>
  796. <p>
  797. Je m’intéresse à la place que je peux avoir dans ce monde. En tant qu’humain, en tant que membre d’une famille et en tant qu’associé d’une coopérative. De temps en temps, je fais aussi des <a href="https://github.com/davidbgk" title="Principalement sur Github mais aussi ailleurs">trucs techniques</a>. Et encore plus rarement, <a href="/david/talks/" title="En ce moment je laisse plutôt la place aux autres">j’en parle</a>.
  798. </p>
  799. <p>
  800. Voici quelques articles choisis :
  801. <a href="/david/blog/2019/faire-equipe/" title="Accéder à l’article complet">Faire équipe</a>,
  802. <a href="/david/blog/2018/bivouac-automnal/" title="Accéder à l’article complet">Bivouac automnal</a>,
  803. <a href="/david/blog/2018/commodite-effondrement/" title="Accéder à l’article complet">Commodité et effondrement</a>,
  804. <a href="/david/blog/2017/donnees-communs/" title="Accéder à l’article complet">Des données aux communs</a>,
  805. <a href="/david/blog/2016/accompagner-enfant/" title="Accéder à l’article complet">Accompagner un enfant</a>,
  806. <a href="/david/blog/2016/senior-developer/" title="Accéder à l’article complet">Senior developer</a>,
  807. <a href="/david/blog/2016/illusion-sociale/" title="Accéder à l’article complet">L’illusion sociale</a>,
  808. <a href="/david/blog/2016/instantane-scopyleft/" title="Accéder à l’article complet">Instantané Scopyleft</a>,
  809. <a href="/david/blog/2016/enseigner-web/" title="Accéder à l’article complet">Enseigner le Web</a>,
  810. <a href="/david/blog/2016/simplicite-defaut/" title="Accéder à l’article complet">Simplicité par défaut</a>,
  811. <a href="/david/blog/2016/minimalisme-esthetique/" title="Accéder à l’article complet">Minimalisme et esthétique</a>,
  812. <a href="/david/blog/2014/un-web-omni-present/" title="Accéder à l’article complet">Un web omni-présent</a>,
  813. <a href="/david/blog/2014/manifeste-developpeur/" title="Accéder à l’article complet">Manifeste de développeur</a>,
  814. <a href="/david/blog/2013/confort-convivialite/" title="Accéder à l’article complet">Confort et convivialité</a>,
  815. <a href="/david/blog/2013/testament-numerique/" title="Accéder à l’article complet">Testament numérique</a>,
  816. et <a href="/david/blog/" title="Accéder aux archives">bien d’autres…</a>
  817. </p>
  818. <p>
  819. On peut <a href="mailto:david%40larlet.fr" title="Envoyer un courriel">échanger par courriel</a>. Si éventuellement tu souhaites que l’on travaille ensemble, tu devrais commencer par consulter le <a href="http://larlet.com">profil dédié à mon activité professionnelle</a> et/ou contacter directement <a href="http://scopyleft.fr/">scopyleft</a>, la <abbr title="Société coopérative et participative">SCOP</abbr> dont je fais partie depuis six ans. Je recommande au préalable de lire <a href="/david/blog/2018/cout-site/" title="Attention ce qui va suivre peut vous choquer">combien coûte un site</a> et pourquoi je suis plutôt favorable à une <a href="/david/pro/devis/" title="Discutons-en !">non-demande de devis</a>.
  820. </p>
  821. <p>
  822. Je ne traque pas ta navigation mais mon
  823. <abbr title="Alwaysdata, 62 rue Tiquetonne 75002 Paris, +33.184162340">hébergeur</abbr>
  824. conserve des logs d’accès.
  825. </p>
  826. </div>
  827. </footer>
  828. <script type="text/javascript">
  829. ;(_ => {
  830. const jumper = document.getElementById('jumper')
  831. jumper.addEventListener('click', e => {
  832. e.preventDefault()
  833. const anchor = e.target.getAttribute('href')
  834. const targetEl = document.getElementById(anchor.substring(1))
  835. targetEl.scrollIntoView({behavior: 'smooth'})
  836. })
  837. })()
  838. </script>