<?xml version="1.0" encoding="UTF-8"?> <rss version="2.0" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:sy="http://purl.org/rss/1.0/modules/syndication/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/" ><channel><title>Kévin Subileau &#187; Boite à code</title> <atom:link href="http://www.kevinsubileau.fr/informatique/boite-a-code/feed" rel="self" type="application/rss+xml" /><link>http://www.kevinsubileau.fr</link> <description>Espace personnel</description> <lastBuildDate>Sun, 02 Feb 2020 15:18:58 +0000</lastBuildDate> <language>fr-FR</language> <sy:updatePeriod>hourly</sy:updatePeriod> <sy:updateFrequency>1</sy:updateFrequency> <item><title>Powershell - Créer, lire et modifier des raccourcis</title><link>http://www.kevinsubileau.fr/informatique/boite-a-code/powershell-creer-lire-modifier-raccourcis.html?utm_source=rss&#038;utm_medium=rss&#038;utm_campaign=rss</link> <comments>http://www.kevinsubileau.fr/informatique/boite-a-code/powershell-creer-lire-modifier-raccourcis.html#comments</comments> <pubDate>Mon, 24 Apr 2017 18:45:42 +0000</pubDate> <dc:creator>Kévin Subileau</dc:creator> <category><![CDATA[Boite à code]]></category> <category><![CDATA[Powershell]]></category> <category><![CDATA[raccourci]]></category><guid isPermaLink="false">http://www.kevinsubileau.fr/?p=2634</guid> <description><![CDATA[Avec Powershell, il est possible de créer un raccourci (.lnk ou .url), mais aussi d’en lire les propriétés et de les modifier, en utilisant simplement les fonctionnalités de l’objet COM Wscript.Shell. <a href="http://www.kevinsubileau.fr/informatique/boite-a-code/powershell-creer-lire-modifier-raccourcis.html">Lire la Suite <span class="meta-nav">&#8594;</span></a>]]></description> <content:encoded><![CDATA[<p>Que ce soit pour réaliser un script d'installation ou un traitement particulier sur un grand nombre de postes, il arrive parfois que l’on ait besoin de <strong>lire, modifier ou créer un raccourci à l’aide d’un script</strong>. Pour ce dernier cas, on peut se contenter de coder un copier/coller d'un raccourci préfabriqué, mais cette méthode peut manquer de souplesse car elle ne permet pas par exemple d'adapter le raccourci créé selon certains paramètres.</p><p><strong>Avec Powershell</strong>, il est en fait possible de <strong>créer un raccourci à partir de zéro</strong>, mais aussi d’en <strong>lire les propriétés et de les modifier</strong>, en utilisant simplement les fonctionnalités de l’objet COM <code>Wscript.Shell</code>.</p><p>Pour cela, il faut commencer par créer un nouvel objet <code>Wscript.Shell</code> en utilisant la <em>cmdlet</em> <code>New-Object</code> :</p><pre class="brush: powershell; gutter: false; first-line: 1; highlight: []; html-script: false">$Shell = New-Object -ComObject Wscript.Shell</pre><p>Ensuite, on utilise la méthode <code>CreateShortcut</code> pour créer un objet raccourci associé à un chemin. Le nom de cette méthode est un peu trompeur car elle s’applique aussi bien que vous souhaitiez créer, lire ou modifier un raccourci. En fait, elle ne crée pas véritablement le raccourci sur le disque dur mais seulement sa représentation en mémoire (instanciation de la classe <code>WshShortcut</code> ou <code>WshURLShortcut</code>). Elle prend en paramètre le chemin du raccourci à lire ou à créer. <strong>Penser bien à ajouter l’extension .lnk ou .url</strong> selon que votre raccourci pointe respectivement vers un fichier ou une adresse Internet.</p><pre class="brush: powershell; gutter: false; first-line: 1; highlight: []; html-script: false">$Shortcut = $Shell.CreateShortcut($env:USERPROFILE + &quot;\Desktop\Mon raccourci.lnk&quot;)</pre><p>Vous disposez ensuite d’<strong>un ensemble de propriétés</strong> sur l’objet obtenu que vous pouvez lire ou modifier selon vos souhaits :</p><pre class="brush: powershell; gutter: false; first-line: 1; highlight: []; html-script: false"># Cible du raccourci
$Shortcut.TargetPath = &quot;C:\chemin\vers\votre\executable.exe&quot;
# Paramètres optionnels de ligne de commande
$Shortcut.Arguments = &quot;-arguments –si -necessaire&quot;
# Dossier cible
$Shortcut.WorkingDirectory = &quot;C:\chemin\vers\le\dossier\de\travail&quot;;
# Taille de la fenêtre d&#039;exécution (normale, réduite ou agrandie)
$Shortcut.WindowStyle = 1;
# Raccourci clavier
$Shortcut.Hotkey = &quot;CTRL+SHIFT+F&quot;;
# Chemin vers l&#039;icône du raccourci
$Shortcut.IconLocation = &quot;C:\chemin\vers\votre\executable.exe, 0&quot;;</pre><p>A noter que dans le cas d’un raccourci vers une adresse Internet, seule la propriété <code>TargetPath</code> est disponible.</p><p>Enfin, vous pouvez faire appel à la méthode <code>Save</code> pour enregistrer le raccourci créé ou les modifications apportées à un raccourci existant :</p><pre class="brush: powershell; gutter: false; first-line: 1; highlight: []; html-script: false">$Shortcut.Save()</pre><p>Et c’est tout ! Plutôt simple n’est-ce pas ?</p><p>Pour aller un peu plus loin, on peut ensuite <strong>combiner tout cela pour créer une ou plusieurs fonctions</strong> de manipulation des fichiers raccourcis. Voici par exemple une fonction permettant de <strong>récupérer le chemin cible d'un raccourci</strong> :</p><pre class="brush: powershell; gutter: true; first-line: 1; highlight: []; html-script: false">function function Get-ShortcutTarget {
    &lt;#
    .SYNOPSIS
        This function returns the target of a shortcut file (LNK or URL extension).
    .EXAMPLE
        Get-ShortcutTarget -FilePath &#039;C:\Users\profilename\Desktop\MyShortcut.lnk&#039;
    .PARAMETER FilePath
        The shortcut&#039;s file path (don&#039;t forget the extension !)
    #&gt;
    [CmdletBinding()]
    param (
        [Parameter(Mandatory = $true, Position = 0, ValueFromPipeline = $true)]
        [ValidateScript({ Test-Path -Path $_ -PathType Leaf })]
        [Alias(&#039;Fullname&#039;)]
        [string[]]$FilePath
    )
    process {
        $ShellObject = New-Object -ComObject Wscript.Shell
        ($ShellObject.CreateShortcut($FilePath)).TargetPath
    }
}</pre><p>A vous ensuite d'adapter ou de créer vos propres fonctions selon vos besoins. N'hésitez pas également à faire quelques recherches sur Internet, et notamment sur Github, où vous pourrez trouver des fonctions toutes prêtes pour traiter les raccourcis, comme <a href="https://github.com/adbertram/PSShortcut">ici</a> par exemple.</p> ]]></content:encoded> <wfw:commentRss>http://www.kevinsubileau.fr/informatique/boite-a-code/powershell-creer-lire-modifier-raccourcis.html/feed</wfw:commentRss> <slash:comments>3</slash:comments> </item> <item><title>Debounce et throttle : limiter les appels successifs à une fonction Javascript</title><link>http://www.kevinsubileau.fr/informatique/boite-a-code/php-html-css/javascript-debounce-throttle-reduire-appels-fonction.html?utm_source=rss&#038;utm_medium=rss&#038;utm_campaign=rss</link> <comments>http://www.kevinsubileau.fr/informatique/boite-a-code/php-html-css/javascript-debounce-throttle-reduire-appels-fonction.html#comments</comments> <pubDate>Mon, 08 Dec 2014 20:10:41 +0000</pubDate> <dc:creator>Kévin Subileau</dc:creator> <category><![CDATA[PHP, HTML et CSS]]></category> <category><![CDATA[optimisation]]></category><guid isPermaLink="false">http://www.kevinsubileau.fr/?p=1306</guid> <description><![CDATA[Les fonctions debounce et throttle sont deux techniques très efficaces pour optimiser une application Web, en évitant les appels trop fréquents à une fonction Javascript en réaction à certains événements par exemple. <a href="http://www.kevinsubileau.fr/informatique/boite-a-code/php-html-css/javascript-debounce-throttle-reduire-appels-fonction.html">Lire la Suite <span class="meta-nav">&#8594;</span></a>]]></description> <content:encoded><![CDATA[<p>Lorsque l'on développe une application Web réagissant à certains <strong>évènements en Javascript</strong>, comme le redimensionnement de la fenêtre, le mouvement de la souris ou la frappe au clavier, les fonctions rattachées à ces événements risquent d'être appelées très fréquemment. Si le code contenu dans ces fonctions est coûteux en ressources, cela peut ralentir considérablement l'application Web.</p><p>Pour <strong>améliorer les performances</strong>, ou plutôt ne pas les plomber, il existe deux techniques simples, appelées <strong><em>debounce</em></strong> et <strong><em>throttle</em></strong>. Toutes deux permettent de <strong>réduire le nombre d'appels</strong> à une fonction <strong>dans un intervalle de temps donné</strong>. En effet, il est souvent inutile d'exécuter ces fonctions à chaque fois que l’événement est déclenché.</p><p>Imaginons par exemple que l'on souhaite synchroniser sur le serveur, via des appels AJAX, le contenu d'un champ de saisie au fur et à mesure que l'utilisateur tape le texte (comme le fait Google Docs par exemple). Dans ce cas, plutôt que de solliciter le serveur à chaque caractère saisi ou inutilement lorsque le texte reste inchangé, il peut être plus judicieux de sauvegarder le texte toutes les 5 secondes tant que l'utilisateur le modifie, et de ne plus faire de requêtes lorsque que le texte reste inchangé. Et c'est exactement ce que la fonction <em>throttle</em> permet de faire.</p><p>Cependant, bien que ces deux techniques soit assez similaires, il existe une <strong>différence fondamentale</strong> dans leurs fonctionnements qu'il est important de bien comprendre pour les utiliser correctement.</p><p>Je vais donc vous présenter ces deux méthodes l'une après l'autre, en vous expliquant leurs <strong>fonctionnements </strong>et en vous donnant le <strong>code Javascript</strong> nécessaire pour les mettre en place.<br /> <span id="more-1306"></span></p><h1><em>Debounce</em></h1><p>Commençons par la fonction <em>debounce</em>. Cette technique a pour but de <strong>n'appeler qu'une seule fois une méthode</strong> au début ou à la fin d'une succession de déclenchements d'un événement. Voici tout d'abord le <strong>code source</strong> de la fonction en question :</p><pre class="gutter: true; brush: javascript;">/**
 * Retourne une fonction qui, tant qu&#039;elle continue à être invoquée,
 * ne sera pas exécutée. La fonction ne sera exécutée que lorsque
 * l&#039;on cessera de l&#039;appeler pendant plus de N millisecondes.
 * Si le paramètre `immediate` vaut vrai, alors la fonction 
 * sera exécutée au premier appel au lieu du dernier.
 * Paramètres :
 *  - func : la fonction à `debouncer`
 *  - wait : le nombre de millisecondes (N) à attendre avant 
 *           d&#039;appeler func()
 *  - immediate (optionnel) : Appeler func() à la première invocation
 *                            au lieu de la dernière (Faux par défaut)
 *  - context (optionnel) : le contexte dans lequel appeler func()
 *                          (this par défaut)
 */
function debounce(func, wait, immediate, context) {
    var result;
    var timeout = null;
    return function() {
        var ctx = context || this, args = arguments;
        var later = function() {
            timeout = null;
            if (!immediate) result = func.apply(ctx, args);
        };
        var callNow = immediate &amp;&amp; !timeout;
        // Tant que la fonction est appelée, on reset le timeout.
        clearTimeout(timeout);
        timeout = setTimeout(later, wait);
        if (callNow) result = func.apply(ctx, args);
        return result;
    };
}</pre><p>Pour mieux comprendre son fonctionnement, regardons le schéma ci dessous :</p><div id="attachment_1396" class="wp-caption aligncenter" style="width: 751px"><img class="size-full wp-image-1396" alt="js-debounce" src="http://www.kevinsubileau.fr/wp-content/uploads/2014/11/js-debounce.png" width="741" height="210" /><p class="wp-caption-text">Chronogramme de la fonction <em>debounce</em></p></div><p>Sur la première ligne de cette figure, chaque rectangle bleu représente <strong>un déclenchement de l’événement</strong> écouté (<em>keydown</em> par exemple). Lorsque deux déclenchements sont espacés par une <strong>durée inférieure à une valeur prédéfinie</strong> (paramètre <em>wait</em>), on va dire qu'ils appartiennent à <strong>une même séquence</strong>. Si la durée est supérieure, alors cela marque le début d'une nouvelle séquence.</p><p>Sur la deuxième ligne, les rectangles verts représentent les exécutions de la fonction "débouncé" (paramètre <em>func</em>). On remarque alors que la fonction <em>debounce</em> permet d'<strong>attendre la fin d'une séquence d'évènement</strong> pour effectuer le traitement associé. Si maintenant on reprend l'exemple de la synchronisation d'un champ de texte, cela signifie que l'appel AJAX sera effectué uniquement lorsque l'utilisateur cessera de modifier le contenu pendant une durée supérieure à <em>wait</em>.</p><p>Par ailleurs, dans certains cas, il peut être plus intéressant d'exécuter le traitement <strong>au début de la séquence</strong> plutôt qu'à la fin (comme le représente les rectangles violets). Cela est possible simplement en définissant le <strong>paramètre optionnel <em>immediate</em></strong> à <em>true</em>.</p><p>L'utilisation concrète de cette fonction est assez simple. Voici un exemple :</p><pre class="gutter: true; brush: javascript; highlight: [8];">function traiterEvenement() {
	// Fonction de traitement de l&#039;évenement
        // (sauvegarde par appel AJAX par exemple)
}

// On limite l’exécution de la fonction traiterEvenement à une fois
// toutes les 5000 millisecondes (5s) au maximum.
var traiterEvenementDebounce = debounce(traiterEvenement, 5000);

// On s&#039;enregistre sur l’événement de saisie clavier
document.querySelectorAll(&#039;#field&#039;)
        .addEventListener(&#039;keydown&#039;, traiterEvenementDebounce);</pre><p>Cependant, ce mode de fonctionnement <strong>peut parfois poser problème</strong>. Ici par exemple, si l'utilisateur tape son texte en continu pendant plusieurs minutes, il ne sera pas sauvegardé sur le serveur puisque la séquence ne se termine pas. Selon les cas, cela peut être souhaitable ou gênant, c'est à vous de voir. Pour éviter cela, il y a deux solutions :</p><ul><li>Soit <strong>réduire l'intervalle</strong> entre les séquences (de 5s à 500ms par exemple), en se disant que l'utilisateur ne pourra pas taper longtemps sur son clavier sans jamais s'arrêter moins de 500ms. C'est plutôt vrai, mais du coup on augmente potentiellement le nombre d’exécutions, donc ça risque d'être plus lent et ça perd un peu de son intérêt...</li><li>Soit <strong>utiliser la fonction <em>throttle</em></strong>, qui propose un fonctionnement un peu différent.</li></ul><h1><em>Throttle</em></h1><p>Parlons donc maintenant de la fonction <em>throttle</em>. Ici, comme le montre le chronogramme ci-dessous, on va exécuter la fonction de traitement de l'événement <strong>de manière périodique</strong> durant la séquence de déclenchements.</p><div id="attachment_1397" class="wp-caption aligncenter" style="width: 785px"><img class="size-full wp-image-1397" alt="js-throttle" src="http://www.kevinsubileau.fr/wp-content/uploads/2014/11/js-throttle.png" width="775" height="159" /><p class="wp-caption-text">Chronogramme de la fonction <em>throttle</em></p></div><p>Sur cette figure, les rectangles de couleur de la deuxième ligne représentes les exécutions de la fonction <em>func</em>. Attention, par défaut, seuls les rectangles violets sont effectivement exécutés. Pour inclure également les exécutions en début et/ou en fin de séquence (rectangles jaunes et verts), il faut définir respectivement les paramètres <em>leading</em> et/ou <em>trailing</em> à <em>true</em>.</p><p>Si on applique cette fonction à notre exemple, cela signifie que le texte du champ de saisie sera sauvegardé sur le serveur par un appel AJAX toutes les 5 secondes par exemple (paramètre <em>wait</em>), et ce tant que l'utilisateur change le contenu. Et si le texte n'est pas modifié, aucun appel n'est effectué. Ce comportement est donc idéal dans ce cas, puisqu'on limite le nombre d'appels au strict nécessaire pour ne pas risquer une perte de données.</p><p>Voici donc maintenant le code de la fonction <em>throttle</em> :</p><pre class="gutter: true; brush: javascript;">/**
 * Retourne une fonction qui, tant qu&#039;elle est appelée,
 * n&#039;est exécutée au plus qu&#039;une fois toutes les N millisecondes.
 * Paramètres :
 *  - func : la fonction à contrôler
 *  - wait : le nombre de millisecondes (période N) à attendre avant 
 *           de pouvoir exécuter à nouveau la function func()
 *  - leading (optionnel) : Appeler également func() à la première
 *                          invocation (Faux par défaut)
 *  - trailing (optionnel) : Appeler également func() à la dernière
 *                           invocation (Faux par défaut)
 *  - context (optionnel) : le contexte dans lequel appeler func()
 *                          (this par défaut)
 */
function throttle(func, wait, leading, trailing, context) {
    var ctx, args, result;
    var timeout = null;
    var previous = 0;
    var later = function() {
        previous = new Date;
        timeout = null;
        result = func.apply(ctx, args);
    };
    return function() {
        var now = new Date;
        if (!previous &amp;&amp; !leading) previous = now;
        var remaining = wait - (now - previous);
        ctx = context || this;
        args = arguments;
        // Si la période d&#039;attente est écoulée
        if (remaining &lt;= 0) {
            // Réinitialiser les compteurs
            clearTimeout(timeout);
            timeout = null;
            // Enregistrer le moment du dernier appel
            previous = now;
            // Appeler la fonction
            result = func.apply(ctx, args);
        } else if (!timeout &amp;&amp; trailing) {
            // Sinon on s’endort pendant le temps restant
            timeout = setTimeout(later, remaining);
        }
        return result;
    };
};</pre><p>L'utilisation de cette fonction est semblable à la fonction <em>debounce</em>, hormis les arguments optionnels qui sont différents. Voici un exemple :</p><pre class="gutter: true; brush: javascript;  highlight: [7];">function traiterEvenement() {
	// Fonction de traitement de l&#039;évenement
        // (sauvegarde par appel AJAX par exemple)
}

// Ici il est utile d&#039;activer le `trailing` pour traiter le dernier événement
var traiterEvenementThrottle = throttle(traiterEvenement, 5000, false, true);

// On s&#039;enregistre sur l’événement de saisie clavier
document.querySelectorAll(&#039;#field&#039;)
        .addEventListener(&#039;keydown&#039;, traiterEvenementThrottle);</pre><p>Les applications possibles de ces fonctions sont très nombreuses. Ici, j'ai pris l'exemple d'une fonctionnalité d'enregistrement automatique. Mais on peut aussi les utiliser pour repositionner des éléments lors du redimensionnement de la fenêtre, enregistrer des événements sur Piwik sans trop de répétitions, ...</p><p>Notez que <strong>certaines bibliothèques Javascript</strong>, comme <a href="http://lodash.com/">Lodash</a> ou <a href="http://underscorejs.org/#debounce">UnderscoreJS</a>, <strong>fournissent directement ces fonctions</strong>. Les implémentations que je vous propose ci-dessus en sont d'ailleurs inspirées. Inutile donc de les dupliquer si vous utilisez déjà une de ces bibliothèques pour votre application Web.</p><p>Enfin, bien que je parle ici de Web et de Javascript, je pense qu'il est tout à fait envisageable de reprendre le principe pour d'autres types de développement, y compris des applications bureaux en C++, C# ou Java par exemple. Étant donné la singularité de la syntaxe Javascript, il faudra en revanche revoir entièrement l'implémentation...</p><p>Voilà, j'espère que cet article vous aura aidé à comprendre l'utilité et le fonctionnement de ces fonctions. Si vous avez des questions, n'hésitez pas à me les poser en commentaire <img src='http://www.kevinsubileau.fr/wp-includes/images/smilies/icon_wink.gif' alt=';)' class='wp-smiley' /> .</p><p><strong>Maj 12/08/2015</strong> :  En complément de cet article, je vous conseille de voir également ce <a href="http://www.grafikart.fr/tutoriels/javascript/debounce-throttle-642">tutoriel vidéo</a> que l'ami Grafikart a publié ce jour.</p> ]]></content:encoded> <wfw:commentRss>http://www.kevinsubileau.fr/informatique/boite-a-code/php-html-css/javascript-debounce-throttle-reduire-appels-fonction.html/feed</wfw:commentRss> <slash:comments>1</slash:comments> </item> <item><title>Color Thief PHP : extraire les couleurs dominantes d&#039;une image</title><link>http://www.kevinsubileau.fr/informatique/boite-a-code/php-html-css/color-thief-php-couleur-dominante-image.html?utm_source=rss&#038;utm_medium=rss&#038;utm_campaign=rss</link> <comments>http://www.kevinsubileau.fr/informatique/boite-a-code/php-html-css/color-thief-php-couleur-dominante-image.html#comments</comments> <pubDate>Thu, 08 May 2014 16:49:34 +0000</pubDate> <dc:creator>Kévin Subileau</dc:creator> <category><![CDATA[PHP, HTML et CSS]]></category> <category><![CDATA[couleurs]]></category> <category><![CDATA[dominante]]></category> <category><![CDATA[palette]]></category><guid isPermaLink="false">http://www.kevinsubileau.fr/?p=1142</guid> <description><![CDATA[Color Thief PHP est une classe PHP qui vous permet d'extraire la couleur dominante ou une palette de couleurs à partir d'une image JPEG, GIF, ou PNG. Il s'agit d'un portage du script Javascript réalisé par Lokesh Dhakar, qui utilise un algorithme avancé de quantification des couleurs (MMCQ). <a href="http://www.kevinsubileau.fr/informatique/boite-a-code/php-html-css/color-thief-php-couleur-dominante-image.html">Lire la Suite <span class="meta-nav">&#8594;</span></a>]]></description> <content:encoded><![CDATA[<p><strong><a title="Color Thief PHP" href="http://www.kevinsubileau.fr/projets/color-thief-php">Color Thief PHP</a></strong> est une classe PHP qui vous permet d'<strong>extraire la couleur dominante ou une palette de couleurs à partir d'une image</strong> JPEG, GIF, ou PNG. Le projet est disponible sur <a title="Color Thief PHP" href="http://github.com/ksubileau/color-thief-php">GitHub</a>, et sur <a title="Color Thief PHP" href="http://packagist.org/packages/ksubileau/color-thief-php">Packagist</a>. Vous pouvez également voir le code en fonctionnement sur cette <a title="Color Thief PHP" href="http://www.kevinsubileau.fr/projets/color-thief-php">page de démonstration</a>.</p><p>La particularité de cette classe est qu'<strong>elle n'utilise pas une simple moyenne arithmétique</strong> pour déterminer la couleur dominante, contrairement à de nombreux scripts disponibles sur le web. En effet, cette méthode donne souvent des résultats plutôt aberrants, avec une couleur moche qui ne ressemble à rien de ce que l'on perçoit dans l'image. Ici, <strong>un algorithme avancé de quantification de couleurs est utilisé</strong>. Cet algorithme, nommé <a href="http://www.leptonica.com/papers/mediancut.pdf"><em>"Modified Mean Cut Quantizer"</em></a>, est comparable à celui utilisé par la compression JPEG. L'avantage est que les couleurs calculées sont le plus souvent <strong>visuellement très proches de celles présentes dans l'image</strong> d'origine, comme vous pouvez le voir sur l'exemple ci-dessous :</p><div id="attachment_1148" class="wp-caption aligncenter" style="width: 786px"><img class="size-full wp-image-1148" alt="color-thief-example" src="http://www.kevinsubileau.fr/wp-content/uploads/2014/05/color-thief-example.jpg" width="776" height="510" /><p class="wp-caption-text">Un exemple de palette de couleurs obtenue grâce à Color Thief PHP</p></div><p>L'<strong>utilisation de la classe est très simple</strong>, surtout si vous utilisez Composer, mais peut être assez gourmande en ressources en fonction de la taille de l'image et de la qualité demandée. Je vous conseille donc de conserver le résultat en base de données plutôt que d’exécuter le script à chaque chargement de page. Pour plus d'informations, je vous invite à vous reporter à la <a href="http://github.com/ksubileau/color-thief-php/blob/master/README.md">documentation sur GitHub</a>.</p><p>Les applications de cette classe ne sont limitées que par votre imagination : <strong>moteur de recherche par couleur</strong>, adaptation des couleurs de l'interface graphique en fonction de l'image affichée... Alex P. Gates a même développé <a href="http://alexpgates.com/blog/2013/11/scanning-colors-to-hue.html">un script PHP capable de modifier la couleur d'une lampe</a> en fonction des couleurs d'une image, en utilisant Color Thief PHP et une lampe Philips Hue.</p><p>Enfin, si vous avez besoin de cet outil coté client en Javascript, sachez qu'il s'agit en fait <strong>d'un portage d'un script javascript</strong>. Vous pouvez donc utiliser le script <a href="http://lokeshdhakar.com/projects/color-thief/">Color Thief original réalisé par Lokesh Dhakar</a>.</p> ]]></content:encoded> <wfw:commentRss>http://www.kevinsubileau.fr/informatique/boite-a-code/php-html-css/color-thief-php-couleur-dominante-image.html/feed</wfw:commentRss> <slash:comments>10</slash:comments> </item> <item><title>C++ : Déclarer une variable dans un switch</title><link>http://www.kevinsubileau.fr/informatique/boite-a-code/c-cpp/cpp-declarer-variable-switch.html?utm_source=rss&#038;utm_medium=rss&#038;utm_campaign=rss</link> <comments>http://www.kevinsubileau.fr/informatique/boite-a-code/c-cpp/cpp-declarer-variable-switch.html#comments</comments> <pubDate>Sat, 11 Jan 2014 19:20:13 +0000</pubDate> <dc:creator>Kévin Subileau</dc:creator> <category><![CDATA[C, C++]]></category> <category><![CDATA[switch]]></category> <category><![CDATA[variable]]></category><guid isPermaLink="false">http://www.kevinsubileau.fr/?p=822</guid> <description><![CDATA[En C++, il est possible de déclarer une nouvelle variable à tout moment dans le code... ou presque. Si vous déclarez une variable à l'intérieur d'un switch, il est possible que vous obteniez une erreur du compilateur ! <a href="http://www.kevinsubileau.fr/informatique/boite-a-code/c-cpp/cpp-declarer-variable-switch.html">Lire la Suite <span class="meta-nav">&#8594;</span></a>]]></description> <content:encoded><![CDATA[<p>En C++, il est possible de déclarer une nouvelle variable à tout moment dans le code... ou presque !</p><p>Ainsi, l'extrait de code ci-dessous est évidemment <strong>parfaitement valide</strong> et compile sans erreur :</p><pre class="gutter: true; brush: cpp; highlight: 3">for (int i = 0; i &lt; 10; ++i) {
    std::cout &lt;&lt; &quot;Itération n°&quot; &lt;&lt; i &lt;&lt; std::endl;
    int dummy;
    dummy = i * i;
    std::cout &lt;&lt; &quot;Le carré de &quot; &lt;&lt; i &lt;&lt; &quot; est &quot; &lt;&lt; dummy  &lt;&lt; std::endl;
}</pre><p>On note que <strong>la variable <code>dummy</code> est définie au milieu du code</strong>, sans que cela ne pose problème. Partant de ce constat, on pourrait croire que le code suivant compile également sans problème (en supposant que la variable <code>choix</code> est définie) :</p><pre class="gutter: true; brush: cpp; highlight: 4">switch (choix) {
    case 1:
        std::cout &lt;&lt; &quot;Choix 1.&quot; &lt;&lt; std::endl;
        int dummy = time(NULL); // Erreur !!
        std::cout &lt;&lt; &quot;Il est &quot; &lt;&lt; dummy &lt;&lt; std::endl;
        break;
    default:
        std::cout &lt;&lt; &quot;Choix inconnu.&quot; &lt;&lt; std::endl;
        // std::cout &lt;&lt; &quot;Il est &quot; &lt;&lt; dummy &lt;&lt; std::endl;
        break;
}</pre><p>Et bien non ! Si vous compiler un code de ce genre, <strong>le compilateur le refusera</strong> en indiquant une erreur du type :</p><pre class="brush: text; gutter: false;">error: jump to case label
   crosses initialization of &#039;int dummy&#039;</pre><p>ou encore, selon les cas :</p><pre class="brush: text; gutter: false;">error: initialization of &#039;dummy&#039; is skipped by &#039;case&#039; label</pre><p>La raison de cette erreur est que la <strong>portée</strong> de la variable définie à l'intérieur d'un <code>case</code> s'étend à l'ensemble du <code>switch</code>, et pas seulement à ce <code>case</code>. Le <code>case</code> n'est qu'un label, et ne limite pas la portée de la variable, qui n'est limitée que par les accolades englobantes du <code>switch</code>. Que se passerait il alors si le compilateur ne disait rien et que je décommentais la ligne 9 du code précédent ? Et bien, dans le cas où <code>choix</code> serait différent de 1, <strong>l'initialisation de la variable</strong> faite à la ligne 4 serait sautée puisque seul le bloc <code>default</code> serait exécuté. La variable <code>dummy</code> serait donc définie (puisque sa portée est globale à tout le <code>switch</code>) mais non initialisée (puisque l'initialisation n'a pas été exécutée). Dans cet exemple, <code>dummy</code> est un entier, il contiendrait simplement une valeur indéterminée. Mais ce pourrait tout aussi bien être un objet, et dans ce cas, <strong>le constructeur ne serait pas appelé</strong> si <code>choix</code> est différent de 1 ! Ce comportement risqué est donc interdit par le compilateur.</p><p>Pour résoudre ce problème, il faut explicitement limiter la portée de la variable en <strong>entourant le code du <code>case</code> par une paire d'accolades</strong>, comme ci-dessous :</p><pre class="gutter: true; brush: cpp; highlight: [3,5,8]">switch (choix) {
    case 1:
    {
        std::cout &lt;&lt; &quot;Choix 1.&quot; &lt;&lt; std::endl;
        int dummy = time(NULL); // Ok !!
        std::cout &lt;&lt; &quot;Il est &quot; &lt;&lt; dummy &lt;&lt; std::endl;
        break;
    }
    default:
        std::cout &lt;&lt; &quot;Choix inconnu.&quot; &lt;&lt; std::endl;
        // Désormais interdit car la variable est hors de portée !
        // std::cout &lt;&lt; &quot;Il est &quot; &lt;&lt; dummy &lt;&lt; std::endl;
        break;
}</pre><p>La portée de la variable <code>dummy</code> est ainsi limitée au <code>case</code>, et il devient <strong>impossible de l'utiliser dans un autre <code>case</code>.</strong></p><p>Voilà pour cette petite astuce de programmation en C++ assez simple, il suffit juste d'y penser ! A noter que ce problème et sa solution s'applique aussi lorsque l'on déclare une variable entre un <code>goto</code> et le label ciblé par ce <code>goto</code>. Mais bon, c'est bien connu, plus personne n'utilise le <code>goto</code> de nos jours...</p><p style="text-align: right;"><small><a href="http://stackoverflow.com/questions/92396/why-cant-variables-be-declared-in-a-switch-statement">Source</a></small></p> ]]></content:encoded> <wfw:commentRss>http://www.kevinsubileau.fr/informatique/boite-a-code/c-cpp/cpp-declarer-variable-switch.html/feed</wfw:commentRss> <slash:comments>3</slash:comments> </item> <item><title>Générer un faux texte en une ligne de PHP</title><link>http://www.kevinsubileau.fr/informatique/boite-a-code/php-html-css/generer-faux-texte-lorem-ipsum-en-php.html?utm_source=rss&#038;utm_medium=rss&#038;utm_campaign=rss</link> <comments>http://www.kevinsubileau.fr/informatique/boite-a-code/php-html-css/generer-faux-texte-lorem-ipsum-en-php.html#comments</comments> <pubDate>Mon, 04 Nov 2013 19:53:21 +0000</pubDate> <dc:creator>Kévin Subileau</dc:creator> <category><![CDATA[PHP, HTML et CSS]]></category> <category><![CDATA[lorem ipsum]]></category> <category><![CDATA[PHP]]></category><guid isPermaLink="false">http://www.kevinsubileau.fr/?p=640</guid> <description><![CDATA[Le faux texte (lorem ipsum) est très souvent utilisé lors du développement d'un site Web. Voyez ici comment le générer simplement en une ligne de code PHP ! <a href="http://www.kevinsubileau.fr/informatique/boite-a-code/php-html-css/generer-faux-texte-lorem-ipsum-en-php.html">Lire la Suite <span class="meta-nav">&#8594;</span></a>]]></description> <content:encoded><![CDATA[<p>Lorsque l'on développe un site ou une application Web, il est souvent très utile de pouvoir remplir la base de données ou la page Web de <strong>faux texte</strong>, de type <a href="http://fr.wikipedia.org/wiki/Faux-texte">Lorem ipsum</a>. En effet, cela permet de <strong>se concentrer sur le design et la mise en page</strong> sans pour autant avoir le contenu final de la page et sans que ce contenu ne détourne notre attention.</p><p>Mais plutôt que de copier/coller ces faux paragraphes sans cesse, saviez-vous qu'il est possible de<strong> le "générer" facilement avec une ligne de code PHP</strong> ? C'est plus classe, ça prend moins de place dans le code côté serveur, et surtout vous pouvez l'utiliser pour <strong>remplir la base de données</strong> et pas seulement pour l'afficher directement !</p><p>Le suspens a assez duré, <strong>voici le code en question</strong> :</p><pre class="gutter: true; brush: php;">$lipsum = simplexml_load_file(&#039;http://www.lipsum.com/feed/xml?amount=1&amp;what=paras&amp;start=0&#039;)-&gt;lipsum;</pre><p>Bon, ok, j'ai un peu triché. En réalité, on ne génère pas réellement le <em>lipsum</em> en PHP, mais on utilise plutôt l'API du site <a href="http://lipsum.com/">lipsum.com</a>. Mais peu importe, le but principal est atteint, on a <strong>un faux texte en une ligne de PHP</strong> !</p><p>Pour allez plus loin, vous pouvez transformer cette simple ligne en une fonction un peu plus évoluée qui vous permettra de contrôler un peu plus de paramètres sur le texte généré :</p><pre class="gutter: true; brush: php;">function generer_lipsum($quantite = 1, $type = &#039;paras&#039;, $lorem = false) {
    $url = &quot;http://www.lipsum.com/feed/xml?amount=$quantite&amp;what=$type&amp;start=&quot;.($lorem?&#039;yes&#039;:&#039;no&#039;);
    return simplexml_load_file($url)-&gt;lipsum;
}</pre><p>Où les paramètres sont :</p><ul><li><strong><em> $quantite</em></strong> : la quantité de texte à générer.</li><li><strong><em>$type</em></strong> : l'unité de comptage de la quantité de texte : <em>paras</em> pour paragraphes, <em>words</em> pour mots, <em>bytes</em> pour octets ou <em>lists</em> pour des listes HTML. Ainsi, si vous définissez <em>$quantite</em> à 5 et <em>$type</em> à <em>words</em>, vous allez générer une phrase aléatoire de 5 mots.</li><li><strong><em>$lorem</em></strong> : Si vrai, force le texte généré à débuter par <em>"Lorem ipsum dolor sit amet...".</em></li></ul><p>Voilà pour cette petite astuce qui me plait beaucoup et qui, je l'espère, vous plaira tout autant ! Et si vous en connaissez d'autres de ce style, n’hésitez pas à les partager en commentaire de cet article <img src='http://www.kevinsubileau.fr/wp-includes/images/smilies/icon_biggrin.gif' alt=':D' class='wp-smiley' /> .</p> ]]></content:encoded> <wfw:commentRss>http://www.kevinsubileau.fr/informatique/boite-a-code/php-html-css/generer-faux-texte-lorem-ipsum-en-php.html/feed</wfw:commentRss> <slash:comments>0</slash:comments> </item> <item><title>Rediriger vers un fichier en conservant l&#039;affichage</title><link>http://www.kevinsubileau.fr/informatique/boite-a-code/bash/rediriger-vers-un-fichier-en-conservant-affichage.html?utm_source=rss&#038;utm_medium=rss&#038;utm_campaign=rss</link> <comments>http://www.kevinsubileau.fr/informatique/boite-a-code/bash/rediriger-vers-un-fichier-en-conservant-affichage.html#comments</comments> <pubDate>Sun, 20 Jan 2013 17:07:06 +0000</pubDate> <dc:creator>Kévin Subileau</dc:creator> <category><![CDATA[Bash]]></category> <category><![CDATA[redirection]]></category> <category><![CDATA[tee]]></category><guid isPermaLink="false">http://www.kevinsubileau.fr/?p=209</guid> <description><![CDATA[Dans un script Bash, il peut arriver que l'on souhaite rediriger la sortie d'une commande vers un fichier tout en conservant l'affichage sur l'écran. L'astuce consiste simplement à utiliser la commande tee. Par exemple, le code : echo &#34;toto&#34; &#124; &#8230; <a href="http://www.kevinsubileau.fr/informatique/boite-a-code/bash/rediriger-vers-un-fichier-en-conservant-affichage.html">Lire la Suite <span class="meta-nav">&#8594;</span></a>]]></description> <content:encoded><![CDATA[<p>Dans un script Bash, il peut arriver que l'on souhaite rediriger la sortie d'une commande vers un fichier tout en conservant l'affichage sur l'écran. L'astuce consiste simplement à utiliser la commande <strong>tee</strong>. Par exemple, le code :</p><pre class="brush: bash; gutter: false">echo &quot;toto&quot; | tee monfichier</pre><p>Permet donc d'afficher toto sur l'écran tout en l'écrivant dans le fichier <em>monfichier</em>. Si le fichier n'existe pas il sera créé, sinon son contenu sera écrasé.</p><p>Il est également possible de spécifier plusieurs fichiers :</p><pre class="brush: bash; gutter: false">echo &quot;toto&quot; | tee monfichier autrefichier encoreun</pre><p>Enfin, si l'on souhaite ajouter la sortie aux fichiers indiqués plutôt que de les écraser, il faut spécifier l'option -a ou <code>--</code>append :</p><pre class="brush: bash; gutter: false">echo &quot;toto&quot; | tee -a monfichier autrefichier encoreun</pre><p>Quelques options supplémentaires sont disponibles, voir le <a title="Man tee" href="http://pwet.fr/man/linux/commandes/tee" rel="nofollow">man de tee</a> ! Pour se souvenir du nom de cette commande, on peut faire l'analogie avec un T de plomberie, en sachant que la lettre T se prononce tee en anglais <img src='http://www.kevinsubileau.fr/wp-includes/images/smilies/icon_wink.gif' alt=';)' class='wp-smiley' /> <img class="aligncenter  wp-image-221" alt="tee" src="http://www.kevinsubileau.fr/wp-content/uploads/2013/01/tee.jpg" width="182" height="133" /></p> ]]></content:encoded> <wfw:commentRss>http://www.kevinsubileau.fr/informatique/boite-a-code/bash/rediriger-vers-un-fichier-en-conservant-affichage.html/feed</wfw:commentRss> <slash:comments>0</slash:comments> </item> </channel> </rss>
<!-- Performance optimized by W3 Total Cache. Learn more: http://www.w3-edge.com/wordpress-plugins/

Minified using disk: basic
Page Caching using disk: enhanced
Database Caching using disk: basic

Served from: www.kevinsubileau.fr @ 2026-04-06 04:27:15 -->