//Advanced Delphi Systems Code: ads_Globals
unit ads_Globals;
{Copyright(c)2016 Advanced Delphi Systems

 Richard Maley
 Advanced Delphi Systems
 12613 Maidens Bower Drive
 Potomac, MD 20854 USA
 phone 301-840-1554
 dickmaley@advdelphisys.com

 The code herein can be used or modified by anyone.  Please retain references
 to Richard Maley at Advanced Delphi Systems.  If you make improvements to the
 code please send your improvements to dickmaley@advdelphisys.com so that the
 entire Delphi community can benefit.  All comments are welcome.
}

(*
UnitIndex Master Index Implementation Section Download Units
Description: ads_Globals.pas
This unit contains the following routines.

PathOfAppDataCommon   PathOfAppDataLocal   PathOfHistory   PathOfInternetCache   PathOfInternetCookies   PathOfMyDocuments   PathOfMyPictures   PathOfProgramFiles   PathOfProgramFilesCommon  PathOfSpecialFolder   PathOfSystem32   PathOfWindows   UpdateIniFromVar_1   UpdateIniFromVar_2   UpdateIniFromVar_3   UpdateVarFromIni_1   UpdateVarFromIni_2   UpdateVarFromIni_3  

*)
interface
Uses
  Classes, SysUtils, dialogs;
Var
  boDirDB              : Boolean = False;
  boDirDest            : Boolean = False;
  boDirHelp            : Boolean = False;
  boDirImages          : Boolean = False;
  boDirPersist         : Boolean = False;
  boDirReports         : Boolean = False;
  boDirResources       : Boolean = False;
  boDirScripts         : Boolean = False;
  boDirSource          : Boolean = False;
  boDirTemp            : Boolean = False;
  boDirWorking         : Boolean = False;
  DirAppDataCommon     : String  = '';
  DirAppDataLocal      : String  = '';
  DirCommonFiles       : String  = '';
  DirDB                : String  = '';
  DirDest              : String  = '';
  DirHelp              : String  = '';
  DirHistory           : String  = '';
  DirImages            : String  = '';
  DirInternetCache     : String  = '';
  DirInternetCookies   : String  = '';
  DirMyDocuments       : String  = '';
  DirMyPictures        : String  = '';
  DirPersist           : String  = '';
  DirProgFiles         : String  = '';
  DirProgramFiles      : String  = '';
  DirProgramFilesCommon: String  = '';
  DirReports           : String  = '';
  DirResources         : String  = '';
  DirScripts           : String  = '';
  DirSource            : String  = '';
  DirSystem32          : String  = '';
  DirTemp              : String  = '';
  DirWindows           : String  = '';
  DirWorking           : String  = '';
  ExeName              : String  = '';
  ExePath              : String  = '';
  FileIni              : String  = '';
  FileLast             : String  = '';
  IniData              : TStringList;

Function UpdateIniFromVar(var v: Boolean; VarName: String;ini: TStringList): String; OverLoad;
Function UpdateIniFromVar(var v: Integer; VarName: String;ini: TStringList): String; OverLoad;
Function UpdateIniFromVar(var v: String ; VarName: String;ini: TStringList): String; OverLoad;
Function UpdateVarFromIni(var v: Boolean; VarName: String;ini: TStringList): String; OverLoad;
Function UpdateVarFromIni(var v: Integer; VarName: String;ini: TStringList): String; OverLoad;
Function UpdateVarFromIni(var v: String ; VarName: String;ini: TStringList): String; OverLoad;

implementation

Uses
  ActiveX,
  Forms,
  ShlObj,
  Windows
  ;

//
Unit Description UnitIndex Master Index
Function PathOfSpecialFolder(Folder: Integer): String;
Var
  ppidl      : PItemIdList;
  shellMalloc: IMalloc;
begin
  ppidl := nil;
  try
    If SHGetMalloc(shellMalloc) = NOERROR Then
    Begin
      SHGetSpecialFolderLocation(Application.Handle, Folder, ppidl);
      SetLength(Result, MAX_PATH);
      {$WARNINGS OFF}
      If Not SHGetPathFromIDList(ppidl, PChar(Result)) Then
      {$WARNINGS ON}
        Raise exception.create('SHGetPathFromIDList failed : invalid pidl');
      {$WARNINGS OFF}
      SetLength(Result, lStrLen(PChar(Result)));
      {$WARNINGS ON}
      If Result<>'' Then
      Begin
        If Copy(Result,Length(Result),1)<>'\' Then
          Result:=Result+'\';
      End;
    End;
  Finally
   If ppidl <> nil Then shellMalloc.free(ppidl);
  End;
End;

//
Unit Description UnitIndex Master Index
Function PathOfAppDataCommon()     :String;Begin Result:=PathOfSpecialFolder(35);End;
//
Unit Description UnitIndex Master Index
Function PathOfAppDataLocal()      :String;Begin Result:=PathOfSpecialFolder(28);End;
//
Unit Description UnitIndex Master Index
Function PathOfHistory()           :String;Begin Result:=PathOfSpecialFolder(34);End;
//
Unit Description UnitIndex Master Index
Function PathOfInternetCache()     :String;Begin Result:=PathOfSpecialFolder(32);End;
//
Unit Description UnitIndex Master Index
Function PathOfInternetCookies()   :String;Begin Result:=PathOfSpecialFolder(33);End;
//
Unit Description UnitIndex Master Index
Function PathOfMyDocuments()       :String;Begin Result:=PathOfSpecialFolder(5);End;
//
Unit Description UnitIndex Master Index
Function PathOfMyPictures()        :String;Begin Result:=PathOfSpecialFolder(39);End;
//
Unit Description UnitIndex Master Index
Function PathOfProgramFiles()      :String;Begin Result:=PathOfSpecialFolder(38);End;
//
Unit Description UnitIndex Master Index
Function PathOfProgramFilesCommon():String;Begin Result:=PathOfSpecialFolder(43);End;
//
Unit Description UnitIndex Master Index
Function PathOfSystem32()          :String;Begin Result:=PathOfSpecialFolder(37);End;
//
Unit Description UnitIndex Master Index
Function PathOfWindows()           :String;Begin Result:=PathOfSpecialFolder(36);End;

//
Unit Description UnitIndex Master Index
Function UpdateVarFromIni(var v: String; VarName: String;ini: TStringList): String; OverLoad;
Var
  sgTemp: String;
Begin
  Result:='';
  VarName:=Trim(VarName);
  If VarName='' Then Exit;
  If ini=nil Then Exit;
  If ini.Values[VarName]<>'' Then v:=ini.Values[VarName];
  sgTemp:=Trim(v);
  ini.Values[VarName]:=sgTemp;
  If sgTemp='' Then
  Begin
    //Empty values are not stored in the ini normally.
    //However, I want the variable name in the ini so that
    //a reader of the ini can see what varibles are controllable.
    ini.Add(VarName+'=');
    ini.Sort();
  End;
  ini.SaveToFile(FileIni);
  Result:=ini.Values[VarName];
End;

//
Unit Description UnitIndex Master Index
Function UpdateVarFromIni(var v: Integer; VarName: String;ini: TStringList): String; OverLoad;
Var
  sgTemp: String;
Begin
  Result:='';
  VarName:=Trim(VarName);
  If VarName='' Then Exit;
  If ini=nil Then Exit;
  If ini.Values[VarName]<>'' Then v:=StrToInt(ini.Values[VarName]);
  sgTemp:=Trim(IntToStr(v));
  ini.Values[VarName]:=sgTemp;
  If sgTemp='' Then
  Begin
    //Empty values are not stored in the ini normally.
    //However, I want the variable name in the ini so that
    //a reader of the ini can see what varibles are controllable.
    ini.Add(VarName+'=');
    ini.Sort();
  End;
  ini.SaveToFile(FileIni);
  Result:=ini.Values[VarName];
End;

//
Unit Description UnitIndex Master Index
Function UpdateVarFromIni(var v: Boolean; VarName: String;ini: TStringList): String; OverLoad;
Var
  sgTemp: String;
Begin
  Result :='';
  VarName:=Trim(VarName);
  If VarName='' Then Exit;
  If ini=nil Then Exit;
  If ini.Values[VarName]<>'' Then v:=(ini.Values[VarName]='TRUE');
  If v Then sgTemp:='TRUE' Else sgTemp:='FALSE';
  ini.Values[VarName]:=sgTemp;
  ini.Sort();
  ini.SaveToFile(FileIni);
  Result:=ini.Values[VarName];
End;

//
Unit Description UnitIndex Master Index
Function UpdateIniFromVar(var v: String ; VarName: String;ini: TStringList): String; OverLoad;
Begin
  ini.Values[VarName]:=v;
  If Trim(v)='' Then ini.Add(VarName+'=');
  ini.Sort();
  ini.SaveToFile(FileIni);
  Result:=ini.Values[VarName];
End;

//
Unit Description UnitIndex Master Index
Function UpdateIniFromVar(var v: Integer; VarName: String;ini: TStringList): String; OverLoad;
Begin
  ini.Values[VarName]:=IntToStr(v);
  ini.Sort();
  ini.SaveToFile(FileIni);
  Result:=ini.Values[VarName];
End;

//
Unit Description UnitIndex Master Index
Function UpdateIniFromVar(var v: Boolean; VarName: String;ini: TStringList): String; OverLoad;
Var
  sgBool: String;
Begin
  If v Then sgBool:='TRUE' Else sgBool:='FALSE';
  ini.Values[VarName]:=sgBool;
  ini.Sort();
  ini.SaveToFile(FileIni);
  Result:=ini.Values[VarName];
End;

Initialization
  FileLast             := '';
  DirAppDataCommon     := PathOfAppDataCommon();
  DirAppDataLocal      := PathOfAppDataLocal();
  DirHistory           := PathOfHistory();
  DirInternetCache     := PathOfInternetCache();
  DirInternetCookies   := PathOfInternetCookies();
  DirMyDocuments       := PathOfMyDocuments();
  DirMyPictures        := PathOfMyPictures();
  DirProgramFiles      := PathOfProgramFiles();
  DirProgramFilesCommon:= PathOfProgramFilesCommon();
  DirSystem32          := PathOfSystem32();
  DirWindows           := PathOfWindows();
  ExeName              := ExtractFileName(ParamStr(0));
  ExeName              := LowerCase(ExeName);
  ExeName              := UpperCase(Copy(ExeName,1,1))+Copy(ExeName,2,Length(ExeName)-5);
  ExePath              := ExtractFilePath(ParamStr(0));
  DirPersist           := DirAppDataLocal+ExeName+'\';
  DirPersist           := ExePath;
  If Not DirectoryExists(DirPersist) Then ForceDirectories(DirPersist);
  FileIni              := DirPersist+ExeName+'.ini';
  IniData              := TStringList.Create();
  DirCommonFiles       := DirAppDataCommon;
  If DirCommonFiles='' Then DirCommonFiles:='C:\Program Files\Common Files\';
  If Copy(DirCommonFiles,Length(DirCommonFiles),1)<>'\' Then DirCommonFiles:=DirCommonFiles+'\';
  DirDB                := DirPersist+'data\';
  DirDest              := DirPersist+'Dest\';
  DirDest              := DirPersist+'Help\';
  DirImages            := DirPersist+'images\';
  DirProgFiles         := DirProgramFiles;
  If DirProgFiles='' Then DirProgFiles:='C:\Program Files\';
  If Copy(DirProgFiles,Length(DirProgFiles),1)<>'\' Then DirProgFiles:=DirProgFiles+'\';
  DirReports           := DirPersist+'Reports\';
  DirResources         := DirPersist+'Resources\';
  DirSource            := ExePath+'Source\';
  DirTemp           := ExePath+'Temp\';
  DirScripts           := ExePath+'Scripts\';
  DirWorking           := DirPersist+'Working\';
  //Start Directory Modifications



  //End Directory Modifications
  //Start Directory Creation Booleans
  {example set boDirDB:=True to create DirDB directory}
  //boDirReports:=True;
  //boDirResources:=True;
  //boDirImages:=True;
  //Start Directory Creation Booleans
  If boDirDB        Then If Not DirectoryExists(DirDB         ) Then ForceDirectories(DirDB         );
  If boDirDest      Then If Not DirectoryExists(DirDest       ) Then ForceDirectories(DirDest       );
  If boDirHelp      Then If Not DirectoryExists(DirHelp       ) Then ForceDirectories(DirHelp       );
  If boDirImages    Then If Not DirectoryExists(DirImages     ) Then ForceDirectories(DirImages     );
  If boDirPersist   Then If Not DirectoryExists(DirPersist    ) Then ForceDirectories(DirPersist    );
  If boDirReports   Then If Not DirectoryExists(DirReports    ) Then ForceDirectories(DirReports    );
  If boDirResources Then If Not DirectoryExists(DirResources  ) Then ForceDirectories(DirResources  );
  If boDirScripts   Then If Not DirectoryExists(DirScripts    ) Then ForceDirectories(DirScripts    );
  If boDirSource    Then If Not DirectoryExists(DirSource     ) Then ForceDirectories(DirSource     );
  If boDirTemp      Then If Not DirectoryExists(DirTemp       ) Then ForceDirectories(DirTemp       );
  If boDirWorking   Then If Not DirectoryExists(DirWorking    ) Then ForceDirectories(DirWorking    );

  If Not FileExists(FileIni)          Then IniData.SaveToFile(FileIni);
  IniData.LoadFromFile(FileIni);
  //Update From Ini
  UpdateVarFromIni(boDirDB              ,'boDirDB'              ,IniData);
  UpdateVarFromIni(boDirDest            ,'boDirDest'            ,IniData);
  UpdateVarFromIni(boDirHelp            ,'boDirHelp'            ,IniData);
  UpdateVarFromIni(boDirImages          ,'boDirImages'          ,IniData);
  UpdateVarFromIni(boDirPersist         ,'boDirPersist'         ,IniData);
  UpdateVarFromIni(boDirReports         ,'boDirReports'         ,IniData);
  UpdateVarFromIni(boDirResources       ,'boDirResources'       ,IniData);
  UpdateVarFromIni(boDirScripts         ,'boDirScripts'         ,IniData);
  UpdateVarFromIni(boDirSource          ,'boDirSource'          ,IniData);
  UpdateVarFromIni(boDirTemp            ,'boDirTemp'            ,IniData);
  UpdateVarFromIni(boDirWorking         ,'boDirWorking'         ,IniData);
  UpdateVarFromIni(DirDB                ,'DirDB'                ,IniData);
  UpdateVarFromIni(DirDest              ,'DirDest'              ,IniData);
  UpdateVarFromIni(DirHelp              ,'DirHelp'              ,IniData);
  UpdateVarFromIni(DirImages            ,'DirImages'            ,IniData);
  UpdateVarFromIni(DirPersist           ,'DirPersist'           ,IniData);
  UpdateVarFromIni(DirReports           ,'DirReports'           ,IniData);
  UpdateVarFromIni(DirScripts           ,'DirScripts'           ,IniData);
  UpdateVarFromIni(DirSource            ,'DirSource'            ,IniData);
  UpdateVarFromIni(DirTemp              ,'DirTemp'              ,IniData);
  UpdateVarFromIni(DirWorking           ,'DirWorking'           ,IniData);
  UpdateVarFromIni(Filelast             ,'Filelast'             ,IniData);
  //Update Ini: These are set not read
  UpdateIniFromVar(DirAppDataCommon     ,'//DirAppDataCommon'     ,IniData);
  UpdateIniFromVar(DirAppDataLocal      ,'//DirAppDataLocal'      ,IniData);
  UpdateIniFromVar(DirHistory           ,'//DirHistory'           ,IniData);
  UpdateIniFromVar(DirInternetCache     ,'//DirInternetCache'     ,IniData);
  UpdateIniFromVar(DirInternetCookies   ,'//DirInternetCookies'   ,IniData);
  UpdateIniFromVar(DirMyDocuments       ,'//DirMyDocuments'       ,IniData);
  UpdateIniFromVar(DirMyPictures        ,'//DirMyPictures'        ,IniData);
  UpdateIniFromVar(DirProgramFiles      ,'//DirProgramFiles'      ,IniData);
  UpdateIniFromVar(DirProgramFilesCommon,'//DirProgramFilesCommon',IniData);
  UpdateIniFromVar(DirSystem32          ,'//DirSystem32'          ,IniData);
  UpdateIniFromVar(DirWindows           ,'//DirWindows'           ,IniData);
  IniData.Sort();
  IniData.SaveToFile(FileIni);
Finalization
  IniData.SaveToFile(FileIni);
  IniData.Free;
end.

//