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.

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161
  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>SVG, le dessin vectoriel pour le web (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://www.alsacreations.com/tuto/lire/1421-svg-initiation-syntaxe-outils.html">
  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. SVG, le dessin vectoriel pour le web (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://www.alsacreations.com/tuto/lire/1421-svg-initiation-syntaxe-outils.html">Source originale du contenu</a></h3>
  445. <p class="doc-abstract">SVG est un format d'images vectorielles basé sur le langage de balisage XML. Il répond parfaitement à des besoins graphiques légers, qu'ils soient statiques, dynamiques ou interactifs.</p>
  446. <div class="doc-content"><p>
  447. <img alt="Logo SVG" class="right" src="http://www.alsacreations.com/xmedia/doc/large/svglogo.jpg"/><strong>SVG (Scalable Vector Graphics)</strong> est un format de dessin vectoriel, élaboré à partir de 1998 par un groupe de travail comprenant entre autre IBM, Apple, Microsoft, Xerox.</p>
  448. <p>
  449. Il a mis du temps à être estimé à sa juste valeur sur le Web, notamment à cause de sa lente adoption par les navigateurs. En effet, Internet Explorer ne l'a pris en charge qu'a partir de sa version 9. Il était possible, au moyen d'extensions propriétaires, de parvenir à un rendu similaire mais leur installation était contraignante et paradoxale vis-à-vis de ce format ouvert. Pour ce qui est des autres acteurs majeurs, <a href="http://www.w3.org/TR/SVG11/">SVG dans sa version 1.1</a> est reconnu et interprété, à partir de Firefox 4+, Chrome 16+, Safari 5+ et Opera 9.5+ (voir <a href="http://en.wikipedia.org/wiki/Comparison_of_layout_engines_%28Scalable_Vector_Graphics%29#SVG_1.1_support">détail des moteurs de rendu</a> sur Wikipedia).</p>
  450. <h3>
  451. Avantages</h3>
  452. <p>
  453. <img alt="" class="right" src="http://www.alsacreations.com/xmedia/doc/full/avantagesvg1.png"/>SVG est un <strong>format d'image léger</strong> lorsqu'il s'agit de représenter des formes simples, car seules les informations décrivant ces formes sont stockées (coordonnées, couleurs, effets) contrairement aux images bitmap (JPG, PNG, GIF) qui doivent mémoriser le contenu pixel par pixel. Ce principe rend les images SVG étirables <strong>sans perte de qualité</strong>. Il est également une alternative à Flash pour les petites animations lorsqu'il est combiné à <abbr title="Synchronized Multimedia Integration Language">SMIL</abbr>, ou pour présenter des données qui doivent être dynamiques.</p>
  454. <ul>
  455. <li>
  456. Son apprentissage est facile car basé sur une syntaxe simple et intuitive</li>
  457. <li>
  458. Il peut être édité par un éditeur de texte basique car c'est du <abbr title="eXtended Markup Language">XML</abbr></li>
  459. <li>
  460. Il peut être manipulé via JavaScript, car présent dans le <abbr title="Document Object Model">DOM</abbr></li>
  461. <li>
  462. Il peut être stylé grâce à <abbr title="Cascading Style Sheets">CSS</abbr></li>
  463. </ul>
  464. <p>
  465. SVG est dans la lignée de HTML : spécifié par le <abbr title="World Wide Web Consortium">W3C</abbr>, ouvert, libre, simple d'utilisation. Il interagit avec les différents langages qui composent nos pages web.</p>
  466. <h3>
  467. Outils</h3>
  468. <p>
  469. <img alt="Inkscape" class="right" src="http://www.alsacreations.com/xmedia/doc/medium/inkscape-logo.png"/></p>
  470. <p>
  471. En tant que format vectoriel, SVG est éditable dans un logiciel tel qu'Illustrator ou Inkscape, pour ne citer que les deux plus célèbres protagonistes, ce qui rend triviale la création de formes complexes. Il existe d'autres outils pour manipuler ce format.</p>
  472. <p class="center">
  473. <img alt="Inkscape" src="http://www.alsacreations.com/xmedia/doc/full/svg-inkscape.png"/></p>
  474. <p class="center">
  475. Exemple de dessin dans Inkscape<br/>
  476. (sans écrire une seule ligne de code)</p>
  477. <h3>
  478. Intégrer SVG à sa page web</h3>
  479. <p>
  480. Il y a différentes possibilités plus ou moins pratiques et plus ou moins supportées, afin d'intégrer du SVG dans une page web.</p>
  481. <h4>
  482. La balise <code>&lt;embed&gt;</code></h4>
  483. <p>
  484. Cet élément non standard a été créé pour combler un manque du côté des spécifications du W3C. Employé en des temps obscurs, nous éviterons donc son utilisation.</p>
  485. <h4>
  486. La balise <code>&lt;object&gt;</code></h4>
  487. <p>
  488. Introduite en HTML4 la balise fourre-tout <code>&lt;object&gt;</code> peut également être utilisée pour importer du contenu SVG dans une page web.</p>
  489. <pre class="code">
  490. <code class="html">&lt;object type="image/svg+xml" data="kiwi.svg" width="200" height="100"&gt;
  491. Le navigateur ne peut lire ce kiwi
  492. &lt;/object&gt;</code></pre>
  493. <h4>
  494. La balise <code>&lt;svg&gt;</code></h4>
  495. <p>
  496. HTML5 introduit un nouvel élément afin d'embarquer du contenu SVG dans une page web. L'élément <code>&lt;svg&gt;</code> permet de ne plus ce soucier du <a href="http://fr.wikipedia.org/wiki/Espace_de_noms">namespace</a> et d'intérargir avec les nœuds de SVG directement au sein du document HTML.</p>
  497. <pre class="code">
  498. <code class="css">&lt;svg width="200" height="100"&gt;
  499. ...
  500. &lt;/svg&gt;</code></pre>
  501. <h4>
  502. La balise <code>&lt;img&gt;</code></h4>
  503. <p>
  504. Même s'il est possible d'inclure du SVG dans la balise <code>&lt;img&gt;</code>, c'est à éviter dans la mesure où cette balise n'a pas été faite pour accueillir des éventuels comportements scriptés. À partir du moment où vous utilisez Javascript avec SVG, il vaudra mieux éviter de l'inclure via la balise <code class="html">&lt;img&gt;</code>, pour une utilisation plus basique cette balise sera totalement appropriée. À noter que cette partie de la spécifications est toujours en brouillon.</p>
  505. <pre class="code">
  506. <code class="html">&lt;img src="kiwi.svg" alt="Un kiwi en SVG"&gt;</code></pre>
  507. <h4>
  508. Par CSS</h4>
  509. <p>
  510. Fonctionnant en synergie avec SVG, ont peut également inclure ce format comme ressource pour un background CSS. De plus, quand vous utilisez <code class="css">@font-face</code> vous  êtes également susceptible d'employer des fontes SVG.</p>
  511. <pre class="code">
  512. <code class="css">.kiwi {
  513. background : url("kiwi.svg") no-repeat left left ;
  514. }</code></pre>
  515. <p>
  516. <a class="demo" href="/xmedia/tuto/svg/integrationsvg.html">Voir les exemples</a></p>
  517. <h4>
  518. État des lieux de l'implémentation d'SVG</h4>
  519. <p>
  520. L'incontournable référence "When can I use..." permet de voir un état des lieu exhaustif au sujet de l'<a href="http://caniuse.com/#cats=SVG">implémentation de SVG</a> sur les différents navigateurs.</p>
  521. <table class="pagetable">
  522. <caption>
  523. Support de SVG (versions minimales)</caption>
  524. <thead>
  525. <tr>
  526. <th scope="row">
  527. Navigateurs</th>
  528. <th scope="col">
  529. Versions</th>
  530. <th scope="col">
  531. Support basique</th>
  532. <th scope="col">
  533. Dans &lt;img&gt;</th>
  534. <th scope="col">
  535. CSS background</th>
  536. <th scope="col">
  537. Élément SVG inline</th>
  538. <th scope="col">
  539. Effet SVG</th>
  540. <th scope="col">
  541. SMIL</th>
  542. </tr>
  543. </thead>
  544. <tbody>
  545. <tr>
  546. <td scope="row">
  547. <img alt="Firefox" height="40" src="http://www.alsacreations.com/xmedia/doc/small/Firefox_Transparent.png" width="40"/></td>
  548. <td>
  549. <strong>Firefox</strong></td>
  550. <td>
  551. 3.6</td>
  552. <td>
  553. 4</td>
  554. <td>
  555. 4</td>
  556. <td>
  557. 4</td>
  558. <td>
  559. 3.6</td>
  560. <td>
  561. 8</td>
  562. </tr>
  563. <tr>
  564. <td scope="row">
  565. <img alt="Chrome" height="40" src="http://www.alsacreations.com/xmedia/doc/small/Chrome_Transparent.png" width="40"/></td>
  566. <td>
  567. <strong>Chrome</strong></td>
  568. <td>
  569. 16</td>
  570. <td>
  571. 4</td>
  572. <td>
  573. 5</td>
  574. <td>
  575. 7</td>
  576. <td>
  577. 16 (partiel)</td>
  578. <td>
  579. 16</td>
  580. </tr>
  581. <tr>
  582. <td scope="row">
  583. <img alt="Internet Explorer" height="40" src="http://www.alsacreations.com/xmedia/doc/small/IExplorer_Transparent.png" width="40"/></td>
  584. <td>
  585. <strong>Internet Explorer</strong></td>
  586. <td>
  587. 9</td>
  588. <td>
  589. 9</td>
  590. <td>
  591. 9</td>
  592. <td>
  593. 9</td>
  594. <td>
  595. 9 (partiel)</td>
  596. <td>
  597. /</td>
  598. </tr>
  599. <tr>
  600. <td scope="row">
  601. <img alt="Opera" height="40" src="http://www.alsacreations.com/xmedia/doc/small/Opera_Transparent.png" width="40"/></td>
  602. <td>
  603. <strong>Opera</strong></td>
  604. <td>
  605. 11.6</td>
  606. <td>
  607. 9</td>
  608. <td>
  609. 9.5</td>
  610. <td>
  611. 11.6</td>
  612. <td>
  613. 11.6 (partiel)</td>
  614. <td>
  615. 11.6</td>
  616. </tr>
  617. <tr>
  618. <td scope="row">
  619. <img alt="Safari" height="40" src="http://www.alsacreations.com/xmedia/doc/small/Safari_Transparent.png" width="40"/></td>
  620. <td>
  621. <strong>Safari</strong></td>
  622. <td>
  623. 3.2</td>
  624. <td>
  625. 4</td>
  626. <td>
  627. 5</td>
  628. <td>
  629. 5.1</td>
  630. <td>
  631. 4 (partiel)</td>
  632. <td>
  633. 4 (partiel)</td>
  634. </tr>
  635. </tbody>
  636. </table>
  637. <p class="info">
  638. <a href="http://fr.wikipedia.org/wiki/Synchronized_Multimedia_Integration_Language">SMIL </a>est une spécification du W3C qui <em>décrit le déroulement temporel et spatial des différents composants intégrés</em>, autrement dit les animations</p>
  639. <p>
  640. Comme on peut le voir SVG et son système d'animation est plutôt bien implémenté dans les navigateurs actuels. On regrettera Internet Explorer qui traîne à implémenter la spécification SMIL même sous la version 10. On notera aussi le retard de Chrome au niveau des possibilités plus avancées de SVG telles que les masques, les filtres, les transformations, etc.</p>
  641. <h3>
  642. Un fichier SVG, c'est quoi ?</h3>
  643. <p>
  644. Voici la structure de base d'un fichier type SVG :</p>
  645. <pre class="code">
  646. <code class="html">&lt;?xml version="1.0" encoding="utf-8"?&gt;
  647. &lt;!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 20010904//EN"
  648. "http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd"&gt;
  649. &lt;svg width="300px" height="200px" xml:lang="fr"
  650. xmlns="http://www.w3.org/2000/svg"
  651. xmlns:xlink="http://www.w3.org/1999/xlink"&gt;
  652. &lt;title&gt;La kiwiParty, le web pulpeux&lt;/title&gt;
  653. &lt;desc&gt;Un logo animé en SVG&lt;/desc&gt;
  654. &lt;/svg&gt;
  655. </code></pre>
  656. <p class="remarque">
  657. Si cette syntaxe vous semble familière c'est tout à fait normal : SVG s'appuie sur XML, famille sur laquelle est construite d'autres langages de balisage tels que XHTML.</p>
  658. <p>
  659. Décomposons les différentes parties :</p>
  660. <pre class="code">
  661. <code class="html">&lt;?xml version="1.0" encoding="utf-8"?&gt;</code></pre>
  662. <p>
  663. Tout document XML commence par ce que l'on appelle un prologue XML qui va indiquer la version utilisée ainsi que l'encodage, de préférence UTF-8 (il faut donc veiller à ce que l'éditeur utilise bien cette page de code pour le fichier).</p>
  664. <pre class="code">
  665. <code class="html">&lt;!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 20010904//EN"
  666. "http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd"&gt;</code></pre>
  667. <p>
  668. Vient ensuite le fameux <em>doctype</em> qui va spécifier aux navigateurs qu'ici on <em>parle</em> le SVG.</p>
  669. <pre class="code">
  670. <code class="html">&lt;svg width="400px" height="300px" xml:lang="fr"
  671. xmlns="http://www.w3.org/2000/svg"
  672. xmlns:xlink="http://www.w3.org/1999/xlink"&gt;
  673. &lt;/svg&gt;</code></pre>
  674. <p>
  675. À l'instar de l'élément <code class="html">html</code>, <code class="html">&lt;svg&gt;</code> représente la racine de notre document. C'est elle qui va contenir toutes les descriptions des formes graphiques affichées à l'écran.</p>
  676. <pre class="code">
  677. <code class="html">&lt;title&gt;La kiwiParty, le web pulpeux&lt;/title&gt;
  678. &lt;desc&gt;Un logo animé en SVG&lt;/desc&gt;</code></pre>
  679. <p>
  680. On peut également spécifier <code>&lt;title&gt;</code> et <code>&lt;desc&gt;</code> qui permettront de donner un titre et une description au document. Ces balises sont notamment utiles pour le référencement et certains agents utilisateurs.</p>
  681. <h3>
  682. Les formes</h3>
  683. <p>
  684. SVG propose plusieurs moyens de créer des formes, simples ou plus complexes. Chaque forme et plus généralement chaque élément SVG peut être accompagné d'attributs qui vont en décrire les propriétés.</p>
  685. <h4>
  686. Le rectangle</h4>
  687. <p>
  688. Pour dessiner un rectangle, on utilise la balise <code class="html">&lt;rect&gt;</code> en spécifiant sa longueur et sa largeur avec les attributs <code>width</code> et <code>height</code>. Les attributs <code>x</code> et <code>y</code> indiquent la position (horizontale et verticale) au sein de notre élément <code class="html">svg</code>.</p>
  689. <pre class="code">
  690. <code class="html">&lt;rect x="25px" y="25px" width="150" height="100"/&gt;
  691. &lt;rect x="200px" y="75px" width="150" height="100"/&gt;</code></pre>
  692. <p class="center">
  693. <img alt="SVG Rectangle" src="http://www.alsacreations.com/xmedia/doc/full/svg-rect.png"/></p>
  694. <p>
  695. L'unité utilisée ici est le <code class="css">px</code> (pixel). Il est possible de ne pas la préciser, le <a href="http://dictionnaire.phpmyvisites.net/definition-PARSER-4876.htm">parseur </a>l'aurait compris ainsi par défaut. D'autres unités sont envisageables, principalement les mêmes qu'en CSS. Étant donné qu'aucune couleur n'a été précisée, le rectangle se retrouve noir.</p>
  696. <p>
  697. <a class="demo" href="/xmedia/tuto/svg/rect.html">Exemple</a></p>
  698. <h4>
  699. Le cercle et l’ellipse</h4>
  700. <p>
  701. Pour dessiner un cercle rien de plus simple avec la balise <code class="html">circle</code>. L'attribut <code class="html">r</code> spécifie le rayon du cercle, et les attributs <code>cx</code> et <code>cy</code> les coordonnées du centre.</p>
  702. <pre class="code">
  703. <code class="html">&lt;circle cx="110" cy="110" r="50" /&gt;</code></pre>
  704. <p class="center">
  705. <img alt="SVG Circle" src="http://www.alsacreations.com/xmedia/doc/full/svg-circle.png"/></p>
  706. <p>
  707. <a class="demo" href="/xmedia/tuto/svg/circle.html">Exemple</a></p>
  708. <h4>
  709. Les lignes</h4>
  710. <p>
  711. Pour créer une ligne on utilise l'élément <code class="html">line</code> qui nécessite quatre paramètres obligatoirement.</p>
  712. <ul>
  713. <li>
  714. <code class="html">x1</code> : spécifie la position du premier point sur l'axe des abscisses ;</li>
  715. <li>
  716. <code class="html">x2</code> : spécifie la position du second  point sur l'axe des abscisses ;</li>
  717. <li>
  718. <code class="html">y1</code> : spécifie la position du premier sur l'axe des ordonnées ;</li>
  719. <li>
  720. <code class="html">y2</code> : spécifie la position du second  point sur l'axe des ordonnées ;</li>
  721. </ul>
  722. <pre class="code">
  723. <code class="html">&lt;line x1="50" y1="50" x2="150" y2="150" stroke="black" stroke-width="2" /&gt;
  724. &lt;line x1="100" y1="50" x2="200" y2="150" stroke="red" stroke-width="10" /&gt;
  725. &lt;line x1="150" y1="50" x2="250" y2="150" stroke="blue" stroke-width="5" stroke-dasharray="5,3,2" /&gt;</code></pre>
  726. <p class="center">
  727. <img alt="SVG Ligne" src="http://www.alsacreations.com/xmedia/doc/full/svg-line.png"/></p>
  728. <p>
  729. L'apparence du trait est définie par les attributs de couleur (<code>stroke</code>), de largeur (<code>stroke-width</code>) ou de pointillés (<code>stroke-dasharray</code>).</p>
  730. <p>
  731. Notez que l'écriture avec l'attribut <code>style</code> est équivalente :</p>
  732. <pre class="code">
  733. <code class="html">&lt;line x1="50" y1="50" x2="150" y2="150" style="stroke:black;stroke-width:2px;" /&gt;
  734. &lt;line x1="100" y1="50" x2="200" y2="150" style="stroke:red;stroke-width:10px;" /&gt;
  735. &lt;line x1="150" y1="50" x2="250" y2="150" style="stroke:blue;stroke-width:5px;stroke-dasharray: 5,3,2" /&gt;</code></pre>
  736. <h4>
  737. Fin de ligne</h4>
  738. <p>
  739. Lorsqu'un trait mesure 1 pixel de large, son style de fin n'a que peu d'importance car il ne se visualise pas. En revanche dès qu'il est plus épais, il sera intéressant de pouvoir définir un style grâce à l'attribut <code>stroke-linecap</code> : coupé (<code>butt</code>), carré (<code>square</code>) ou arrondi (<code>round</code>).</p>
  740. <pre class="code">
  741. <code class="html">&lt;line x1="50" y1="50" x2="300" y2="50" stroke="#5a3434" stroke-width="20" <strong>stroke-linecap="butt"</strong> /&gt;
  742. &lt;line x1="50" y1="100" x2="300" y2="100" stroke="#0a989a" stroke-width="20" <strong>stroke-linecap="round"</strong> /&gt;
  743. &lt;line x1="50" y1="150" x2="300" y2="150" stroke="#933c8e" stroke-width="20" <strong>stroke-linecap="square"</strong> /&gt;</code></pre>
  744. <p class="center">
  745. <img alt="SVG Stroke linecap" src="http://www.alsacreations.com/xmedia/doc/full/svg-stroke-linecap.png"/></p>
  746. <p>
  747. <a class="demo" href="/xmedia/tuto/svg/stroke-linecap.html">Exemple</a></p>
  748. <h4>
  749. Les chemins</h4>
  750. <p>
  751. Les éléments précédents sont des formes simples qui ne permettent pas de créer des dessins plus complexes. Heureusement SVG a prévu l'élément <code class="html">path</code> pouvant correspondre à tout type de tracé (chemin). Cet élément n'a qu'un attribut obligatoire : <code class="css">d</code> (comme <em>data</em>).</p>
  752. <pre class="code">
  753. <code class="html">&lt;path d="M 100,180 L 140,0 L 180,180 L 220,0 L 260,180 L 300,0 L 330,180" style="fill:none; stroke:black"/&gt;</code></pre>
  754. <p class="center">
  755. <img alt="" src="http://www.alsacreations.com/xmedia/doc/full/path1.JPG"/></p>
  756. <h5>
  757. Les commandes de l'attribut d</h5>
  758. <ul>
  759. <li>
  760. <code>Moveto</code> : noté <strong>M</strong>, prend comme paramètre les coordonnées du premier point du tracé ;</li>
  761. <li>
  762. <code>Lineto</code> : noté <strong>L</strong>, trace une ligne entre les dernières coordonnées mentionnés ;</li>
  763. <li>
  764. <code>ClosePath</code> : noté <strong>Z</strong>, ferme le tracé ;</li>
  765. <li>
  766. <code>Lineto horizontal</code> : noté <strong>H</strong>, raccourci pour noter des lingne horizontales ;</li>
  767. <li>
  768. <code>Lineto vertical</code> : noté <strong>V</strong>, raccourci pour noter des lignes verticales ;</li>
  769. </ul>
  770. <p>
  771. Afin de simplifier la tâche il est possible de rendre ces coordonnées <strong>relatives</strong>. Pour ce faire, il faudra veiller à indiquer les noms de commande en <strong>minuscules</strong>.</p>
  772. <p>
  773. Sachez que l'on peut faire bien plus avec cet élément. Y compris des formes plus fluides notamment grâce aux arcs elliptiques et aux <a href="http://fr.wikipedia.org/wiki/Courbe_de_B%C3%A9zier">courbes de Bézier</a>, quadratiques et cubiques. La rédaction de telles formes géométriques fait appel à de fortes notions de mathématiques. Si vous avez besoin de formes de ce type, il est plus intéressent de passer par un logiciel de création vectorielle pour ensuite l'enregistrer en SVG. Si vous ouvrez le fichier avec votre éditeur de texte vous pourrez constater qu'un élément <code class="html">path</code> a été généré.</p>
  774. <h3>
  775. Les remplissages</h3>
  776. <p>
  777. À toutes ces formes s'appliquent des couleurs de remplissage ou de contours. Les attributs suivants en définissent l'apparence :</p>
  778. <ul>
  779. <li>
  780. <code>stroke</code> : couleur du contour</li>
  781. <li>
  782. <code>fill</code> : couleur de remplissage</li>
  783. <li>
  784. <code>stroke-opacity</code> : opacité du contour (de 0 à 1)</li>
  785. <li>
  786. <code>fill-opacity</code> : opacité du remplissage (de 9 à 1)</li>
  787. </ul>
  788. <p>
  789. Dans toutes les situations, on peut utiliser des valeurs de couleurs sous forme de noms (<code>blue</code>, <code>red</code>, <code>black</code>) ou de codes couleurs héxadécimaux (<code>#xxxxxx</code>).</p>
  790. <pre class="code">
  791. <code class="html">&lt;circle cx="100" cy="100" r="80" stroke="#4b6c0b" fill="#9dcc41" /&gt;
  792. &lt;circle cx="150" cy="100" r="80" stroke="#ff6000" fill="orange" fill-opacity="0.5" /&gt;
  793. &lt;circle cx="300" cy="100" r="40" stroke="#4b6c0b" stroke-width="20" fill="transparent" stroke-opacity="0.5" /&gt;
  794. &lt;circle cx="340" cy="100" r="40" stroke="#4b6c0b" stroke-width="20" fill="transparent" stroke-opacity="0.5" /&gt;</code></pre>
  795. <p>
  796. Dans le cas présent, les deux premiers cercles disposent par défaut d'un contour de 1 pixel. L'un <em>recouvre </em>l'autre car son opacité de remplissage est de 50% grâce à <code>fill-opacity</code>. Les deux autres cercles se recouvrent également mais avec une opacité sur le contour (beaucoup plus large, sans remplissage).</p>
  797. <p class="center">
  798. <img alt="SVG Stroke fill" src="http://www.alsacreations.com/xmedia/doc/full/svg-stroke-fill.png"/></p>
  799. <p>
  800. <a class="demo" href="/xmedia/tuto/svg/stroke-fill.html">Exemple</a></p>
  801. <h3>
  802. Les balises et attributs de base</h3>
  803. <h4>
  804. Les attributs <code>id</code> et <code>class</code></h4>
  805. <p>
  806. Comme en HTML, il est possible d'identifier un élément et un groupe d'élément de façon unique avec un <code>id</code>, ou de façon groupée avec un attribut <code>class</code>, cela servira notamment lors des événements (début et fin d'une animation), appliquer des masques, des styles CSS, des dégradés, réutiliser des éléments génériques, etc.</p>
  807. <h4>
  808. L'élément <code class="html">g</code></h4>
  809. <p>
  810. Permet de regrouper plusieurs formes dans un seul élément afin de pouvoir les réutiliser ensemble par la suite. L'élément <code class="html">g</code> (<em>group</em>) est souvent accompagné d'un identifiant <code>id</code> pour le désigner de manière unique.</p>
  811. <h4>
  812. Les éléments <code class="html">defs</code> et <code class="html">use</code></h4>
  813. <p>
  814. Dans certaines situations, il sera utile de déclarer (<em>définir</em>) un ensemble de formes ou d'autres informations en tant que modèles. Ceci évite de répliquer plusieurs fois les mêmes tracés et d'aboutir à une lourde redondance du code source. Par défaut, ces formes sont cachées, et regroupées entre les balises <code class="html">&lt;defs&gt;</code> et <code class="html">&lt;/defs&gt;</code>. Grâce à <code class="html">use</code> il est ensuite possible de réutiliser ces ensembles, par exemple en les affichant à des coordonnées différentes.</p>
  815. <pre class="code">
  816. <code class="html">  &lt;defs&gt;
  817.       &lt;g id="tete"&gt;
  818.          &lt;circle cx="40" cy="30" r="40" style="stroke:black; stroke-width: 1px;fill: #F4F4F4;" /&gt;
  819.          &lt;rect width="100" height="75" x="-10" y="-20" style="fill:#F4F4F4"/&gt;
  820.          &lt;circle cx="40" cy="30" r="50" style="stroke:black; stroke-width: 1px;fill: none;" /&gt;
  821.          &lt;circle cx="20" cy="20" r="20" /&gt;
  822.          &lt;circle cx="60" cy="20" r="15" /&gt;
  823.          &lt;circle cx="35" cy="20" r="5" style="fill:white"/&gt;
  824.          &lt;circle cx="50" cy="20" r="4" style="fill:white" /&gt;
  825.      &lt;/g&gt;
  826.  &lt;/defs&gt;
  827.  &lt;use xlink:href="#tete" x="0" y="30" /&gt;
  828.  &lt;use xlink:href="#tete" x="0" y="140" /&gt;
  829.  &lt;use xlink:href="#tete" x="-100" y="80" /&gt;
  830.  &lt;use xlink:href="#tete" x="100" y="80" /&gt;</code></pre>
  831. <p class="center">
  832. <img alt="SVG Defs Use" src="http://www.alsacreations.com/xmedia/doc/full/svg-defs-use.png"/></p>
  833. <p>
  834. <a class="demo" href="/xmedia/tuto/svg/1.html">Exemple</a></p>
  835. <h3>
  836. Styles CSS applicables</h3>
  837. <p>
  838. L'attribut style est applicable aux objets SVG. Il y a trois façons d'intégrer du style, comme en HTML.</p>
  839. <p class="warning">
  840. Attention, cette pratique n'est <a href="https://jwatt.org/svg/authoring/#the-style-attribute">pas toujours recommandée</a>, les créateurs SVG préconisent plutôt de passer par les attributs SVG plutôt que d'embarquer tout le style dans l'attribut du même nom.</p>
  841. <h4>
  842. Le style CSS en ligne</h4>
  843. <p>
  844. Le style en ligne permet de déclarer grâce à l'attribut <code class="html">style</code> d'un élément une série de déclarations de style.</p>
  845. <pre class="code">
  846. <code class="html">&lt;rect x="25px" y="25px" width="200" height="100" <strong>style="fill:pink"</strong> /&gt;</code></pre>
  847. <h4>
  848. Le style CSS interne</h4>
  849. <p>
  850. Avec la balise <code class="html">style </code>nous pouvons, comme en HTML déclarer une feuille de style interne qui devra être nécéssairement enfant direct de l'élement <code class="html">svg</code>. Il faudra veiller également à baliser le contenu grâce à une section <code class="html">CDATA</code>. On précisera également son type MIME.</p>
  851. <p class="remarque">
  852. Rappel : <a href="http://en.wikipedia.org/wiki/CDATA en">CDATA </a>fait partie de la syntaxe XML et permet d'éviter de devoir échapper les caractères spéciaux.</p>
  853. <pre class="code">
  854. <code class="html">&lt;svg&gt;
  855. &lt;title&gt;Le web pulpeux&lt;/title&gt;
  856. &lt;style type="text/css"&gt;
  857. &lt;![CDATA[
  858. #rect {
  859. fill : pink;
  860. }
  861. ]]&gt;
  862. &lt;rect x="25px" y="25px" width="100" height="50" id="rect" /&gt;
  863. &lt;/svg&gt;</code></pre>
  864. <h4>
  865. Le style CSS externe</h4>
  866. <p>
  867. Avec SVG, pas de balise <code class="html">link</code> comme HTML pour faire le lien vers le fichier externe, mais on utilise, ce qu'on appel dans le jargon XML, une <abbr title="processing instruction">PI</abbr>. Tout ce que vous devez savoir c'est qu'elle possède deux attributs obligatoires, <code class="html">href</code> et <code class="html">type</code>.</p>
  868. <pre class="code">
  869. <code class="html">&lt;?xml-stylesheet type="text/css" href="styleSVG.css"?&gt;</code></pre>
  870. <p>
  871. Cette dernière méthode, à l'instar des feuilles de styles CSS est la plus souple. Si vous souhaitez avoir une approche modulaire c'est avec cette méthode qu'il faudra travailler.</p>
  872. <p>
  873. Les exemples suivants feront néanmoins appel aux styles en ligne dans un souci de lisibilité du code proposé.</p>
  874. <p>
  875. Une fois le fichier CSS lié à SVG, il faut faire appel à des propriétés. Celles-ci sont spécifiques et ne sont pas transposables directement depuis ce que l'on connaît déjà du côté de HTML. L'exemple suivant utilise un fond vert avec une bordure noire de 2 pixels.</p>
  876. <pre class="code">
  877. <code class="html">&lt;rect x="25px" y="25px" width="100" height="50" id="rect" /&gt;
  878. </code></pre>
  879. <pre class="code">
  880. <code class="css">#rect {
  881. fill: #B5CC45;
  882. stroke: black;
  883. stroke-width: 2px;
  884. }</code></pre>
  885. <p>
  886. Cet article est une introduction à SVG, si vous souhaitez découvrir les autres propriétés de style utilisables, consultez la <a href="http://www.w3.org/TR/SVG/styling.html">documentation officielle du W3C au sujet des styles SVG</a> ou encore la <a href="http://www.yoyodesign.org/doc/w3c/svg1/styling.html">version française</a>.</p>
  887. <h3>
  888. L'animation SVG</h3>
  889. <p>
  890. SVG propose plusieurs solutions afin de créer des animations :</p>
  891. <ul>
  892. <li>
  893. Les animations des attributs de présentation par CSS via les propriétés <code class="css">transition</code> et <code class="css">animation</code>.</li>
  894. <li>
  895. Les animations des noeuds du DOM via <a href="http://fr.wikipedia.org/wiki/ECMAScript">ECMAScript</a> (<a href="http://fr.wikipedia.org/wiki/Javascript">Javascript</a>)</li>
  896. <li>
  897. Les éléments d'animations basés sur le language <a href="http://fr.wikipedia.org/wiki/SMIL)">SMIL</a></li>
  898. </ul>
  899. <p>
  900. Dans cet article consacré à SVG seront abordées les animations SMIL.</p>
  901. <p>
  902. Développé par le W3C, le langage SMIL permet de changer les données graphiques vectorielles dans le temps. Il représente un jeu de fonctions d'animations XML. Concrètement, ses balises sont placées comme enfants directs de l'élément sur lequel on souhaite agir. Une propriété n'a pas besoin d'être déclarée pour pouvoir être animée.</p>
  903. <h4>
  904. L'élément <code class="html">animate</code></h4>
  905. <p>
  906. Utilisé pour animer un seul attribut ou une seule propriété au cours du temps.</p>
  907. <pre class="code">
  908. <code class="html">&lt;rect width="100" height="50"&gt;
  909.     &lt;animate attributeName="width" attributeType="XML"
  910.     fill="freeze"
  911.     from="0" to="300"
  912.     begin="0s" dur="3s"/&gt;
  913. &lt;/rect&gt;</code></pre>
  914. <p>
  915. <a class="demo" href="/xmedia/tuto/svg/2.html">Voir la démonstration</a></p>
  916. <p>
  917. Un zeste de JavaScript et l'on peut obtenir une magnifique barre de chargement. SI vous êtes vigilants, vous aurez remarqué que <code class="html">rect</code> n'est plus une balise auto-fermante. En effet maintenant elle est devenue une balise ouvrante/fermante pour contenir <code class="html">animate</code>.</p>
  918. <p>
  919. Voici les attributs utilisés :</p>
  920. <ul>
  921. <li>
  922. <code class="html">attributName</code> : spécifie l'attribut ou la propriété CSS à animer ;</li>
  923. <li>
  924. <code class="html">attributType</code> : spécifie le type de nœud à traiter ;</li>
  925. <li>
  926. <code class="html">fill</code> : permet de geler l'animation arrivée à sa fin ;</li>
  927. <li>
  928. <code class="html">from</code> : la valeur de départ de l'animation ;</li>
  929. <li>
  930. <code class="html">to</code> : la valeur finale à atteindre ;</li>
  931. <li>
  932. <code class="html">begin</code> : l'instant de départ de notre animation;</li>
  933. <li>
  934. <code class="html">dur</code> : la durée de notre animation;</li>
  935. </ul>
  936. <p>
  937. On peut également commencer et finir une animation en fonction du début ou de la fin d'une autre animation, pour les faire de succéder. Afin d'obtenir cet effet, il faut renseigner l'animation incriminée par un <code>id</code>, pour ensuite passer cet <code>id</code> comme valeur de la propriété <code class="html">begin</code> de l'animation que l'on souhaite démarrer. On utilise également un pseudo « écouteur d'évènement » pour déclencher l'action.</p>
  938. <p>
  939. Un exemple vaut mieux qu'un long discours :</p>
  940. <pre class="code">
  941. <code class="html">&lt;rect width="100" height="50"&gt;
  942.     &lt;animate attributeName="width" attributeType="XML" id="rect1"
  943.     fill="freeze"
  944.     from="0" to="150"
  945.     begin="0s" dur="1s"/&gt;
  946. &lt;/rect&gt;
  947. &lt;rect y="50" x="150" width="0" height="50" &gt;
  948.     &lt;animate attributeName="width" attributeType="XML" id="rect2"
  949.     fill="freeze"
  950.     from="0" to="150"
  951.     begin="rect1.end" dur="1s"/&gt;
  952. &lt;/rect&gt;
  953. &lt;rect y="100" x="0" width="0" height="50" &gt;
  954.     &lt;animate attributeName="width" attributeType="XML" id="rect3"
  955.     fill="freeze"
  956.     from="0" to="150"
  957.     begin="rect2.end" dur="1s"/&gt;
  958. &lt;/rect&gt;
  959. &lt;rect y="150" x="150" width="0" height="50"&gt;
  960.     &lt;animate attributeName="width" attributeType="XML"
  961.     fill="freeze"
  962.     from="0" to="150"
  963.     begin="rect3.end" dur="1s"/&gt;
  964. &lt;/rect&gt;</code></pre>
  965. <p>
  966. <a class="demo" href="/xmedia/tuto/svg/3.html">Voir la démonstration</a></p>
  967. <h4>
  968. L'élément <code class="html">animateColor</code></h4>
  969. <p>
  970. Comme son nom le suggère, cet élément est dédié à l'animation de la couleur. Fonctionnant de la même façon que <code class="html">animate</code> à cela près que les valeurs de <code>from</code> et <code>to</code> doivent être… des couleurs ! Cependant il semblerait qu'il ne soit pas encore totalement bien interpreté par Firefox.</p>
  971. <pre class="code">
  972. <code class="html">&lt;rect x="15" y="0" width="80" height="200" rx="20" ry="20" style="fill:black;"/&gt;
  973. &lt;circle cx="55" cy="40" r="25" style="stroke:black; stroke-width: 1px;fill: #F4F4F4;"&gt;
  974. &lt;animateColor attributeName="fill" id="rect1"
  975. repeatDur="3"
  976. from="green" to="yellow"
  977. dur="3s"/&gt;
  978. &lt;/circle&gt;
  979. &lt;circle cx="55" cy="100" r="25" style="stroke:black; stroke-width: 1px;fill: #F4F4F4;" &gt;
  980. &lt;animateColor attributeName="fill" id="rect2"
  981. repeatDur="3"
  982. from="yellow" to="orange"
  983. begin="rect1.end" dur="3s"/&gt;
  984. &lt;/circle&gt;
  985. &lt;circle cx="55" cy="160" r="25" style="stroke:black; stroke-width: 1px;fill: #F4F4F4;" &gt;
  986. &lt;animateColor attributeName="fill" id="rect3"
  987. repeatDur="3"
  988. from="orange" to="red"
  989. begin="rect2.end" dur="3s"/&gt;
  990. &lt;/circle&gt;</code></pre>
  991. <p class="center">
  992. <img alt="" src="http://www.alsacreations.com/xmedia/doc/full/demo.JPG"/></p>
  993. <p>
  994. <a class="demo" href="/xmedia/tuto/svg/4.html">Voir la démonstration</a></p>
  995. <p>
  996. Il faut ajouter à cela deux nouveaux attributs :</p>
  997. <ul>
  998. <li>
  999. <code class="html">repeatCount</code> : Spécifie le nombre de répétitions de l'action, prend comme paramètre soit un entier soit le mot clé <em>indefinite </em>;</li>
  1000. <li>
  1001. <code class="html">repeatDur</code>: Spécifie la durée durant laquelle se répète l'action, prend comme paramètre soit un entier soit le mot clé <em>indefinite </em>;</li>
  1002. </ul>
  1003. <h4>
  1004. L'élément <code class="html">set</code></h4>
  1005. <p>
  1006. Cet élément permet de fixer une valeur pendant une certaine durée de temps. Dans cet exemple le rectangle rose est affiché pendant 3 secondes. L'attribut CSS <code class="html">visibility</code> est modifié pendant ce laps de temps, ensuite il récupère sa valeur initiale déclarée dans l'élément <code class="html">g</code>.</p>
  1007. <pre class="code">
  1008. <code class="html">&lt;g style="visibility: hidden"&gt;
  1009. &lt;rect x="25px" y="25px" width="200" height="100" style="fill :pink" /&gt;
  1010. &lt;set attributeName="visibility" attributeType="CSS"
  1011. to="visible"
  1012. begin="0" dur="3s"/&gt;
  1013. &lt;/g&gt;</code></pre>
  1014. <h4>
  1015. L'élément <code class="html">animateTransform</code></h4>
  1016. <p>
  1017. Avant de vous parler de l'animation des transformations, il faut une brève introduction sur le concept de transformations en SVG. Il y a cinq valeurs possibles de transformations pour l'attribut <code class="html">transform</code> d'un élément SVG :</p>
  1018. <ul>
  1019. <li>
  1020. La translation (<code class="html">translate</code>);</li>
  1021. <li>
  1022. La rotation (<code class="html">rotate</code>);</li>
  1023. <li>
  1024. Le mise à l'échelle (<code class="html">scale</code>);</li>
  1025. <li>
  1026. L'inclinaison (<code class="html">skewX</code>, <code class="html">skewY</code>);</li>
  1027. </ul>
  1028. <p>
  1029. Ces transformations telles quelles ne sont pas extraordinairement utiles. Mais les transformations peuvent être animées grâce à l'élément <code class="html">animateTransform</code> et là cela devient utile ! Pour la mise en œuvre, c'est similaire aux exemples précédents.</p>
  1030. <pre class="code">
  1031. <code class="html">&lt;rect width="200" height="100" style="fill:pink" &gt;
  1032.     &lt;animateTransform attributeName="transform" attributeType="XML" type="translate"
  1033.     from="-0,0" to="100,0"
  1034.     begin="0s" dur="2s"
  1035.     repeatCount="1"
  1036.     fill="freeze"
  1037.     /&gt;
  1038. &lt;/rect&gt;</code></pre>
  1039. <h4>
  1040. L'élément <code class="html">animatemotion</code></h4>
  1041. <p>
  1042. L'élément <code>animateMotion</code> permet de faire défiler un objet sur un <code class="html">path</code>. Il y a deux façons de faire. La première consiste à utiliser un attribut <code class="html">path<span> </span></code>dans l'élément <code class="html">animateMotion<span> </span></code>dans lequel on renseignera les coordonées du <code class="html">path</code>. La deuxieme à utiliser la balise <code class="html">mpath</code> comme enfant direct d'<code class="html">animateMotion</code> avec l'attribut <code>xlink:href</code> qui sera lié à l'<code>id</code> d'un <code class="html">path</code> existant.<code class="html"> </code></p>
  1043. <pre class="code">
  1044. <code class="html">&lt;path id="chemin" d="M 20,20 h 30 v 30 h 30 v 30 h 30 v 30 h 30 v 30 h 30 v 30 h 30 v 30 h 30 v 30" style="fill:none"/&gt;
  1045. &lt;g&gt;
  1046. &lt;circle r="10" /&gt;
  1047. &lt;animateMotion begin="0s" dur="10s" repeatCount="indefinite"&gt;
  1048. &lt;mpath xlink:href="#chemin"/&gt;
  1049. &lt;/animateMotion&gt;
  1050. &lt;/g&gt;</code></pre>
  1051. <h4>
  1052. Aller plus loin avec le DOM</h4>
  1053. <p>
  1054. SVG est un langage de dessin vectoriel qui offre quelque possibilités d'animation cependant il lui manque de l’interactivité. Le DOM de SVG est conforme aux aspect de la spécifications DOM2. Chaque paramétrage d'attribut et de style est accessible au moyen de JavaScript. On peut donc obtenir toute sorte d'animation et avoir un contrôle très précis sur celles-ci. Afin de s'y adresser on fait souvent appel à des frameworks complets.</p>
  1055. <h3>
  1056. Et pour IE ?</h3>
  1057. <p>
  1058. Malheureusement, SVG n'est pas directement utilisable sur IE8 et inférieurs. Heureusement des personnes bien intentionnées on réalisé des librairies pour combler ce manque. C'est notamment le cas du célèbre <a href="http://raphaeljs.com/">RaphaëlJs</a> qui rend pratiquable SVG sur IE6 et supérieur via JavaScript et l'utilisation de VML. D'autres librairies existent pour les navigateurs n'interprétant pas SMIL (ce qui est de plus en plus rare) notamment <a href="http://leunen.me/fakesmile/">FakeSmile.js</a>.</p>
  1059. <h3>
  1060. Aller plus loin</h3>
  1061. <h4>
  1062. Sources</h4>
  1063. <h4>
  1064. Polyfills (alternatives)</h4>
  1065. <ul>
  1066. <li>
  1067. <a href="http://raphaeljs.com/">RaphaëlJS</a> : librairie Javascript pour tracer du SVG sur tous les navigateurs et du VML sur IE&lt;9</li>
  1068. <li>
  1069. <a href="http://code.google.com/p/svgweb/">SVGweb</a> : librairie offrant un repli vers Flash si nécessaire (beta)</li>
  1070. <li>
  1071. <a href="http://leunen.me/fakesmile/">Fakesmile</a> : produit des animations en JavaScript pour les navigateurs ne reconnaissant pas SMIL</li>
  1072. </ul>
  1073. <p>
  1074. <em>Tutoriel complété par Dew</em></p></div>
  1075. </article>
  1076. </section>
  1077. <nav id="jumpto">
  1078. <p>
  1079. <a href="/david/blog/">Accueil du blog</a> |
  1080. <a href="http://www.alsacreations.com/tuto/lire/1421-svg-initiation-syntaxe-outils.html">Source originale</a> |
  1081. <a href="/david/stream/2019/">Accueil du flux</a>
  1082. </p>
  1083. </nav>
  1084. <footer>
  1085. <div>
  1086. <img src="/static/david/david-larlet-avatar.jpg" loading="lazy" class="avatar" width="200" height="200">
  1087. <p>
  1088. Bonjour/Hi!
  1089. 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>
  1090. 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>).
  1091. </p>
  1092. <p>
  1093. 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>.
  1094. </p>
  1095. <p>
  1096. Voici quelques articles choisis :
  1097. <a href="/david/blog/2019/faire-equipe/" title="Accéder à l’article complet">Faire équipe</a>,
  1098. <a href="/david/blog/2018/bivouac-automnal/" title="Accéder à l’article complet">Bivouac automnal</a>,
  1099. <a href="/david/blog/2018/commodite-effondrement/" title="Accéder à l’article complet">Commodité et effondrement</a>,
  1100. <a href="/david/blog/2017/donnees-communs/" title="Accéder à l’article complet">Des données aux communs</a>,
  1101. <a href="/david/blog/2016/accompagner-enfant/" title="Accéder à l’article complet">Accompagner un enfant</a>,
  1102. <a href="/david/blog/2016/senior-developer/" title="Accéder à l’article complet">Senior developer</a>,
  1103. <a href="/david/blog/2016/illusion-sociale/" title="Accéder à l’article complet">L’illusion sociale</a>,
  1104. <a href="/david/blog/2016/instantane-scopyleft/" title="Accéder à l’article complet">Instantané Scopyleft</a>,
  1105. <a href="/david/blog/2016/enseigner-web/" title="Accéder à l’article complet">Enseigner le Web</a>,
  1106. <a href="/david/blog/2016/simplicite-defaut/" title="Accéder à l’article complet">Simplicité par défaut</a>,
  1107. <a href="/david/blog/2016/minimalisme-esthetique/" title="Accéder à l’article complet">Minimalisme et esthétique</a>,
  1108. <a href="/david/blog/2014/un-web-omni-present/" title="Accéder à l’article complet">Un web omni-présent</a>,
  1109. <a href="/david/blog/2014/manifeste-developpeur/" title="Accéder à l’article complet">Manifeste de développeur</a>,
  1110. <a href="/david/blog/2013/confort-convivialite/" title="Accéder à l’article complet">Confort et convivialité</a>,
  1111. <a href="/david/blog/2013/testament-numerique/" title="Accéder à l’article complet">Testament numérique</a>,
  1112. et <a href="/david/blog/" title="Accéder aux archives">bien d’autres…</a>
  1113. </p>
  1114. <p>
  1115. 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>.
  1116. </p>
  1117. <p>
  1118. Je ne traque pas ta navigation mais mon
  1119. <abbr title="Alwaysdata, 62 rue Tiquetonne 75002 Paris, +33.184162340">hébergeur</abbr>
  1120. conserve des logs d’accès.
  1121. </p>
  1122. </div>
  1123. </footer>
  1124. <script type="text/javascript">
  1125. ;(_ => {
  1126. const jumper = document.getElementById('jumper')
  1127. jumper.addEventListener('click', e => {
  1128. e.preventDefault()
  1129. const anchor = e.target.getAttribute('href')
  1130. const targetEl = document.getElementById(anchor.substring(1))
  1131. targetEl.scrollIntoView({behavior: 'smooth'})
  1132. })
  1133. })()
  1134. </script>