Présentation, description et utilisation des variables d'environnement sous Windows.
Date de publication : 8/11/2003
Par
Pierre Castelain
Présentation, description et utilisation des variables d'environnement sous
Windows. A l'article est associée une unité Delphi permettant une
manipulation aisée de celles-ci.
1. Remerciements
2. Préambule
3. Présentation
4. Variables d'environnement fournies par Windows
5. Implémentation
6. Modifier les variables d'environnement
7. Variables système et utilisateur
8. Emplacements dans la base de registre (Windows NT uniquement)
9. Manipuler les variables d'environnement par programme
10. Code Delphi
1. Remerciements
Je tiens à remercier tous particulièrement les personnes suivantes pour leur aide précieuse lors de la rédaction et de la relecture de cet article :
2. Préambule
Cet article est un document de synthèse dont le but est de fournir un
maximum d'information concernant l'utilisation des variables
d'environnement sous Windows. Il n'a pas la prétention d'être
exhaustif mais devrait permettre aux développeurs d'avoir une vision
relativement complète de ce système.
Le but recherché n'est pas d'encourager le lecteur à utiliser ce
mécanisme vieillissant mais plutôt de servir de référence afin d'aider
les développeurs devant manipuler des variables d'environnement dans
le cadre de développement compatibles avec l'applicatif existant.
3. Présentation
Les variables d'environnement, présentes depuis les premières versions
de DOS, permettent de véhiculer simplement de l'information entre
plusieurs programmes. De nos jours, celles-ci sont de moins en moins
utilisées et remplacées par la base de registre. Elles restent tout de
même pratiques et sont encore utilisées par les systèmes d'exploitation
modernes.
On peut considérer une variable d'environnement comme une variable
globale au système. Chaque application, programme ou service peut lire
ou modifier la valeur d'une de ces variables sous certaines conditions
que nous verrons un peu plus loin.
Windows propose un certain nombre de ces variables qui permettent aux
applications d'obtenir des informations sur la configuration du système.
Par exemple les variables TMP ou TEMP fournissent le
chemin du dossier temporaire de Windows et la variable PATH
indique à Windows où aller chercher les programmes lancés depuis
l'invite de commande et les DLL nécessaires aux applications.
Pour que plusieurs applications puissent partager une information sous
forme de variable d'environnement, il suffit que celles-ci connaissent
le nom de la variable pour pouvoir y accéder. C'est donc un système
très simple.
Prenons un exemple afin d'illustrer ce mécanisme. Imaginons deux
applications manipulant un même fichier de données. La première
application permet de saisir des données dans le fichier et la seconde
permet d'afficher ces données. Ces deux application peuvent utiliser une
variable que nous appellerons par exemple CHEMIN_DONNEES pour
stocker le chemin d'accès au fichier. Ces applications peuvent donc être
installées n'importe où sur le disque, il leur suffit de lire la valeur
stockée dans la variable CHEMIN_DONNEES pour connaître le nom du
fichier à utiliser. De même, le déplacement de ce fichier est possible
et ne nécessite que la modification de la valeur de la variable.
4. Variables d'environnement fournies par Windows
Il existe quelques variables fournies par le système d'exploitation. En
voici une liste non-exhaustive classée par type de système. La casse des
variables n'a aucune importance. Les noms des variables sont indiqués
tels qu'ils apparaissent sous les systèmes utilisés par l'auteur.
Variables communes à la plupart des versions de Windows :
-
TMP et TEMP : répertoire temporaire de Windows.
-
PROMPT : Invite affichée par l'invite de commandes.
-
Winbootdir : répertoire de démarrage de Windows.
-
COMSPEC : nom du programme d'invite de commande.
-
PATH : chemins de recherche des programmes et DLL (séparés par des points virgules).
-
Windir : répertoire de Windows.
Variables disponibles sous Windows NT et 2000 :
- COMPUTERNAME : nom de l'ordinateur.
- HOMEDRIVE : disque local primaire (partition système).
- HOMEPATH : dossier par défaut pour les utilisateurs.
- LOGONSERVER : nom du serveur de domaine.
- NUMBER_OF_PROCESSORS : nombre de processeurs installés.
- OS : nom du système d'exploitation.
- Os2LibPath : chemin de la bibliothèque Microsoft OS/2.
- PATHEXT : liste des extensions de fichier reconnus comme des exécutables.
- PROCESSOR_ARCHITECTURE : type de processeur installé.
- PROCESSOR_IDENTIFIER : identification du processeur installé (type, modèle, etc.).
- PROCESSOR_LEVEL : niveau du processeur.
- PROCESSOR_REVISION : révision du processeur.
- SystemDrive : disque local sur lequel le système réside.
- SystemRoot : chemin du système (égal à Windir).
- USERDOMAIN : nom du domaine sous lequel l'utilisateur s'est connecté.
- USERNAME : nom de l'utilisateur courant.
- USERPROFILE : chemin du profil de l'utilisateur courant.
Variables disponibles sous Windows 2000 :
- ALLUSERSPROFILE : chemin du profil commun à tous les utilisateurs.
- APPDATA : chemin des données applicatives de l'utilisateur courant.
- CommonProgramFiles : chemin des programmes communs.
- ProgramFiles : chemin des programmes.
5. Implémentation
Les variables d'environnement sont stockées sous la forme d'un bloc
d'environnement dans chaque processus en cours d'exécution. Sous
Windows, chaque processus possède donc un bloc de données contenant un
ensemble de variables et leur valeur. Ce bloc est constitué d'un vecteur
de chaînes de caractères C (à zéro terminal) sous la forme
"Nom_de_la_variable=Valeur_de_la_variable" et terminé par un zéro (il y
a donc deux caractères zéro à la fin du bloc). Un de ces blocs peut donc
se présenter ainsi :
TEMP=%USERPROFILE%\Local Settings\Temp#0
TMP=%USERPROFILE%\Local Settings\Temp#0
#0
Note : #0 représente ici le caractère de code ANSI égal à zéro. Les
retours à la ligne ont été ajoutés pour améliorer la lisibilité, en
réalité ils n'existent pas.
Par défaut, un processus enfant hérite du bloc d'environnement de son
processus parent sous la forme d'une copie de celui-ci. Le processus
enfant hérite donc de toutes les variables d'environnement de ses
processus ancêtres. Il est cependant possible de fournir un nouveau
bloc d'environnement en créant celui-ci et en passant son adresse à la
fonction CreateProcess.
Ce mécanisme permet d'offrir l'accès à ces variables depuis toutes les
applications sans risque de collision puisque chaque processus travaille
sur sa propre copie de l'environnement.
Pour bien comprendre ce mécanisme, je vous propose un petit exercice.
-
Ouvrez une invite de commandes (Menu Démarrer, Exécuter, tapez "CMD"
sous Windows NT ou "COMMAND" sous 9x).
-
Nous allons utiliser la commande SET qui permet d'afficher et de
modifier la valeur de chaque variable.
-
Tapez la commande "SET DV=DEVELOPPEZ.COM"
-
Nous venons de créer une nouvelle variable nommée DV dont la
valeur est "DEVELOPPEZ.COM".
-
Tapez la commande "SET" pour afficher la liste des variables ainsi que
leurs valeurs respectives.
-
Vous pouvez également taper la commande "ECHO %DV%" pour afficher la
valeur de la variable DV (les caractères % permettent de
spécifier à l'invite de commandes qu'il s'agit d'une variable
d'environnement dont nous voulons obtenir la valeur).
-
Ne fermez pas l'invite de commande actuelle et ouvrez-en une seconde.
-
Tapez la commande "SET" pour obtenir la liste des variables.
-
Vous pouvez constater que la variable DV n'existe pas dans cet
environnement, celui-ci étant directement hérité de l'environnement
principal de Windows et non de l'environnement de la première invite
de commandes.
-
Fermez cette invite de commande et retournez sur la première.
-
Tapez la commande "CMD" (ou "COMMAND" si vous êtes sous Windows 9x)
pour créer une nouvelle invite de commande (attention, celle-ci
n'ouvre pas de nouvelle fenêtre).
-
Utilisez la commande "SET" pour vérifier la présence de la variable
DV.
-
Vous pouvez donc constater que cette nouvelle invite a hérité de
l'environnement de la première. Ce processus à bien hérité
l'environnement du processus parent.
-
Utilisez deux fois la commande "EXIT" pour fermer les deux invites.
6. Modifier les variables d'environnement
La modification "manuelle" des variables d'environnement se fait
différemment selon la version de Windows utilisée.
Les versions 9x de Windows (95, 98 et Millenium) utilisent le fichier
autoexec.bat situé à la racine de la partition de démarrage
(habituellement C: ). Ce fichier qui est lu au démarrage de Windows
(ou plutôt du DOS) contient entre autres une suite de commandes SET
définissant les variables. Il est donc nécessaire de redémarrer Windows
lorsque l'on modifie une ou plusieurs de ces variables et que l'on
désire que l'ensemble des applications en tiennent compte. La taille du
bloc d'environnement n'est pas illimité sous ces versions de Windows et
le système ne génère malheureusement aucun message d'erreur (en dehors
de la console) lors du dépassement de la capacité de ce bloc. Il est
toutefois possible de modifier la taille du bloc en modifiant le fichier
system.ini situé dans le dossier de Windows. Il suffit d'ajouter la
ligne CommandEnvSize=Taille en octets dans la section [NonWindowsApp].
Par exemple pour un bloc de 4ko :
[NonWindowsApp]
CommandEnvSize=4096
Les versions NT de Windows (NT 4, 2000 et XP) stockent les variables
dans la base de registre et permettent la modification de celles-ci via
l'icône "Système" du panneau de configuration (onglet "Environnement" ou
"Avancé" selon les versions). Contrairement à Windows 9X, la prise en
compte des modifications est immédiate (elle nécessite tout de même
quelques secondes) et valable pour toutes les applications qui seront
démarrées après les modifications. De rares applications sont capables
de détecter que l'environnement a été modifié et rechargent celui-ci
sans avoir besoin d'être relancées (en particulier le shell).
7. Variables système et utilisateur
Sous Windows NT, les variables d'environnement sont séparées en deux
groupes distincts, les variables dites "système" et les variables dites
"utilisateur". Cette distinction est en fait relativement simple. Les
variables système sont communes à tous les utilisateurs d'un même
ordinateur, elles sont valables pour la machine alors que les variables
utilisateur ne sont valables que pour un seul utilisateur de cette
machine. Il est possible qu'une même variable apparaisse donc deux fois
avec une valeur différente dans chaque groupe. Dans ce cas, c'est la
variable utilisateur qui est prise en compte.
8. Emplacements dans la base de registre (Windows NT uniquement)
Les variables d'environnement sont enregistrées sous la forme d'une
liste de valeurs situées dans certaines clés précises du registre. Le
nom de la valeur correspond au nom de la variable d'environnement et le
contenu de la valeur à la valeur de la variable d'environnement.
Le contenu de ces valeurs est de type chaîne (REG_SZ) ou de type chaîne
"extensible" (REG_EXPAND_SZ) dans le cas ou le contenu de la valeur
contient une référence à une autre variable d'environnement. Par exemple
la variable TEMP est généralement définie comme ayant la valeur
"%USERPROFILE%\Local Settings\Temp". Cette variable peut ainsi être
définie de manière globale tout en étant spécifique à chaque utilisateur
(la variable USERPROFILE contenant le nom de l'utilisateur). Ces
valeurs ne peuvent être manipulées avec l'éditeur de registre RegEdit,
il faut utiliser RegEdt32 pour pouvoir le faire.
-
Les variables utilisateur sont stockées sous la clé :
HKEY_CURRENT_USER\Environment
-
Les variables système sont stockées sous la clé :
HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Session Manager\Environment
-
Il existe un troisième emplacement qui est généralement très mal
compris. Il s'agit de la clé :
HKEY_USERS\.DEFAULT\Environment
Cet emplacement ne définit pas les variables d'environnement par défaut
fournies à chaque nouvel utilisateur mais plutôt les variables
disponibles quand aucun utilisateur n'est connecté, c'est à dire quand
Windows présente l'invite de connexion. Si vous voulez spécifier des
variables utilisateur qui seront définies à chaque création
d'utilisateur, il vous faut créer un profil et le copier dans le
profil par défaut. Cette manipulation dépasse le cadre de cet article,
vous trouverez facilement la marche à suivre sur de nombreux sites et
forums.
Attention, la modification des variables d'environnement
réalisée directement dans la base de registre n'est pas prise en
compte directement par le système. Il faut que celui-ci soit informé
de cette modification par un message WM_SETTINGCHANGE comme
nous le verrons un peu plus loin.
9. Manipuler les variables d'environnement par programme
L'API Windows propose quelques fonctions pour manipuler les variables
d'environnement. Ces fonctions sont exclusivement prévues pour manipuler
l'environnement courant du processus courant. La modification globale
des variables ne peut se faire que par l'intermédiaire de la base de
registre (ou du fichier autoexec.bat pour les versions 9x de Windows).
-
GetEnvironmentVariable : Cette fonction permet d'obtenir la
valeur d'une variable de l'environnement du processus courant si elle
existe. Dans le cas contraire, la fonction retourne zéro et la
fonction
GetLastError retourne ERROR_ENVVAR_NOT_FOUND.
-
SetEnvironmentVariable : Cette fonction permet d'ajouter, de
modifier ou de supprimer une variable de l'environnement du processus
courant. Si la valeur passée est nulle, la variable est supprimée,
sinon la variable est modifiée dans le cas où elle existe déjà et
créée dans le cas où elle n'existe pas.
Attention, comme nous l'avons déjà vu, ces modifications ne sont
valables que pour l'environnement du processus courant (en général
l'application) et par héritage pour l'environnement des processus
enfants du processus courant.
-
GetEnvironmentStrings : Cette fonction permet d'obtenir la
liste complète des variables de l'environnement du processus courant.
Cette liste est fournie sous la forme d'un vecteur de chaînes de
caractères à zéro terminal (chaînes C), lui-même terminé par un zéro.
La fonction retourne l'adresse du bloc de mémoire contenant ces
informations. Il est strictement interdit de modifier ce bloc de
mémoire. Pour modifier les variables, utilisez la fonction
SetEnvironmentVariable.
Une fois que vous n'avez plus besoin de ce bloc de mémoire, utilisez
la fonction
FreeEnvironmentStrings pour le libérer.
-
FreeEnvironmentStrings : Cette fonction libère un bloc
d'environnement fourni par
GetEnvironmentStrings.
-
CreateProcess : Il est possible de modifier le bloc
d'environnement d'un processus lancé par la fonction
CreateProcess. Le paramètre lpEnvironment permet de
spécifier l'adresse d'un bloc d'environnement que vous aurez
préalablement créé et rempli. Si cette adresse n'est pas fournie,
la fonction
CreateProcess utilise l'environnement du processus courant.
-
WM_SETTINGCHANGE : Ce message permet d'informer les processus
en cours d'exécution de la modification des variables d'environnement
(entre autres). Il doit être envoyé à l'aide des fonctions
SendMessageTimeOut ou
BroadcastSystemMessage et le paramètre LParam doit
contenir la chaîne 'Environment'.
L'utilisation d'un temps mort (time out) permet d'attendre
l'acquittement des applications traitant ce message tout en évitant
de bloquer le système lorsque certaines applications ne traitent pas
celui-ci.
10. Code Delphi
Ce paragraphe présente une unité Delphi proposant des fonctions
simplifiant l'utilisation des API Windows pour la manipulation des
variables d'environnement.
Attention, les fonctions agissant sur les variables système, utilisateur
et par défaut ainsi que la fonction BroadcastEnvironmentChange ne
sont valables que sous Windows NT.
Les source de cette unité est également disponible dans une
fichier archive au format zip. Ce fichier peut être téléchargé en cliquant
sur le lien suivant :
Environment.zip
unit Environment;
interface
uses
Classes;
function GetCurrentProcessEnvVar(const VariableName: string): string;
procedure SetCurrentProcessEnvVar(const VariableName, VariableValue: string);
procedure DeleteCurrentProcessEnvVar(const VariableName: string);
procedure ReadCurrentProcessEnvVars(Vars: TStrings);
function BuildEnvironmentBlock(Vars: TStrings; Buffer: PAnsiChar;
var Len: Longword): LongWord;
procedure ReadSystemEnvVars(Vars: TStrings);
procedure ReadUserEnvVars(Vars: TStrings);
procedure ReadDefaultEnvVars(Vars: TStrings);
procedure SetSystemEnvVar(const VariableName, VariableValue: string;
const BroadcastChange: boolean);
procedure DeleteSystemEnvVar(const VariableName: string;
const BroadCastChange: boolean);
procedure SetUserEnvVar(const VariableName, VariableValue: string;
const BroadcastChange: boolean);
procedure DeleteUserEnvVar(const VariableName: string;
const BroadcastChange: boolean);
procedure SetDefaultEnvVar(const VariableName, VariableValue: string;
const BroadcastChange: boolean);
procedure DeleteDefaultEnvVar(const VariableName: string;
const BroadcastChange: boolean);
procedure BroadcastEnvironmentChange(TimeOut: Cardinal = 2000);
implementation
uses
Windows, SysUtils, Registry, Messages;
function GetCurrentProcessEnvVar(const VariableName: string): string;
var
nSize: DWord;
begin
nSize:= 0;
nSize:= GetEnvironmentVariable(PChar(VariableName), nil, nSize);
if nSize = 0 then
result:= ''
else
begin
SetLength(result, nSize - 1);
if GetEnvironmentVariable(PChar(VariableName), PChar(result), nSize) <> nSize - 1 then
raise Exception.Create(SysErrorMessage(GetlastError))
end;
end;
procedure SetCurrentProcessEnvVar(const VariableName, VariableValue: string);
begin
SetEnvironmentVariable(PChar(VariableName), PChar(VariableValue));
end;
procedure DeleteCurrentProcessEnvVar(const VariableName: string);
begin
SetCurrentProcessEnvVar(VariableName, '');
end;
procedure ReadEnvironmentBlock(const Block: PAnsiChar; Vars: TStrings);
var
i: Integer;
s: string;
begin
Vars.Clear;
i:= 0;
while Block[i] <> #0 do
begin
s:= '';
while Block[i] <> #0 do
begin
s:= s + Block[i];
Inc(i);
end;
Vars.Add(s);
Inc(i);
end;
end;
procedure ReadCurrentProcessEnvVars(Vars: TStrings);
var
block: PAnsiChar;
begin
block:= GetEnvironmentStrings;
try
ReadEnvironmentBlock(block, Vars);
finally
FreeEnvironmentStrings(block);
end;
end;
function BuildEnvironmentBlock(Vars: TStrings; Buffer: PAnsiChar;
var Len: Longword): LongWord;
var
line, i: Integer;
p, l: LongWord;
begin
p:= 0;
l:= p;
for line:= 0 to Vars.Count - 1 do
begin
for i:= 1 to Length(Vars[line]) do
begin
if p < Len then
begin
Buffer[p]:= Vars[line][i];
Inc(l);
end;
Inc(p);
end;
if p < Len then
begin
Buffer[p]:= #0;
Inc(l);
end;
Inc(p);
end;
if p < Len then
begin
Buffer[p]:= #0;
Inc(l);
end;
result:= l;
Len:= p;
end;
procedure ReadSystemEnvVars(Vars: TStrings);
var
i: Integer;
begin
Vars.Clear;
with TRegistry.Create do
try
Access:= KEY_READ;
RootKey:= HKEY_LOCAL_MACHINE;
if OpenKey('SYSTEM\CurrentControlSet\Control\Session Manager\Environment',
false) then
begin
GetValueNames(Vars);
for i:= Vars.Count - 1 downto 0 do
try
Vars[i]:= Vars[i] + '=' + ReadString(Vars[i]);
except
Vars.Delete(i);
end;
CloseKey;
end
else
raise Exception.Create('Impossible d''ouvrir la clé.');
finally
Free;
end;
end;
procedure ReadUserEnvVars(Vars: TStrings);
var
i: Integer;
begin
Vars.Clear;
with TRegistry.Create do
try
Access:= KEY_READ;
RootKey:= HKEY_CURRENT_USER;
if OpenKey('Environment', false) then
begin
GetValueNames(Vars);
for i:= Vars.Count - 1 downto 0 do
try
Vars[i]:= Vars[i] + '=' + ReadString(Vars[i]);
except
Vars.Delete(i);
end;
CloseKey;
end
else
raise Exception.Create('Impossible d''ouvrir la clé.');
finally
Free;
end;
end;
procedure ReadDefaultEnvVars(Vars: TStrings);
var
i: Integer;
begin
Vars.Clear;
with TRegistry.Create do
try
Access:= KEY_READ;
RootKey:= HKEY_USERS;
if OpenKey('.DEFAULT\Environment', false) then
begin
GetValueNames(Vars);
for i:= Vars.Count - 1 downto 0 do
try
Vars[i]:= Vars[i] + '=' + ReadString(Vars[i]);
except
Vars.Delete(i);
end;
CloseKey;
end
else
raise Exception.Create('Impossible d''ouvrir la clé.');
finally
Free;
end;
end;
procedure SetSystemEnvVar(const VariableName, VariableValue: string;
const BroadcastChange: boolean);
begin
with TRegistry.Create do
try
Access:= KEY_WRITE;
RootKey:= HKEY_LOCAL_MACHINE;
if OpenKey('SYSTEM\CurrentControlSet\Control\Session Manager\Environment',
false) then
begin
if (VariableValue = '') then
DeleteValue(VariableName)
else
WriteString(VariableName, VariableValue);
if BroadcastChange then
BroadcastEnvironmentChange;
end;
finally
Free;
end;
end;
procedure SetUserEnvVar(const VariableName, VariableValue: string;
const BroadcastChange: boolean);
begin
with TRegistry.Create do
try
Access:= KEY_WRITE;
RootKey:= HKEY_CURRENT_USER;
if OpenKey('Environment', false) then
begin
if (VariableValue = '') then
DeleteValue(VariableName)
else
WriteString(VariableName, VariableValue);
if BroadcastChange then
BroadcastEnvironmentChange;
end;
finally
Free;
end;
end;
procedure SetDefaultEnvVar(const VariableName, VariableValue: string;
const BroadcastChange: boolean);
begin
with TRegistry.Create do
try
Access:= KEY_WRITE;
RootKey:= HKEY_USERS;
if OpenKey('.DEFAULT\Environment', false) then
begin
if (VariableValue = '') then
DeleteValue(VariableName)
else
WriteString(VariableName, VariableValue);
if BroadcastChange then
BroadcastEnvironmentChange;
end;
finally
Free;
end;
end;
procedure BroadcastEnvironmentChange(TimeOut: Cardinal = 2000);
var
lParam: PChar;
dwResult: Cardinal;
begin
lParam:= 'Environment';
SendMessageTimeOut(HWND_BROADCAST, WM_SETTINGCHANGE, 0,
Integer(lParam), SMTO_NORMAL , TimeOut, dwResult);
if dwResult <> 0 then
raise Exception.Create(SysErrorMessage(dwResult));
end;
procedure DeleteSystemEnvVar(const VariableName: string;
const BroadCastChange: boolean);
begin
SetSystemEnvVar(VariableName, '', BroadCastChange);
end;
procedure DeleteUserEnvVar(const VariableName: string;
const BroadCastChange: boolean);
begin
SetUserEnvVar(VariableName, '', BroadCastChange);
end;
procedure DeleteDefaultEnvVar(const VariableName: string;
const BroadCastChange: boolean);
begin
SetDefaultEnvVar(VariableName, '', BroadCastChange);
end;
end.
| Articles | |
Delphi 2005 : Découvrez le futur Delphi 2005
| |
DirectX : Introduction à DirectX 9 en Delphi
| |
Variables d'environnement : Présentation, description et utilisation des variables d'environnement sous Windows
| |
Mailslots : Présentation des mailslots et de leur utilisation en Delphi pour la communication inter-processus
| | Projets complets avec sources | |
NumericalParser : Parser numérique en Delphi afin de transformer une chaîne de caractères en
valeur flottante ou entière.
| |
RegSearch : Composant de recherche dans la base de registre
| |
CDAReader : Lecture des informations contenues dans les fichier CDA de Windows
| |
ScreenSaverPreview : Composant d'affichage de l'aperçu des économiseurs d'écran de Windows
| |
ScanResources : Programme d'exploration des ressources des programmes ou des dll d'un répertoire
| |
ClipboardViewer : Démonstration de la détection des modifications et de l'affichage du contenu du presse-papier
| |
Matrix : Tentative de reproduction en Delphi de l'animation bien connue du film Matrix
| | Sources et exemples | |
EMFTransform : Transformation (rotation, inversion, miroir) d'un metafile Windows en mémoire
| |
DeleteKeyTree : Suppression récursive d'un clé de la base de registre
| |
MultiStrings : Routines de gestion de tableaux de chaînes C
| |
GetDllFilename : Pour récupérer le chemin d'une dll par son handle
| |
Extension du shell : Exemple d'extension du menu contextuel du shell de Windows
| |
TriStringGrid : Exemple de tri par colonne d'un composant TStringGrid à l'aide d'un algorithme
de tri rapide (quick sort)
| |
XPManifestCPL : Utilisation des contrôles XP dans une application du panneau de configuration (cpl)
| |
Bouboules : Modélisation à l'aide du design pattern Observer
| | Divers | |
Diagramme ternaire : Un logiciel gratuit de tracé de diagramme ternaire
|
|
|