diff --git a/files/fr/_redirects.txt b/files/fr/_redirects.txt index 0af28c473e2d9e..ebf01aa8ee2250 100644 --- a/files/fr/_redirects.txt +++ b/files/fr/_redirects.txt @@ -1433,7 +1433,7 @@ /fr/docs/Glossaire/Hyperlien /fr/docs/Glossary/Hyperlink /fr/docs/Glossaire/Hypertexte /fr/docs/Glossary/Hypertext /fr/docs/Glossaire/Héritage /fr/docs/Glossary/Inheritance -/fr/docs/Glossaire/I18N /fr/docs/Glossary/I18N +/fr/docs/Glossaire/I18N /fr/docs/Glossary/Internationalization /fr/docs/Glossaire/IANA /fr/docs/Glossary/IANA /fr/docs/Glossaire/ICANN /fr/docs/Glossary/ICANN /fr/docs/Glossaire/ICE /fr/docs/Glossary/ICE @@ -1459,7 +1459,7 @@ /fr/docs/Glossaire/Input_method_editor /fr/docs/Glossary/Input_method_editor /fr/docs/Glossaire/Instance /fr/docs/Glossary/Instance /fr/docs/Glossaire/Intergiciel /fr/docs/Glossary/Middleware -/fr/docs/Glossaire/Internationalisation_et_localisation /fr/docs/Glossary/Internationalization_and_localization +/fr/docs/Glossaire/Internationalisation_et_localisation /fr/docs/Glossary/Internationalization /fr/docs/Glossaire/Internet /fr/docs/Glossary/Internet /fr/docs/Glossaire/JSON /fr/docs/Glossary/JSON /fr/docs/Glossaire/Jank /fr/docs/Glossary/Jank @@ -1730,7 +1730,9 @@ /fr/docs/Glossary/Descriptor_(CSS) /fr/docs/Glossary/CSS_Descriptor /fr/docs/Glossary/Empty_element /fr/docs/Glossary/Void_element /fr/docs/Glossary/Grid_Rows /fr/docs/Glossary/Grid_Row +/fr/docs/Glossary/I18N /fr/docs/Glossary/Internationalization /fr/docs/Glossary/Index /fr/docs/Glossary +/fr/docs/Glossary/Internationalization_and_localization /fr/docs/Glossary/Internationalization /fr/docs/Glossary/Modern_web_apps /fr/docs/Glossary/Progressive_web_apps /fr/docs/Glossary/Node/réseau /fr/docs/Glossary/Node/networking /fr/docs/Glossary/Origine /fr/docs/Glossary/Origin @@ -3580,7 +3582,7 @@ /fr/docs/Tutoriel_canvas/Ajout_de_styles_et_de_couleurs /fr/docs/Web/API/Canvas_API/Tutorial/Applying_styles_and_colors /fr/docs/Tutoriel_canvas/Animations_basiques /fr/docs/Web/API/Canvas_API/Tutorial/Basic_animations /fr/docs/Tutoriel_canvas/Composition /fr/docs/Web/API/Canvas_API/Tutorial/Compositing -/fr/docs/Tutoriel_canvas/Composition/Example /fr/docs/Web/API/Canvas_API/Tutorial/Compositing/Example +/fr/docs/Tutoriel_canvas/Composition/Example /fr/docs/Web/API/CanvasRenderingContext2D/globalCompositeOperation /fr/docs/Tutoriel_canvas/Formes_géométriques /fr/docs/Web/API/Canvas_API/Tutorial/Drawing_shapes /fr/docs/Tutoriel_canvas/Optimizing_canvas /fr/docs/Web/API/Canvas_API/Tutorial/Optimizing_canvas /fr/docs/Tutoriel_canvas/Pixel_manipulation_with_canvas /fr/docs/Web/API/Canvas_API/Tutorial/Pixel_manipulation_with_canvas @@ -3631,12 +3633,13 @@ /fr/docs/Web/API/ByteString /fr/docs/Web/JavaScript/Reference/Global_Objects/String /fr/docs/Web/API/CSSMatrix /fr/docs/Web/API/DOMMatrix /fr/docs/Web/API/Canvas_API/Drawing_graphics_with_canvas /fr/docs/Web/API/Canvas_API/Tutorial +/fr/docs/Web/API/Canvas_API/Tutorial/Compositing/Example /fr/docs/Web/API/CanvasRenderingContext2D/globalCompositeOperation /fr/docs/Web/API/Canvas_API/Tutoriel_canvas /fr/docs/Web/API/Canvas_API/Tutorial /fr/docs/Web/API/Canvas_API/Tutoriel_canvas/Advanced_animations /fr/docs/Web/API/Canvas_API/Tutorial/Advanced_animations /fr/docs/Web/API/Canvas_API/Tutoriel_canvas/Ajout_de_styles_et_de_couleurs /fr/docs/Web/API/Canvas_API/Tutorial/Applying_styles_and_colors /fr/docs/Web/API/Canvas_API/Tutoriel_canvas/Animations_basiques /fr/docs/Web/API/Canvas_API/Tutorial/Basic_animations /fr/docs/Web/API/Canvas_API/Tutoriel_canvas/Composition /fr/docs/Web/API/Canvas_API/Tutorial/Compositing -/fr/docs/Web/API/Canvas_API/Tutoriel_canvas/Composition/Example /fr/docs/Web/API/Canvas_API/Tutorial/Compositing/Example +/fr/docs/Web/API/Canvas_API/Tutoriel_canvas/Composition/Example /fr/docs/Web/API/CanvasRenderingContext2D/globalCompositeOperation /fr/docs/Web/API/Canvas_API/Tutoriel_canvas/Dessin_de_texte_avec_canvas /fr/docs/Web/API/Canvas_API/Tutorial/Drawing_text /fr/docs/Web/API/Canvas_API/Tutoriel_canvas/Formes_géométriques /fr/docs/Web/API/Canvas_API/Tutorial/Drawing_shapes /fr/docs/Web/API/Canvas_API/Tutoriel_canvas/Optimizing_canvas /fr/docs/Web/API/Canvas_API/Tutorial/Optimizing_canvas @@ -6369,6 +6372,7 @@ /fr/docs/conflicting/Glossary/DOM /fr/docs/Glossary/DOM /fr/docs/conflicting/Glossary/Doctype /fr/docs/Glossary/Doctype /fr/docs/conflicting/Glossary/Firefox_OS /fr/docs/Glossary/Firefox_OS +/fr/docs/conflicting/Glossary/Internationalization /fr/docs/Glossary/Internationalization /fr/docs/conflicting/Glossary/Object_reference /fr/docs/Glossary/Object_reference /fr/docs/conflicting/Glossary/TCP /fr/docs/Glossary/TCP /fr/docs/conflicting/Learn /fr/docs/Learn @@ -6442,6 +6446,7 @@ /fr/docs/conflicting/Tools/Responsive_Design_Mode https://firefox-source-docs.mozilla.org/devtools-user/responsive_design_mode/index.html /fr/docs/conflicting/Web/API /fr/docs/Web/API /fr/docs/conflicting/Web/API/Blob /fr/docs/Web/API/Blob +/fr/docs/conflicting/Web/API/CanvasRenderingContext2D/globalCompositeOperation /fr/docs/Web/API/CanvasRenderingContext2D/globalCompositeOperation /fr/docs/conflicting/Web/API/Canvas_API/Tutorial /fr/docs/Web/API/Canvas_API/Tutorial /fr/docs/conflicting/Web/API/DOMMatrix /fr/docs/Web/API/DOMMatrix /fr/docs/conflicting/Web/API/Document /fr/docs/Web/API/Document diff --git a/files/fr/_wikihistory.json b/files/fr/_wikihistory.json index b5657c3ea36c33..86b344d7cd8ce0 100644 --- a/files/fr/_wikihistory.json +++ b/files/fr/_wikihistory.json @@ -1018,10 +1018,6 @@ "modified": "2019-03-23T22:42:03.435Z", "contributors": ["loella16", "Porkepix", "xdelatour"] }, - "Glossary/I18N": { - "modified": "2019-03-23T22:41:26.912Z", - "contributors": ["Goofy", "xdelatour"] - }, "Glossary/IANA": { "modified": "2019-03-23T22:42:02.685Z", "contributors": ["loella16", "xdelatour"] @@ -1118,9 +1114,9 @@ "modified": "2019-03-23T22:41:11.990Z", "contributors": ["xdelatour"] }, - "Glossary/Internationalization_and_localization": { - "modified": "2020-10-09T08:51:46.428Z", - "contributors": ["Voulto"] + "Glossary/Internationalization": { + "modified": "2019-03-23T22:41:26.912Z", + "contributors": ["Goofy", "xdelatour"] }, "Glossary/Internet": { "modified": "2019-03-23T22:53:44.936Z", @@ -7359,10 +7355,6 @@ "modified": "2020-11-13T03:38:19.786Z", "contributors": ["SphinxKnight", "a-mt", "Syberam"] }, - "Web/API/Canvas_API/Tutorial/Compositing/Example": { - "modified": "2020-11-13T03:38:18.691Z", - "contributors": ["SphinxKnight", "a-mt"] - }, "Web/API/Canvas_API/Tutorial/Drawing_shapes": { "modified": "2020-11-13T03:38:18.692Z", "contributors": [ diff --git a/files/fr/glossary/i18n/index.md b/files/fr/glossary/i18n/index.md deleted file mode 100644 index 65a02c16ae8c46..00000000000000 --- a/files/fr/glossary/i18n/index.md +++ /dev/null @@ -1,33 +0,0 @@ ---- -title: I18N -slug: Glossary/I18N ---- - -{{GlossarySidebar}} - -i18n (issu de "internationalisation", un mot de 20 lettres) est l'ensemble des bonnes pratiques pour permettre à des produits ou des services d'être lisiblement adaptés à toute culture visée. - -> L'**internationalisation** est la conception et le développement d'un produit, d'une application ou d'un contenu de document qui **permet** une localisation facile pour les publics ciblés de culture, région et langue différentes. (Définition du {{Glossary("W3C")}}) - -Parmi d'autres choses, i18n nécessite le support de plusieurs… - -- jeux de caractères (en général via [Unicode](http://searchcio-midmarket.techtarget.com/definition/Unicode)) -- unités de mesure (monnaie, °C/°F, km/miles, etc.) -- formats de dates et heures -- dispositions de clavier -- directions de texte - -## Pour en savoir plus - -### Culture générale - -- [Internationalisation]() sur Wikipédia - -### Référence technique - -- [i18n sur W3C](http://www.w3.org/International/questions/qa-i18n.en#Internationalization) -- [i18n sur gala-global.org](http://www.gala-global.org/what-internationalization) - -### Apprendre sur ce sujet - -- [Ressources i18n sur i18nguy.com](http://www.i18nguy.com/) diff --git a/files/fr/glossary/internationalization/index.md b/files/fr/glossary/internationalization/index.md new file mode 100644 index 00000000000000..ec8eca51e33235 --- /dev/null +++ b/files/fr/glossary/internationalization/index.md @@ -0,0 +1,27 @@ +--- +title: Internationalisation +slug: Glossary/Internationalization +l10n: + sourceCommit: 050c1825df97d836d7b91c0719386dcb5b5dded2 +--- + +{{GlossarySidebar}} + +L'**internationalisation** (aussi abrégée en "i18n") est l'ensemble des bonnes pratiques permettant à des produits ou des services d'être adaptés pour différents publics, d'une langue, d'une culture ou d'une région différente. + +La [localisation](/fr/docs/Glossary/Localization) est le processus complémentaire pour adapter un système à un public donné. + +L'internationalisation permet entre autres l'adaptation des différences relatives aux : + +- Systèmes d'écriture +- Unités de mesure (monnaie, °C/°F, km/miles, etc.) +- Formats de dates et heures +- Dispositions de clavier + +Le travail du [consortium Unicode](https://home.unicode.org/) fait partie intégrante de l'internationalisation. Unicode prend en charge les variations entre les systèmes d'écriture du monde entier, et aussi les variations culturelles notamment liées aux devises et formats des dates et heures. + +## Voir aussi + +- [La localisation sur le glossaire MDN](/fr/docs/Glossary/Localization) +- [Le site du consortium Unicode](https://home.unicode.org/) +- [L'API JavaScript pour l'internationalisation](/fr/docs/Web/JavaScript/Reference/Global_Objects/Intl) diff --git a/files/fr/glossary/internationalization_and_localization/index.md b/files/fr/glossary/internationalization_and_localization/index.md deleted file mode 100644 index 8d76b06b60f3e2..00000000000000 --- a/files/fr/glossary/internationalization_and_localization/index.md +++ /dev/null @@ -1,16 +0,0 @@ ---- -title: Internationalisation -slug: Glossary/Internationalization_and_localization ---- - -{{GlossarySidebar}} - -**L'internationalisation**, souvent abrégée en "[i18n](/fr/docs/Glossary/I18N)", est l'adaptation d'un site web ou d'une application web à différentes langues, différences régionales et exigences techniques pour différentes régions et pays. L'internationalisation est le processus d'architecture de votre application web afin qu'elle puisse être rapidement et facilement adaptée à diverses langues et régions sans trop d'efforts d'ingénierie lorsque de nouvelles langues et régions sont prises en charge. Aussi pour qu'un utilisateur puisse parcourir les fonctionnalités pour traduire ou localiser l'application pour accéder à tout le contenu sans casser la mise en page. - -L'internationalisation inclut la prise en charge de plusieurs jeux de caractères (généralement via [Unicode](http://searchcio-midmarket.techtarget.com/definition/Unicode)), des unités de mesure ([devise](/fr/docs/Web/API/PaymentCurrencyAmount), °C/°F, km/miles, etc.), [formats de date et d'heure](/fr/docs/Mozilla/Projects/NSPR/Reference/Date_and_Time), dispositions du clavier, et directions du texte. - -## Voir aussi - -- [Extension d'internationalisation](/fr/docs/Mozilla/Add-ons/WebExtensions/Internationalization) -- [API d'internationalisation](/fr/docs/Web/JavaScript/Reference/Global_Objects/Intl) -- [Disposition Flexbox](/fr/docs/Learn/CSS/CSS_layout/Flexbox) et [Grid](/fr/docs/Web/CSS/CSS_Grid_Layout/Basic_Concepts_of_Grid_Layout) diff --git a/files/fr/web/api/canvas_api/tutorial/compositing/example/index.md b/files/fr/web/api/canvas_api/tutorial/compositing/example/index.md deleted file mode 100644 index 6a4a5448d1e91f..00000000000000 --- a/files/fr/web/api/canvas_api/tutorial/compositing/example/index.md +++ /dev/null @@ -1,320 +0,0 @@ ---- -title: Exemple de composition -slug: Web/API/Canvas_API/Tutorial/Compositing/Example -l10n: - sourceCommit: 3c67eed7b0d2c91198ec95bcc9b1a570f6c0f585 ---- - -{{DefaultAPISidebar("Canvas API")}} - -Cet exemple illustre un certain nombre d'[opérations de composition](/fr/docs/Web/API/CanvasRenderingContext2D/globalCompositeOperation). Voici le résultat : - -{{EmbedLiveSample("Exemple_de_composition", "100%", 7250)}} - -## Exemple de composition - -Ce code configure les valeurs globales utilisées par le reste du programme. - -```js -const canvas1 = document.createElement("canvas"); -const canvas2 = document.createElement("canvas"); -const gco = [ - "source-over", - "source-in", - "source-out", - "source-atop", - "destination-over", - "destination-in", - "destination-out", - "destination-atop", - "lighter", - "copy", - "xor", - "multiply", - "screen", - "overlay", - "darken", - "lighten", - "color-dodge", - "color-burn", - "hard-light", - "soft-light", - "difference", - "exclusion", - "hue", - "saturation", - "color", - "luminosity", -].reverse(); -const gcoText = [ - "La configuration par défaut, les nouvelles formes sont dessinées au-dessus du contenu existant sur le canevas.", - "La nouvelle forme est dessinée aux endroits où elle chevauche le contenu du canevas. Tout le reste est rendu transparent.", - "La nouvelle forme est dessinée là où elle ne chevauche pas le contenu existant sur le canevas.", - "La nouvelle forme est uniquement dessinée où elle chevauche le contenu existant du canevas.", - "Les nouvelles formes sont dessinées derrière le contenu existant du canevas.", - "Le contenu existant du canevas est conservé là où il chevauche la nouvelle forme. Tout le reste est rendu transparent.", - "Le contenu existant est conservé où il ne chevauche pas la nouvelle forme.", - "Le canevas existant est uniquement conservé où il chevauche la nouvelle forme. Cette dernière est dessinée derrière le contenu du canevas.", - "Là où les formes se chevauchent, la couleur est déterminée en additionnant les valeurs des couleurs.", - "Seule la nouvelle forme est affichée.", - "Les formes sont rendues transparentes où elles se chevauchent et dessinées normalement par ailleurs.", - "Les pixels de la couche supérieure sont multipliés par les pixels correspondants de la couche inférieure. On obtient alors une image plus sombre.", - "Les pixels sont inversés, multipliés, puis inversés à nouveau. On obtient alors une image plus claire (contrairement à multiply", - "Une combinaison de multiply et de screen. Les parties sombres de la couche de base deviennent plus sombres, et les parties plus claires deviennent plus claires.", - "Ce sont pixels les plus sombres entre les deux couches qui sont retenus.", - "Ce sont pixels les plus clairs entre les deux couches qui sont retenus.", - "Divise la couche inférieure par l'inverse de la couche supérieure.", - "Divise la couche inférieure par la couche supérieure puis inverse le résultat.", - "Une combinaison de multiply et de screen, comme overlay, mais où les couches supérieure et inférieure sont échangées.", - "Une version plus douce de hard-light. Le blanc pur ou le noir pur ne donne pas un noir ou un blanc pur.", - "La couche inférieure est soustraite de la couche supérieure, ou dans l'autre sens, afin de toujours obtenir une valeur positive.", - "Fonctionne comme difference, mais avec un contraste moindre.", - "Conserve la luminance et la chrominance de la couche inférieure, mais adopte la teinte de la couche supérieure.", - "Conserve la luminance et la teinte de la couche inférieure, mais adopte la chrominance de la couche supérieure.", - "Conserve la luminance de la couche inférieure, mais adopte la teinte et la chrominance de la couche supérieure.", - "Conserve la teinte et la chrominance de la couche inférieure, mais adopte la luminance de la couche supérieure.", -].reverse(); -const width = 320; -const height = 340; -``` - -### Programme principal - -Quand la page se charge, le code suivant s'exécute pour configurer et exécuter l'exemple : - -```js -window.onload = () => { - // lum en sRGB - const lum = { - r: 0.33, - g: 0.33, - b: 0.33, - }; - // redimensionne le canevas - canvas1.width = width; - canvas1.height = height; - canvas2.width = width; - canvas2.height = height; - lightMix(); - colorSphere(); - runComposite(); - return; -}; -``` - -Dans le code suivant, `runComposite()` gère la majeure partie du travail, en s'appuyant sur un certain nombre de fonctions utilitaires pour réaliser les parties difficiles. - -```js -function createCanvas() { - const canvas = document.createElement("canvas"); - canvas.style.background = `url(${op_8x8.data})`; - canvas.style.border = "1px solid #000"; - canvas.style.margin = "5px"; - canvas.width = width / 2; - canvas.height = height / 2; - return canvas; -} - -function runComposite() { - const dl = document.createElement("dl"); - document.body.appendChild(dl); - while (gco.length) { - const pop = gco.pop(); - const dt = document.createElement("dt"); - dt.textContent = pop; - dl.appendChild(dt); - const dd = document.createElement("dd"); - const p = document.createElement("p"); - p.textContent = gcoText.pop(); - dd.appendChild(p); - - const canvasToDrawOn = createCanvas(); - const canvasToDrawFrom = createCanvas(); - const canvasToDrawResult = createCanvas(); - - let ctx = canvasToDrawResult.getContext("2d"); - ctx.clearRect(0, 0, width, height); - ctx.save(); - ctx.drawImage(canvas1, 0, 0, width / 2, height / 2); - ctx.globalCompositeOperation = pop; - ctx.drawImage(canvas2, 0, 0, width / 2, height / 2); - ctx.globalCompositeOperation = "source-over"; - ctx.fillStyle = "rgba(0,0,0,0.8)"; - ctx.fillRect(0, height / 2 - 20, width / 2, 20); - ctx.fillStyle = "#FFF"; - ctx.font = "14px arial"; - ctx.fillText(pop, 5, height / 2 - 5); - ctx.restore(); - - ctx = canvasToDrawOn.getContext("2d"); - ctx.clearRect(0, 0, width, height); - ctx.save(); - ctx.drawImage(canvas1, 0, 0, width / 2, height / 2); - ctx.fillStyle = "rgba(0,0,0,0.8)"; - ctx.fillRect(0, height / 2 - 20, width / 2, 20); - ctx.fillStyle = "#FFF"; - ctx.font = "14px arial"; - ctx.fillText("contenu existant", 5, height / 2 - 5); - ctx.restore(); - - ctx = canvasToDrawFrom.getContext("2d"); - ctx.clearRect(0, 0, width, height); - ctx.save(); - ctx.drawImage(canvas2, 0, 0, width / 2, height / 2); - ctx.fillStyle = "rgba(0,0,0,0.8)"; - ctx.fillRect(0, height / 2 - 20, width / 2, 20); - ctx.fillStyle = "#FFF"; - ctx.font = "14px arial"; - ctx.fillText("nouveau contenu", 5, height / 2 - 5); - ctx.restore(); - - dd.appendChild(canvasToDrawOn); - dd.appendChild(canvasToDrawFrom); - dd.appendChild(canvasToDrawResult); - - dl.appendChild(dd); - } -} -``` - -### Fonctions utilitaires - -Notre programme repose sur un certain nombre de fonctions utilitaires. - -```js -const lightMix = () => { - const ctx = canvas2.getContext("2d"); - ctx.save(); - ctx.globalCompositeOperation = "lighter"; - ctx.beginPath(); - ctx.fillStyle = "rgba(255,0,0,1)"; - ctx.arc(100, 200, 100, Math.PI * 2, 0, false); - ctx.fill(); - ctx.beginPath(); - ctx.fillStyle = "rgba(0,0,255,1)"; - ctx.arc(220, 200, 100, Math.PI * 2, 0, false); - ctx.fill(); - ctx.beginPath(); - ctx.fillStyle = "rgba(0,255,0,1)"; - ctx.arc(160, 100, 100, Math.PI * 2, 0, false); - ctx.fill(); - ctx.restore(); - ctx.beginPath(); - ctx.fillStyle = "#f00"; - ctx.fillRect(0, 0, 30, 30); - ctx.fill(); -}; -``` - -```js -const colorSphere = (element) => { - const ctx = canvas1.getContext("2d"); - const width = 360; - const halfWidth = width / 2; - const rotate = (1 / 360) * Math.PI * 2; // par degré - const offset = 0; // décalage de la barre de défilement - const oleft = -20; - const otop = -20; - for (let n = 0; n <= 359; n++) { - const gradient = ctx.createLinearGradient( - oleft + halfWidth, - otop, - oleft + halfWidth, - otop + halfWidth, - ); - const color = Color.HSV_RGB({ H: (n + 300) % 360, S: 100, V: 100 }); - gradient.addColorStop(0, "rgba(0,0,0,0)"); - gradient.addColorStop(0.7, `rgba(${color.R}, ${color.G}, ${color.B}, 1)`); - gradient.addColorStop(1, "rgba(255,255,255,1)"); - ctx.beginPath(); - ctx.moveTo(oleft + halfWidth, otop); - ctx.lineTo(oleft + halfWidth, otop + halfWidth); - ctx.lineTo(oleft + halfWidth + 6, otop); - ctx.fillStyle = gradient; - ctx.fill(); - ctx.translate(oleft + halfWidth, otop + halfWidth); - ctx.rotate(rotate); - ctx.translate(-(oleft + halfWidth), -(otop + halfWidth)); - } - ctx.beginPath(); - ctx.fillStyle = "#00f"; - ctx.fillRect(15, 15, 30, 30); - ctx.fill(); - return ctx.canvas; -}; -``` - -```js -// HSV (1978) = H: Teinte / S: Saturation / V: Valeur -Color = {}; -Color.HSV_RGB = (o) => { - const S = o.S / 100; - let H = o.H / 360, - V = o.V / 100; - let R, G; - let A, B, C, D; - if (S === 0) { - R = G = B = Math.round(V * 255); - } else { - if (H >= 1) H = 0; - H *= 6; - D = H - Math.floor(H); - A = Math.round(255 * V * (1 - S)); - B = Math.round(255 * V * (1 - S * D)); - C = Math.round(255 * V * (1 - S * (1 - D))); - V = Math.round(255 * V); - switch (Math.floor(H)) { - case 0: - R = V; - G = C; - B = A; - break; - case 1: - R = B; - G = V; - B = A; - break; - case 2: - R = A; - G = V; - B = C; - break; - case 3: - R = A; - G = B; - B = V; - break; - case 4: - R = C; - G = A; - B = V; - break; - case 5: - R = V; - G = A; - B = B; - break; - } - } - return { R, G, B }; -}; - -const createInterlace = (size, color1, color2) => { - const proto = document.createElement("canvas").getContext("2d"); - proto.canvas.width = size * 2; - proto.canvas.height = size * 2; - proto.fillStyle = color1; // supérieur gauche - proto.fillRect(0, 0, size, size); - proto.fillStyle = color2; // supérieur droit - proto.fillRect(size, 0, size, size); - proto.fillStyle = color2; // inférieur gauche - proto.fillRect(0, size, size, size); - proto.fillStyle = color1; // inférieur droit - proto.fillRect(size, size, size, size); - const pattern = proto.createPattern(proto.canvas, "repeat"); - pattern.data = proto.canvas.toDataURL(); - return pattern; -}; - -const op_8x8 = createInterlace(8, "#FFF", "#eee"); -``` diff --git a/files/fr/web/api/canvasrenderingcontext2d/globalcompositeoperation/index.md b/files/fr/web/api/canvasrenderingcontext2d/globalcompositeoperation/index.md index c59b58f19ecb5c..e4f57709dbf5c7 100644 --- a/files/fr/web/api/canvasrenderingcontext2d/globalcompositeoperation/index.md +++ b/files/fr/web/api/canvasrenderingcontext2d/globalcompositeoperation/index.md @@ -1,27 +1,78 @@ --- -title: CanvasRenderingContext2D.globalCompositeOperation +title: "CanvasRenderingContext2D : propriété globalCompositeOperation" slug: Web/API/CanvasRenderingContext2D/globalCompositeOperation +l10n: + sourceCommit: 050c1825df97d836d7b91c0719386dcb5b5dded2 --- {{APIRef}} -La propriété **`CanvasRenderingContext2D.globalCompositeOperation`** de l'API Canvas 2D définit le type d'opération de composition à appliquer lors du tracé de nouvelles formes. +La propriété **`CanvasRenderingContext2D.globalCompositeOperation`** de l'API Canvas 2D définit le type d'opération de composition à appliquer lors du tracé de nouvelles formes. -Voir aussi [Composition et découpe](/fr/docs/Tutoriel_canvas/Composition) dans le [Tutoriel canvas](/fr/docs/Tutoriel_canvas). +Voir aussi [Composition et découpe](/fr/docs/Web/API/Canvas_API/Tutorial/Compositing) dans le [Tutoriel sur l'API Canvas](/fr/docs/Web/API/Canvas_API/Tutorial). -## Syntaxe +## Valeur -```js -ctx.globalCompositeOperation = type; -``` +Une chaîne de caractères qui identifie les opérations de composition ou de mode de fusion à utiliser. Elle peut prendre l'une des valeurs suivantes : -`type` est de type {{jsxref("String")}} et permet de choisir quelle opération de composition ou de mode fondu utiliser. +- `"source-over"` + - : Il s'agit du paramètre par défaut. Les nouvelles formes sont dessinées par-dessus le contenu existant du canevas. +- `"source-in"` + - : La nouvelle forme est uniquement dessinée là où elle chevauche le canevas de destination. Tout le reste est rendu transparent. +- `"source-out"` + - : La nouvelle forme est dessinée où elle ne chevauche pas le contenu du canevas existant. +- `"source-atop"` + - : La nouvelle forme est uniquement dessinée où elle chevauche le contenu du canevas existant. +- `"destination-over"` + - : Les nouvelles formes sont dessinées derrière le contenu existant du canevas. +- `"destination-in"` + - : Le contenu existant est conservé où la nouvelle forme chevauche le contenu existant du canevas. Tout le reste est rendu transparent. +- `"destination-out"` + - : Le contenu existant est conservé où il ne chevauche pas la nouvelle forme. +- `"destination-atop"` + - : Le canevas existant est uniquement conservé où il chevauche la nouvelle forme. La nouvelle forme est dessinée derrière le contenu du canevas. +- `"lighter"` + - : Là où les deux formes se chevauchent, la couleur est déterminée en ajoutant les valeurs des couleurs. +- `"copy"` + - : Seule la nouvelle forme est affichée. +- `"xor"` + - : Les formes sont rendues transparentes où les deux se chevauchent, et dessinées normalement partout ailleurs. +- `"multiply"` + - : Les pixels de la couche supérieure sont multipliés avec les pixels correspondants de la couche inférieure. On obtiendra une image plus sombre comme résultat. +- `"screen"` + - : Les pixels sont inversés, multipliés, puis à nouveau inversés. À l'inverse de `multiply`, on obtiendra une image plus claire en résultat. +- `"overlay"` + - : Une combinaison de `multiply` et `screen`. Les parties sombres de la couche de base deviennent plus sombres, les parties claires deviennent plus claires. +- `"darken"` + - : Les pixels les plus sombres des deux couches sont conservés. +- `"lighten"` + - : Les pixels les plus clairs des deux couches sont conservés. +- `"color-dodge"` + - : La couche inférieure est divisée par l'inverse de la couche supérieure. +- `"color-burn"` + - : L'inverse de la couche inférieure est divisé par la couche supérieure, le résultat obtenu est inversé pour fournir le résultat final. +- `"hard-light"` + - : À l'instar d'`overlay`, une combinaison de `multiply` et `screen`, mais avec les couches supérieure et inférieure échangées. +- `"soft-light"` + - : Une version plus douce de `hard-light`. Un noir ou un blanc pur ne donnera pas un noir ou un blanc pur. +- `"difference"` + - : La couche inférieure est soustraite à la couche supérieure, ou inversement pour toujours obtenir une valeur positive. +- `"exclusion"` + - : Semblable à `difference`, avec un contraste plus faible. +- `"hue"` + - : Conserve la luminance et la chrominance de la couche inférieure, en prenant la teinte de la couche supérieure. +- `"saturation"` + - : Conserve la luminance et la teinte de la couche inférieure, en prenant la chrominance de la couche supérieure. +- `"color"` + - : Conserve la luminance de la couche inférieure, en prenant la teinte et la chrominance de la couche supérieure. +- `"luminosity"` + - : Conserve la teinte et la chrominance de la couche inférieure, en prenant la luminance de la couche supérieure. ## Exemples -### Changer l'opération de composition +### Modifier l'opération de composition -Cet exemple utilise la propriété `globalCompositeOperation` pour dessiner deux rectangles qui s'excluent l'un l'autre quand ils se superposent. +Dans cet exemple, on utilise la propriété `globalCompositeOperation` afin de dessiner deux rectangles où leur intersection est exclue. #### HTML @@ -46,7 +97,324 @@ ctx.fillRect(50, 50, 100, 100); #### Résultat -{{ EmbedLiveSample('Exemples', 700, 180) }} +{{EmbedLiveSample('', 700, 180)}} + +### Démonstration pour toutes les valeurs + +#### Valeurs globales + +Ce fragment de code définit les valeurs globales utilisées par le reste du programme. + +```js +const canvas1 = document.createElement("canvas"); +const canvas2 = document.createElement("canvas"); +const gco = [ + "source-over", + "source-in", + "source-out", + "source-atop", + "destination-over", + "destination-in", + "destination-out", + "destination-atop", + "lighter", + "copy", + "xor", + "multiply", + "screen", + "overlay", + "darken", + "lighten", + "color-dodge", + "color-burn", + "hard-light", + "soft-light", + "difference", + "exclusion", + "hue", + "saturation", + "color", + "luminosity", +].reverse(); +const gcoText = [ + "Il s'agit du paramètre par défaut. Les nouvelles formes sont dessinées par-dessus le contenu existant du canevas.", + "La nouvelle forme est uniquement dessinée là où elle chevauche le canevas de destination. Tout le reste est rendu transparent.", + "La nouvelle forme est dessinée où elle ne chevauche pas le contenu du canevas existant.", + "La nouvelle forme est uniquement dessinée où elle chevauche le contenu du canevas existant.", + "Les nouvelles formes sont dessinées derrière le contenu existant du canevas.", + "Le contenu existant est conservé où la nouvelle forme chevauche le contenu existant du canevas. Tout le reste est rendu transparent.", + "Le contenu existant est conservé où il ne chevauche pas la nouvelle forme.", + "Le canevas existant est uniquement conservé où il chevauche la nouvelle forme. La nouvelle forme est dessinée derrière le contenu du canevas.", + "Là où les deux formes se chevauchent, la couleur est déterminée en ajoutant les valeurs des couleurs.", + "Seule la nouvelle forme est affichée.", + "Les formes sont rendues transparentes où les deux se chevauchent, et dessinées normalement partout ailleurs.", + "Les pixels de la couche supérieure sont multipliés avec les pixels correspondants de la couche inférieure. On obtiendra une image plus sombre comme résultat.", + "Les pixels sont inversés, multipliés, puis à nouveau inversés. À l'inverse de multiply, on obtiendra une image plus claire en résultat.", + "Une combinaison de multiply et screen. Les parties sombres de la couche de base deviennent plus sombres, les parties claires deviennent plus claires.", + "Les pixels les plus sombres des deux couches sont conservés.", + "Les pixels les plus clairs des deux couches sont conservés.", + "La couche inférieure est divisée par l'inverse de la couche supérieure.", + "L'inverse de la couche inférieure est divisé par la couche supérieure, le résultat obtenu est inversé pour fournir le résultat final.", + "À l'instar d'overlay, une combinaison de multiply et screen, mais avec les couches supérieure et inférieure échangées.", + "Une version plus douce de hard-light. Un noir ou un blanc pur ne donnera pas un noir ou un blanc pur.", + "La couche inférieure est soustraite à la couche supérieure, ou inversement pour toujours obtenir une valeur positive.", + "Semblable à difference, avec un contraste plus faible.", + "Conserve la luminance et la chrominance de la couche inférieure, en prenant la teinte de la couche supérieure.", + "Conserve la luminance et la teinte de la couche inférieure, en prenant la chrominance de la couche supérieure.", + "Conserve la luminance de la couche inférieure, en prenant la teinte et la chrominance de la couche supérieure.", + "Conserve la teinte et la chrominance de la couche inférieure, en prenant la luminance de la couche supérieure.", +].reverse(); +const width = 320; +const height = 340; +``` + +#### Programme principal + +Au chargement de la page, le code qui suit est exécuté pour initialiser puis exécuter l'exemple : + +```js +window.onload = () => { + // Luminance exprimée en sRGB + const lum = { + r: 0.33, + g: 0.33, + b: 0.33, + }; + // Redimensionnement du canevas + canvas1.width = width; + canvas1.height = height; + canvas2.width = width; + canvas2.height = height; + lightMix(); + colorSphere(); + runComposite(); + return; +}; +``` + +Dans le fragment de code qui suit, c'est `runComposite()` qui est responsable de la majorité du travail, exploitant quelques fonctions utilitaires pour les parties les plus complexes. + +```js +function createCanvas() { + const canvas = document.createElement("canvas"); + canvas.style.background = `url(${op_8x8.data})`; + canvas.style.border = "1px solid #000"; + canvas.style.margin = "5px"; + canvas.width = width / 2; + canvas.height = height / 2; + return canvas; +} + +function runComposite() { + const dl = document.createElement("dl"); + document.body.appendChild(dl); + while (gco.length) { + const pop = gco.pop(); + const dt = document.createElement("dt"); + dt.textContent = pop; + dl.appendChild(dt); + const dd = document.createElement("dd"); + const p = document.createElement("p"); + p.textContent = gcoText.pop(); + dd.appendChild(p); + + const canvasToDrawOn = createCanvas(); + const canvasToDrawFrom = createCanvas(); + const canvasToDrawResult = createCanvas(); + + let ctx = canvasToDrawResult.getContext("2d"); + ctx.clearRect(0, 0, width, height); + ctx.save(); + ctx.drawImage(canvas1, 0, 0, width / 2, height / 2); + ctx.globalCompositeOperation = pop; + ctx.drawImage(canvas2, 0, 0, width / 2, height / 2); + ctx.globalCompositeOperation = "source-over"; + ctx.fillStyle = "rgba(0,0,0,0.8)"; + ctx.fillRect(0, height / 2 - 20, width / 2, 20); + ctx.fillStyle = "#FFF"; + ctx.font = "14px arial"; + ctx.fillText(pop, 5, height / 2 - 5); + ctx.restore(); + + ctx = canvasToDrawOn.getContext("2d"); + ctx.clearRect(0, 0, width, height); + ctx.save(); + ctx.drawImage(canvas1, 0, 0, width / 2, height / 2); + ctx.fillStyle = "rgba(0,0,0,0.8)"; + ctx.fillRect(0, height / 2 - 20, width / 2, 20); + ctx.fillStyle = "#FFF"; + ctx.font = "14px arial"; + ctx.fillText("contenu existant", 5, height / 2 - 5); + ctx.restore(); + + ctx = canvasToDrawFrom.getContext("2d"); + ctx.clearRect(0, 0, width, height); + ctx.save(); + ctx.drawImage(canvas2, 0, 0, width / 2, height / 2); + ctx.fillStyle = "rgba(0,0,0,0.8)"; + ctx.fillRect(0, height / 2 - 20, width / 2, 20); + ctx.fillStyle = "#FFF"; + ctx.font = "14px arial"; + ctx.fillText("nouveau contenu", 5, height / 2 - 5); + ctx.restore(); + + dd.appendChild(canvasToDrawOn); + dd.appendChild(canvasToDrawFrom); + dd.appendChild(canvasToDrawResult); + + dl.appendChild(dd); + } +} +``` + +#### Fonctions utilitaires + +Ce programme utilise certaines fonctions utilitaires. + +```js +const lightMix = () => { + const ctx = canvas2.getContext("2d"); + ctx.save(); + ctx.globalCompositeOperation = "lighter"; + ctx.beginPath(); + ctx.fillStyle = "rgba(255,0,0,1)"; + ctx.arc(100, 200, 100, Math.PI * 2, 0, false); + ctx.fill(); + ctx.beginPath(); + ctx.fillStyle = "rgba(0,0,255,1)"; + ctx.arc(220, 200, 100, Math.PI * 2, 0, false); + ctx.fill(); + ctx.beginPath(); + ctx.fillStyle = "rgba(0,255,0,1)"; + ctx.arc(160, 100, 100, Math.PI * 2, 0, false); + ctx.fill(); + ctx.restore(); + ctx.beginPath(); + ctx.fillStyle = "#f00"; + ctx.fillRect(0, 0, 30, 30); + ctx.fill(); +}; +``` + +```js +const colorSphere = (element) => { + const ctx = canvas1.getContext("2d"); + const width = 360; + const halfWidth = width / 2; + const rotate = (1 / 360) * Math.PI * 2; // par degré + const offset = 0; // décalage de la barre de défilement + const oleft = -20; + const otop = -20; + for (let n = 0; n <= 359; n++) { + const gradient = ctx.createLinearGradient( + oleft + halfWidth, + otop, + oleft + halfWidth, + otop + halfWidth, + ); + const color = Color.HSV_RGB({ H: (n + 300) % 360, S: 100, V: 100 }); + gradient.addColorStop(0, "rgba(0,0,0,0)"); + gradient.addColorStop(0.7, `rgba(${color.R}, ${color.G}, ${color.B}, 1)`); + gradient.addColorStop(1, "rgba(255,255,255,1)"); + ctx.beginPath(); + ctx.moveTo(oleft + halfWidth, otop); + ctx.lineTo(oleft + halfWidth, otop + halfWidth); + ctx.lineTo(oleft + halfWidth + 6, otop); + ctx.fillStyle = gradient; + ctx.fill(); + ctx.translate(oleft + halfWidth, otop + halfWidth); + ctx.rotate(rotate); + ctx.translate(-(oleft + halfWidth), -(otop + halfWidth)); + } + ctx.beginPath(); + ctx.fillStyle = "#00f"; + ctx.fillRect(15, 15, 30, 30); + ctx.fill(); + return ctx.canvas; +}; +``` + +```js +// HSV (1978) +// H: Hue (en anglais, teinte en français) +// S: Saturation +// V: Value (en anglais, valeur en français) +Color = {}; +Color.HSV_RGB = (o) => { + const S = o.S / 100; + let H = o.H / 360, + V = o.V / 100; + let R, G; + let A, B, C, D; + if (S === 0) { + R = G = B = Math.round(V * 255); + } else { + if (H >= 1) H = 0; + H *= 6; + D = H - Math.floor(H); + A = Math.round(255 * V * (1 - S)); + B = Math.round(255 * V * (1 - S * D)); + C = Math.round(255 * V * (1 - S * (1 - D))); + V = Math.round(255 * V); + switch (Math.floor(H)) { + case 0: + R = V; + G = C; + B = A; + break; + case 1: + R = B; + G = V; + B = A; + break; + case 2: + R = A; + G = V; + B = C; + break; + case 3: + R = A; + G = B; + B = V; + break; + case 4: + R = C; + G = A; + B = V; + break; + case 5: + R = V; + G = A; + B = B; + break; + } + } + return { R, G, B }; +}; + +const createInterlace = (size, color1, color2) => { + const proto = document.createElement("canvas").getContext("2d"); + proto.canvas.width = size * 2; + proto.canvas.height = size * 2; + proto.fillStyle = color1; // supérieur gauche + proto.fillRect(0, 0, size, size); + proto.fillStyle = color2; // supérieur droit + proto.fillRect(size, 0, size, size); + proto.fillStyle = color2; // inférieur gauche + proto.fillRect(0, size, size, size); + proto.fillStyle = color1; // inférieur droit + proto.fillRect(size, size, size, size); + const pattern = proto.createPattern(proto.canvas, "repeat"); + pattern.data = proto.canvas.toDataURL(); + return pattern; +}; + +const op_8x8 = createInterlace(8, "#FFF", "#eee"); +``` + +#### Résultat + +{{EmbedLiveSample("démonstration_pour_toutes_les_valeurs", "100%", 7250)}} ## Spécifications @@ -58,5 +426,5 @@ ctx.fillRect(50, 50, 100, 100); ## Voir aussi -- L'interface qui définit cette propriété : {{domxref("CanvasRenderingContext2D")}} -- {{domxref("CanvasRenderingContext2D.globalAlpha")}} +- L'interface définissant cette propriété : [`CanvasRenderingContext2D`](/fr/docs/Web/API/CanvasRenderingContext2D) +- [`CanvasRenderingContext2D.globalAlpha`](/fr/docs/Web/API/CanvasRenderingContext2D/globalAlpha)