Archive for the ‘Trucs & Astuces’ Category

Lenteur avec VNC

26 août 2013

J’ai récemment déménagé à 800 km de ma famille, et avant mon départ, j’ai installé sur leurs machines UltraVNC pour me permettre de les dépanner (j’ai également découvert Ultra VNC Simple Clic, une version du serveur qui se connecte sur le client lorsque l’on clique dessus. L’avantage, c’est qu’il n’y a aucune config à faire côté client, pas de redirection de port dans les box notamment. L’exécutable UVNC SC contient les informations qui permettent de joindre ma machine sur laquelle s’exécute le client VNC ne mode écoute. C’est de mon côté que les redirections de ports sont paramétrées. Il suffit que je donne le lien vers mon exécutable configuré, exécutable hébergé sur mon site Web, et en un clic et aucune config du côté serveur, je peux prendre la main sur la machine distante, magique et pratique pour prendre la main sur une nouvelle machine par exemple !).

UltraVNC

UltraVNC

Bref, sur au moins 2 machines, la prise à distance (que ça soit via VNC Server ou via VNC SC) était quasi inutilisable car l’image de la machine distante ne se rafraîchissait pas de mon côté (j’était obligé de forcer le rafraîchissement via la fonction idoine de VNC Viewer, et même via ce biais, ça ne se rafraîchissait pas rapidement). Le bug est apparu sur Windows XP et Windows 7, j’imagine donc que c’est indépendant des versions de Windows.

Le problème vient en fait du driver de capture vidéo de VNC qui gère mal l’acquisition sur des affichages paramétrés en 24 ou 32 bits. La solution est donc de modifier le paramétrage de l’affichage de la machine distante en la diminuant sur 16 bits. A partir de la, tout est fluide chez moi.

Générer un dégradé en arc-en-ciel

3 novembre 2011

Pour un projet personnel (dont je reparlerais certainement plus tard sur ce blog), j’ai eu besoin de générer des points de couleur en fonction de la position de la valeur du point au sein d’un ensemble. Je souhaitais avoir quelque chose de continu, c’est à dire que 2 points ayant une valeur proche aient une couleur proche, et couvrir la plus large gamme possible de couleur, l’idéal étant d’avoir quelque chose qui se rapproche d’un arc en ciel.

Pour résumer, voici mes contraintes :

  • une variation continue des couleurs (autrement dit, hors de question de faire un saut du jaune au rouge par exemple si 2 points ont des valeurs voisines, chose que l’on obtient en général avec des algorithmes plus simplistes)
  • couvrir la plus large gamme possible de couleurs (pour résumer, je veux du rouge, du orange, du jaune, du vert, du bleu, du violet…)

C’est un problème d’apparence simple, mais qui nécessite d’être correctement modélisé pour parvenir à ses fins. Une simple étude du système RGB permet d’en trouver une solution. Traçons le graph des composantes rouges (R), vertes (V) et bleues (B) des couleurs ordonnées de l’arc en ciel. On obtient quelque chose comme ceci (on a en x les « numéro » des couleurs et en y la valeur entre 0 et 255 de chaque composante RGB. Les pastilles aux bases et aux sommets permettent de représenter la couleur résultante) :

RGB componant graphic

Graphique des composantes RVB

On voit ici que l’idée de l’algorithme est de ne faire varier qu’une seule composante à la fois.

Avec ce graphique, il est aisé de donner les fonctions résultantes des composantes R, V et B, qui sont de simple fonctions du premier degré, à définir par parties (l’objectif étant de d’avoir les valeurs de R, V et B sur l’intervalle [0;255], en ne faisant varier qu’une seule composante à la fois) :

  • Pour la composante rouge :
  (r) \left\{  \begin{array}{lrl}  \textrm{si } 0 \le x < 255 & :r= & 255 \\  \textrm{si } 255 \le x < 510 & :r= & 510-x \\  \textrm{si } 510 \le x < 1020 & :r= & 0 \\  \textrm{si } 1020 \le x \le 1275 & :r= & x-1020 \\  \textrm{si } 1275 \le x \le 1530 & :r= & 255 \\  \end{array}  \right.
  • Pour la composante verte :
  (v) \left\{  \begin{array}{lrl}  \textrm{si } 0 \le x < 255 & :v= & x \\  \textrm{si } 255 \le x < 765 & :v= & 255 \\  \textrm{si } 765 \le x < 1020 & :v= & 1020-x \\  \textrm{si } 1020 \le x \le 1530 & :v= & 0 \\  \end{array}  \right.
  • Pour la composante bleue :
  (b) \left\{  \begin{array}{lrl}  \textrm{si } 0 \le x < 510 & :b= & 0 \\  \textrm{si } 510 \le x < 765 & :b= & x-510 \\  \textrm{si } 765 \le x < 1275 & :b= & 255 \\  \textrm{si } 1275 \le x \le 1530 & :b= & 1530-x \\  \end{array}  \right.

Dans toutes ces formules, x représentant le « numéro » (ou l’indice) de la couleur que l’on souhaite obtenir. Si on a une valeur y comprise entre dans l’intervalle [y_{min};y_{max}], on peut obtenir x par la formule x = \dfrac{1530}{y_{max}-y_{min}} \times y.

A noter qu’ici, j’ai opté pour un intervalle de [0;1530] car il représente 6 times 255 soit le plus grand nombre de couleurs que l’on puisse obtenir avec cet algorithme (au delà, une même couleur pourrait avoir 2 numéros, ce qui serait bien sur inutile). Il est bien sur possible d’adapter cet algorithme de façon à avoir un nombre de nuances plus réduits (100 par exemple).

Cette algorithme produit ces variations (je vous présente ici la gamme complète des couleurs que peut générer l’algo) :

Dégradé généré par l'algorithme présenté

Dégradé généré par l’algorithme présenté

Passons au code, voici le code qui permet de générer les codes RGB correspondants aux valeurs. La fonction prend en argument l’intervalle et la valeur à partir de laquelle il faut  déterminer la couleur. Comme c’est du C++, la fonction retourne simplement un objet QColor (objet Qt).

QColor calcColor(double interval, double value){
QColor color;
int x = (1530/interval)*value;
int r;
int g;
int b;
if(x>=0 && x<255){
r = 255;
g = x;
b = 0;
}
if(x>=255 && x<510){
r = 510-x;
g = 255;
b = 0;
}
if(x>=510 && x<765){
r = 0;
g = 255;
b = x-510;
}
if(x>=765 && x<1020){
r = 0;
g = 1020-x;
b = 255;
}
if(x>=1020 && x<1275){
r = x-1020;
g = 0;
b = 255;
}
if(x>=1275 && x<=1530){
r = 255;
g = 0;
b = 1530-x;
}
color.setRgb(r, g, b);
return color;
}

A noter que cet algorithme devrait également fonctionner dans d’autres espaces de couleur que RGB (en CMY, cyan/magenta/jaune, notamment).

DependencyWalker, explorer les dépendances d’une application

17 octobre 2011

Bien souvent, lorsque l’on développer une application, tout se passe bien jusqu’au moment ou l’on souhaite la faire fonctionner sur une autre machine. Bien souvent, lors de cette étape, on fait le douloureux constat que l’application ne démarre même bien, en général, on obtient juste un message indiquant qu’il y a un problème et que l’application ne peut démarrer, avec pour seule suggestion de remède une réinstallation, ce qui bien sur est inutile.

Dans la plupart des cas, on est face à un problème de dépendances avec des bibliothèques présentes sur la machine de développement (installées au bon endroit lors de l’installation des outils de développement), et absentes des systèmes « classiques ».

Il est parfois aisé de savoir quelles sont les librairies utilisées, en fonction des SDK et autres Framwork utilisés, mais parfois, ça n’est pas si simple.

Dans ces cas, il existe des logiciels capables d’analyser un fichier binaire pour en retirer les dépendances. Dependency Walker fait parti de ceux-ci.

Fenêtre principale de Dependency Walker

Fenêtre principale de Dependency Walker

La simple ouverture d’un exécutable dans ce logiciel vous permettra de voir instantanément de quelles DLL à besoin le logiciel pour fonctionner. Une simple recherche sur la machine de dev devrait vous permettre de mettre la main sur la DLL manquante afin de la joindre à votre programme pour que tout rentre dans l’ordre.

Un certain travail de tri et de sélection des informations restera cependant nécessaire car comme le montre la capture ci-dessus, l’intégralité des DLL et dépendances sont affichées, il faudra donc différencier les DLL systèmes (toujours présentes sous Windows et qu’il ne sera donc pas nécessaire d’importer) des DLL applicatives qu’il faudra fournir.

InnoSetup : ajouter les DLL Visual C++

14 octobre 2011

Si vous développez à l’aide de Microsoft Visual Studio, vos programmes nécessitent, pour fonctionner sur une machine quelconque, de diposer des bibliothèques suivantes (DLL de VC++ 2008) :

  • mfc90.dll
  • msvcr90.dll
  • msvcp90.dll
  • atl90.dll
  • vcomp.dll
L’absence des ces librairies est un cas fréquent de non fonctionnement des programmes développés par vos soins, le syptôme est alors l’apparition d’un message du type : « Cette application n’a pas pu démarrer car la configuration de l’application est incorrecte. Réinstaller l’application pourrait résoudre ce problème.« .

 

La solution est d’installer le package de DLL « Microsoft Visual C++ 2008 Redistribuable Package » (téléchargeable sur le site de Microsoft : vcredist_x86.exe ou vcredist_x64.exe pour la version 64 bits).
Mais voila, si vous distribuez vos applications avec un installeur comme Inno Setup, cela impose à vos utilisateurs de télécharger ce package de DLL en sus, avec le risque qu’ils passent à coté et qu’il ne parviennent donc pas à lancer votre application.
La solution la plus simple est donc d’intégrer vcredist dans l’installeur InnoSetup de façon à ce que son installation soit automatique et transparente pour vos utilisateurs. Voici comment procéder :
  1. Téléchargez vcredist_x86.exe sur le site de Microsoft (voir lien plus haut) et enregistrez le dans un sous dossier ./bin/ de votre projet
  2. Ouvrez votre projet Inno Setup (je suppose ici que celui-ci est d’hors et déjà créé et que l’emplacement des autres fichiers de votre projet sont déjà renseignés)
  3. Dans la section [files] de votre projet, ajoutez ceci :
    Source: "{src}binvcredist_x86.exe"; DestDir: "{app}bin"; Flags: deleteafterinstall
  4. Dans la section [Run], ajoutez :
    Filename: "{app}binvcredist_x86.exe"; Parameters: "/q:a /c:""VCREDI~3.EXE /q:a /c:""""msiexec /i vcredist.msi /qn"""" """; WorkingDir: "{app}bin"; StatusMsg: Installing VCREDIST...
Il faudra bien sur adapter ces commandes si vous intégrez la version 64 bits.
Vous devriez également pouvoir inclure les 2 versions (32 et 64 bits) en jouant avec les options et conditions disponibles dans InnoSetup.

 

Grâce à cette technique, l’installation se fera de façon totallement transparente, l’utilisateur n’ayant même pas besoin de valider les différentes étapes de l’installer du package Visual Studio VC++ Redistribuable (il voit juste une barre de progression qui se remplit sans poser de questions).

 

Note : ce billet traite plus particulièrement de la version 2008 de Visual Studio (celle que j’utilise), mais cette astuce est transposable telle qu’elle pour les autres versions de VS (je pense notamment aux versions 2005 et 2010), il suffit de télécharger les pack vcredist correspondants à ces versions sur le site de Microsoft.