Delphi  TRUCCHI
   
Trucco Data
DISABILIATARE - ABILITARE BARRA APPLICAZIONI DI WINDOWS 2010
NASCONDERE TASTO START DI WINDOWS 2010
VERIFICARE LA PRESENZA DI UNA SCHEDA AUDIO 2008
CONOSCERE IL TIPO DI UN DRIVE 2008
OTTENERE IL PATH DELLAPPLICAZIONE 2008
DIVIDERE UN FILE 2008
COMPATTARE UN DATABASE ACCESS 2008
CONTROLLARE LA PRESENZA DI UN FLOPPY 2008
CERCARE UN FILE 2008
CREARE UN PERCORSO 2008
CONVERSIONE NUMERICA 2008
CREARE UNA BITMAP DA UN'ICONA 2008
INDIVIDUARE IL S.O. IN USO 2008
DIMENSIONE DI UNA DIRECTORY 2008
REFRESH DEL MONITOR 2008
NUMERO DI COLORI SUPPORTATI 2008
NASCONDERE LE ICONE DEL DESKTOP 2008
LISTA DEI PREFERITI DI IE 2008
INDIRIZZO PORTA PARALLELA (LPT) 2006
USARE I FILE INI 2006
IMPOSTARE LA RISOLUZIONE DEL MONITOR 2006
APRIRE E CHIUDERE IL LETTORE CD 2006
SPEGNERE ED ACCENDERE IL MONITOR 2006
HINT SU PIÙ RIGHE 2006
COLORARE LE CELLE DI UNA DBGRID 2006
ULTIMO GIORNO DEL MESE 2006
CANCELLARE UNA DIRECTORY 2006
FINDCOMPONENT 2006
ESEGUIRE UNA APPLICAZIONE DA UN PROGRAMMA 2006
ESEGUIRE WORD O EXCEL DA UN PROGRAMMA 2006
EFFETTUARE IL REBOOT DEL COMPUTER 2006
LEGGERE IL NUMERO SERIALE DI UN DISCO 2006
LEGGERE LE INFORMAZIONI DI UN FILE MP3 2006
CATTURARE LO SCHERMO IN UNA FORM 2006
CAMBIARE PROPRIETÀ COMUNI 2006
SPOSTARE UN FILE 2006
AVVIO DI UN APPLICAZIONE ALL'AVVIO DI WINDOWS 2006
INDIRIZZO IP 2006
CONFRONTO DATE 2006
DISABILITARE BEEP DI SISTEMA 2006
CURSORI E ICONE 2006
COME RENDERE TRASPARENTE UN COMPONENTE DERIVATO DA 2006
COME NASCONDERE UN TASK 2006
REGISTRAZIONE AUTOMATICO DEL BDE 2006
MODIFICARE LA FORMA DI UNA FINESTRA 2006
IDENTIFICAZIONE DEL TIPO DI PIATTAFORMA Win32 2006
CONTROLLO DELLA PORTA LPT1 2006

DISABILIATARE - ABILITARE BARRA APPLICAZIONI DI WINDOWS

 

// Disabilitazione Barra applicazioni

EnableWindow(FindWindowEx(FindWindow('Shell_TrayWnd', nil), 0, 'Button',nil), False);

ShowWindow(FindWindow('Shell_TrayWnd', Nil), SW_Hide);

 

// Ripristino Barra applicazioni

ShowWindow(FindWindow('Shell_TrayWnd', Nil), SW_Show);

EnableWindow(FindWindowEx(FindWindow('Shell_TrayWnd', nil), 0, 'Button',nil), True);

 

NASCONDERE TASTO START DI WINDOWS

 

{Hide the start button}

Pocedure TForm1.Button1Click(Sender: TObject);

Var Rgn : hRgn;

Begin

   Rgn := CreateRectRgn(0, 0, 0, 0);

  SetWindowRgn(FindWindowEx(FindWindow('Shell_TrayWnd',nil),0,'Button',nil),Rgn, true);

End;

 

{Turn the start button back on}

Procedure TForm1.Button2Click(Sender: TObject);

Begin

 SetWindowRgn(FindWindowEx(FindWindow('Shell_TrayWnd',nil),0,'Button',nil),0,true);

End;

 

{Disable the start button}

Procedure TForm1.Button3Click(Sender: TObject);

Begin

 EnableWindow(FindWindowEx(FindWindow('Shell_TrayWnd', nil),0,'Button', nil),false);

End;

 

{Enable the start button}

Procedure TForm1.Button4Click(Sender: TObject);

Begin

 EnableWindow(FindWindowEx(FindWindow('Shell_TrayWnd',nil),0,'Button',nil),true);

End;

 

VERIFICARE LA PRESENZA DI UNA SCHEDA AUDIO

Prima di effettuare operazioni di qualsiasi tipo sulla scheda audio è necessario verificare che la stessa sia installata correttamente sulla macchina.

Per verificare la presenza di una scheda audio sul sistema è necessario ricorrere alla funzione waveOutGetNumDevs, che restituisce il numero di periferiche installate. Il valore restituito 0 indica la mancanza di una scheda audio o la presenza di un errore.

Function IsSoundCardInstalled: Boolean;
Begin
   Result := waveOutGetNumDevs > 0;
End;

Prima di invocare la funzione waveOutGetNumDevs è necessario includere la unit MMSystem.

 

SU^

CONOSCERE IL TIPO DI UN DRIVE

Esiste una funzione molto utile che ritorna il tipo di unità in base alla root del drive specificato come parametro. Questa funzione si chiama GetDriveType e analizziamo il suo funzionamento con un esempio molto semplice:

Procedure ShowDriveType(Drive: Char);
Begin
  Case GetDriveType(PChar(Drive + ':\')) of
    0: ShowMessage('The drive type cannot be determined');
    1: ShowMessage('The root directory does not exist');
    DRIVE_REMOVABLE: ShowMessage(Drive Removable / Diskette');
    DRIVE_FIXED: ShowMessage('Drive Fixed');
    DRIVE_CDROM: ShowMessage('CD-ROM Drive');
    DRIVE_RAMDISK: ShowMessage('RAM Drive');
    DRIVE_REMOTE: ShowMessage('Remote Drive');
  End;
End;

Alcuni esempi di invocazione della procedura ShowDriveType sono i seguenti:

ShowDriveType('A');
ShowDriveType('C');
ShowDriveType('D');

 

SU^

OTTENERE IL PATH DELL'APPLICAZIONE

Qualche volta è necessario ottenere il path della propria applicazione, senza usare file o altri sistemi di supporto per la memorizzazione delle informazioni.

Il path della propria applicazione si può ottenere facilmente in questo modo:

Path := ExtractFilePath(Application.ExeName);

ExeName è una proprietà a sola lettura della classe TApplication, che contiene il riferimento assoluto dell'eseguibile, che per default è uguale a PROJECT1.EXE.

 

SU^

DIVIDERE UN FILE

Questo tip è particolarmente utile per chi vuole implementare un proprio meccanismo di backup.

Var inFile, OutFile: FILE;
      CopyBuffer: POINTER;
      iRecsOK, iRecsWr, iX: Integer;
      sfileName: String;
CONST ChunkSize: LONGINT = 1400000 // Dimensione tipo floppy 1.44 MB
Begin
   GETMEM(CopyBuffer, ChunkSize);
   SfileName := 'C:\TEMP\NomeFileDaDividere';
   AssignFile(infile, sFileName + '.doc');
   Reset(InFile, 1);
   iX := 1;
   Repeat
     AssignFile(OutFile, sFileName + IntToStr(iX) + '.dat');
     ReWrite(outFile, 1);
     Inc(iX);
     BlockRead(InFile, CopyBuffer^, ChunkSize, iRecsOk);
     BlockWrite(OutFile, CopyBuffer^, iRecsOk, iRecWr);
     CloseFile(OutFile);
   Until (iRecOk < ChunkSize);
   CloseFile(inFile);
   FREEMEM(CopyBuffer, ChunkSize);
End;

 

SU^

COMPATTARE UN DATABASE ACCESS

Compattare il database da Delphi senza dover utilizzare Access (e senza nemmeno il bisogno di installarlo sulla macchina) è una procedura molto utile per chi si occupa di programmi gestionali con il diffuso DBMS di Microsoft.
Per risolvere questo problema bisogna appoggiarsi ad un'istanza dell'oggetto COM del provider Microsoft Jet. Nel codice si possono osservare i passi da compiere per compattare il database "C:\prova.mdb".

Uses ComObj;

Procedure CompactDatabase;
Var MsJet: Variant;
Begin
  MsJet := CreateOleObject('JRO.JetEngine');
  MsJet.CompactDatabase('Data Source=C:\prova.mdb;','Data Source=C:\provabak.mdb;');
  DeleteFile('C:\prova.mdb');
  RenameFile('C:\provabak.mdb', 'C:\prova.mdb');
End;

Per creare l'oggetto COM del provider Microsoft Jet è necessario includere la unit ComObj.

 

SU^

CONTROLLARE LA PRESENZA DI UN FLOPPY

Controlla la presenza di un media removibile in una unità come floppy o Iomega.

 

Function DiskReady(const Drive: char): Boolean;
Var DrvNum: byte;
       EMode: Word;
Begin
  result := false;
  DrvNum := ord(Drive);
  If DrvNum >= ord('a') Then dec(DrvNum,32);
  EMode := SetErrorMode(SEM_FAILCRITICALERRORS);
  Try
    If DiskSize(DrvNum-$40) <> -1 Then result := true
  finally
    SetErrorMode(EMode);
  End;
End;

 

SU^

CERCARE UN FILE

Questa function cerca un file di nome "name" partendo dalla posizione "initialpath"

 

Function findafile(initialpath,name:string):string;
Var s:Tsearchrec;
Begin
  If initialpath[length(initialpath)]<>'\ Tthen initialpath:=initialpath+'\';
  If findfirst(initialpath+name,faanyfile,s)=0 Then
    Begin
      findclose(s);
      result:=initialpath+name;
   End
  Else
   Begin
    If findfirst(initialpath+'*.*',faDirectory,s)=0 Then
      repeat
       If (( s.attr and faDirectory ) = faDirectory)and(s.name[1]<>'.') then
         result:=findafile(initialpath+s.name,name);
      Until (findnext(s)<>0)or(result<>'');
    findclose(s);
  End;
End;

 

SU^

CREARE UN PERCORSO

Questa procedura crea un percorso directory per subdirectory

 

Procedure forceMKDIR(path:string);
Bar c,d:integer;
Begin
  c:=pos('\',path)+1;
  If (path[length(path)]<>'\')and(pos('.',path)=0) then path:=path+'\';
  If pos('\',path)=1 Then
    Begin
     If path[2]='\' Then c:=3 // caso della rete \\ prova\ ciao
                           Else c:=2; // caso che manca la lettera \prova\ciao
    End;
   If upcase(path[1])in['A'..'Z'] Then c:=4; // caso normale c:\prova\ciao
   For d:=c to length(path) Do
      If (path[d]='\')and(not directoryexists(copy(path,1,d-1))) Then mkdir(copy(path,1,d-1));
End;

 

SU^

CONVERSIONE NUMERICA

Conversione numerica con punti delle migliaia e virgola decimale

 

Function point(s:string;separator:char):string;
Var c:integer;
Begin
  While pos(#32,s)<>0 Do  delete(s,pos(#32,s),1);
  If s='' Then exit;
   c:=pos('.',s);
  If c=0 then c:=length(s)+1;
  While c>0 Do
    Begin
     dec(c,3);
     insert(separator,s,c);
    End;
  While (length(s)>0)and(s[1]=separator) Do delete(s,1,1);
   result:=s;
End;

 

SU^

CREARE UNA BITMAP DA UN'ICONA

Procedure TForm1.Button1Click(Sender: TObject);
Var TheIcon : TIcon;
       TheBitmap : TBitmap;
Begin
  TheIcon := TIcon.Create;
  TheIcon.LoadFromFile('C:\Icons\Icona.ico');
  TheBitmap := TBitmap.Create;
  TheBitmap.Height := TheIcon.Height;
   TheBitmap.Width := TheIcon.Width;
   TheBitmap.Canvas.Draw(0, 0, TheIcon);
    Form1.Canvas.Draw(10, 10, TheBitmap);
    TheBitmap.Free;
    TheIcon.Free;
End;

 

SU^

INDIVIDUARE IL S.O. IN USO

La funzione che segue individua il tipo di S.O. in uso e la versione.

Function InfoSO: String;
Var piattaforma: string;
       win_ver: integer;
Begin
 Case (Win32Platform) of VER_PLATFORM_WIN32_WINDOWS:

  Begin
    piattaforma := 'Windows 9x/Me';
    win_ver := Win32BuildNumber AND $0000FFFF;
 End;
 VER_PLATFORM_WIN32_NT:

   Begin
    piattaforma := 'Windows NT';
    win_ver := Win32BuildNumber;
   End;
 Else

  Begin
   piattaforma := 'Windows';
   win_ver := 0;
  End;
 End; // case
If (Win32CSDVersion = '') Then
    InfoSO := Format('%s %d.%d (Build %d)', [piattaforma,Win32MajorVersion,

                                 Win32MinorVersion,win_ver])
 Else
    InfoSO := Format('%s %d.%d (Build %d: %s)', [piattaforma,Win32MajorVersion,
                               Win32MinorVersion,win_ver,WIN32CSDVersion]);
End;

 

SU^

DIMENSIONE DI UNA DIRECTORY

Fornisce l'esatta dimensione in byte del contenuto di una directory e delle sue sotto directory, potendo selezionare tramite caratteri jolly solo l'analisi di certi files e permettendo di scegliere se deve procedere anche nelle sottodirectory.

 

Function directorysize(path:string; var totfiles : integer):int64;
var s:Tsearchrec;
      t:integer;
Begin
  result:=0;
  t:=0;
  If path[length(path)]<>'\' Then path:=path+'\';
  If findfirst(path+'*.*',faanyfile,s)=0 Then
  repeat
    If s.name[1]<>'.' then

     Begin
      If ( s.attr and ( FaVolumeID + FaDirectory ) ) = 0 then

       Begin
          inc(result,s.Size);
          inc(totfiles);
       End;
     If ( s.attr and faDirectory ) = faDirectory Then
      Begin
         inc(result,directorysize(path+s.name+'\',t));
        inc(totfiles,t);
      End;
   End;
  until findnext(s)<>0;
  findclose(s);
End;

 

SU^

REFRESH DEL MONITOR

Questa procedura, collegata all'evento Click di un bottone permette di effettuare il refresh del desktop.

SendMessage(FindWindow('Progman', 'Program Manager'), WM_COMMAND, $A065, 0);

 

SU^

NUMERO DI COLORI SUPPORTATI

La funzione qui riportata consente di sapere il numero colori chee la risoluzione corrente riesce a
supportare, usando la funzione standart delle API GetDeviceCaps.

Function GetColor: Integer
Var h: hDC;
Begin
 Result := 0;
 try
  h := GetDC(0);
  Result := 1 shl (GetDeviceCaps(h,PLANES) * GetDeviceCaps(h, BITSPIXEL));
 finally
  ReleaseDC(0,h)
 End;
End;

 

SU^

NASCONDERE LE ICONE DEL DESKTOP

Ecco come nascondere tutte le icone presenti sul desktop di Windows.

Procedure ShowDesktop(const YesNo: boolean);
Var h: THandle;
Begin
  h := FindWindow('Progman', NIL);
  h := GetWindow(h, GW_CHILD);
  If (YesNo = TRUE) Then  ShowWindow(h, SW_SHOW);
                                     Else ShowWindow(h, SW_HIDE);
End;

Utilizzo:

Nascondi icone: ShowDesktop(FALSE);
Mostra icone: ShowDesktop(TRUE);
 

SU^

LISTA DEI PREFERITI DI IE

Richiamando la funzione GetIEFavorites verranno inseriti in una ListBox le voci presenti nel menù Preferiti del noto browser della software house di Redmond.

Function GetIEFavorites (const bm_path : string): TStrings;
Var s_rec : TSearchRec;
      str : TStrings;
     path, dir, filename : string;
     buffer : Array[0..2047] of char;
     found : integer;
Begin
 str := TStringList.Create;
 Try
   path := bm_path + '\*.url';
   dir := ExtrachFilePath(path);
   found := FindFirst(path, faAnyFile, s_rec);
   While (found = 0) Do

    Begin
      SetString(filename, buffer, GetPrivateProfileString('InternetSC',  PChar('URL'), NIL, buffer,

                       SizeOf(buffer), PChar(dir+s_rec.Name)));
      str.Add(filename);
      found := FindNext(s_rec);
    End; { while }
  found := FindFirst(dir+'\*.*', faAnyFile, s_rec);
  While (found = 0) Do

   Begin
     If ((s_rec.Attr AND faDirectory) > 0) AND (s_rec.Name[1] <> '.')) Then
          str.AddStrings(GetIE_BM(dir+'\'+s_rec.Name));
     Found := FindNext(s_rec);
   End; { while }
  FindClose(s_rec);
 finally
   result := str;
 End; {try-finally }
End;

{ Ecco come usarla }

Procedure TForm1.Button1Click(Sender: TObject);
Var pidl: PItemIDList;
      bm_path : Array[0..MAX_PATH] of char;
Begin
 SHGetSpecialFolderLocation(Handle, CSIDL_FAVORITES, pidl);
 SHGetPathFromIDList(pidl, bm_path);
 ListBox1.Items := GetIEFavorites(StrPas(bm_path));
End;

 

SU^

INDIRIZZO PORTA PARALLELA (LPT)

Questa funzione implementa una routine assembler che restituisce l'indirizzo hardware della porta LPT,
solitamente usata per la connessione ad una stampante.

Function GetPortAddress(PortNo:Integer):word; assembler; stdcall;
Asm
 push es
 push ebx
 mov ebx, PortNo
 shl ebx, 1
 mov ax,40h // Segmento dell'indirizzo
 mov es,ax
 mov ax,ES:[ebx+6]
 pop ebx
 pop es
End;

 

SU^

USARE I FILE INI

Molte volte i programmi hanno bisogno di salvare alcune informazioni in un file per poterle poi rileggere all'avvio successivo. Un metodo comodo per fare ciò è usare i file INI. Delphi mette a disposizione la classe TIniFile per la gestione automatica di tali file.
 

uses IniFiles;

Procedure CaricaDalFile;
Var FileIni: TIniFile;
Begin
 FileIni := TIniFile.Create('C:\Il_Mio_File.ini');
 try
  If FileIni.ReadBool('Sezione', 'Entry', false) Then FileIni.WriteString('Sezione2', 'Entry2', 'Valore2')
                                                                             Else FileIni.WriteString('Sezione2', 'Entry2', 'Valore1');
  FileIni.UpdateFile;
 finally
   FileIni.Free;
 End;
End;

Notiamo che la prima cosa da fare è creare un oggetto di tipo TIniFile passandogli come parametro il percorso del file. A questo punto abbiamo a disposizione vari metodi per leggere e scrivere stringhe, interi, booleani, etc. Questi metodi sono caratterizzati da tre parametri: il primo si riferisce ad una sezione del file (ad esempio "Opzioni generali"), il secondo richiama il nome del campo sul quale vogliamo fare l'operazione (ad esempio "Data Ultima esecuzione"). Infine il terzo parametro ha due scopi diversi: se stiamo andando a scrivere, il terzo parametro sarà il dato memorizzato; se invece stiamo leggendo questo sarà il valore che sarà restituito come valore predefinito nel caso che il file non contenesse la sezione o/e il campo che stiamo cercando di leggere. Una volta finite tutte le operazioni di scrittura è necessario eseguire il metodo "UpdateFile", altrimenti il file non sarà modificato.

 

SU^

IMPOSTARE LA RISOLUZIONE DEL MONITOR

In alcuni casi può essere utile impostare la risoluzione del monitor "al volo".
Come accade spesso, occorre utilizzare un'API di Windows: ChangeDisplaySettings.
La definizione della funzione è la seguente:

LONG ChangeDisplaySettings(LPDEVMODE lpDevMode, DWORD dwflags );

E' possibile utilizzarla anche per controllare se una particolare modalità è supportata dalla scheda video. Per una descrizione completa consultare il file di Help "Windows SDK"fornito con Delphi.
Il listato seguente illustra l'utilizzo dell'API.

Function SetMonitorRes(ResX, ResY, BxPix, Freq: Integer; ChangeMode: String): Boolean;
Var Mode: TDeviceMode; // Struttura con le nuove impostazioni
       Flags: DWORD; // Tipo d'impostazione: Test / Permanente
Begin
 // Preparo la struttura
 With Mode Do
  Begin
   dmSize := SizeOf(Mode);
   dmPelsWidth := ResX;
   dmPelsHeight := ResY;
   dmBitsPerPel := BxPix;
   dmDisplayFrequency := Freq;
   dmFields := DM_PELSWIDTH Or DM_PELSHEIGHT Or
   DM_BITSPERPEL Or DM_DISPLAYFREQUENCY;
 End;
 // Imposta la modalità
 Flags := 0;
 If ChangeMode = 'TEST' Then Flags := CDS_TEST
                                              Else If ChangeMode = 'REG' Then Flags := CDS_UPDATEREGISTRY;
 // Eseguo la chiamata: Restituisco True se la chiamata ha successo
 Result := (ChangeDisplaySettings(Mode, Flags) = DISP_CHANGE_SUCCESSFUL);
End;
 

SU^

APRIRE E CHIUDERE IL LETTORE CD

Create una nuova applicazione ed includete in essa la unit "MMSystem"

uses MMSystem;

Ora per aprire il lettore cd usate il comando :

mciSendString('Set cdaudio door open wait', nil, 0, handle);

mentre per chiudere il lettore cd usate il comando :

mciSendString('Set cdaudio door closed wait', nil, 0, handle);

 

SU^

SPEGNERE ED ACCENDERE IL MONITOR

Per spegnere il monitor usate il comando :

SendMessage(Application.Handle, WM_SYSCOMMAND, SC_MONITORPOWER, 0);

mentre per accendere il monitor usate il comando :

SendMessage(Application.Handle, WM_SYSCOMMAND,SC_MONITORPOWER, -1);

 

SU^

HINT SU PIU' RIGHE

Nell' evento FormCreate della form contenente ad esempio il Button1aggiungete la seguente linea :

Button1.Hint := 'Prima riga' + Chr(13) + 'Seconda riga' + Chr(13) +'...';

 

SU^

COLORARE LE CELLE DI UNA DBGRID

Creiamo una nuova applicazione ed utilizziamo i seguenti componenti :  Table1, DataSource1,
DBGrid1 ed eseguiamo le seguenti operazioni : poniamo la proprietà DatabaseName del componente Table1 uguale a DBDEMOS, poniamo la proprietà TableName del componente Table1 uguale a
animals.dbf, poniamo la proprietà Active del componente Table1 uguale a True, poniamo la proprietà DataSet del componente DataSource1 uguale a Table1, poniamo la proprietà DataSource del componente DBGrid1 uguale a DataSource1, ora facciamo doppio click nella casella a lato dell'evento
OnDrawColumnCell del componente DBGrid1 creando così l'evento DBGrid1DrawColumnCell, quindi andiamo a scrivere le seguenti linee di codice :

Procedure TForm1.DBGrid1DrawColumnCell(Sender: TObject; const Rect: TRect;
                                                                    DataCol: Integer; Column: TColumn; State: TGridDrawState);
Begin
 If ((State = [gdSelected,gdFocused]) or (State = [gdSelected])) and

     (Table1.FieldByName('SIZE').AsString = '10')  Then
    {Se la cella è selezionata ed il valore della cella SIZE è 10 allora ...}
    Begin
     If Column.FieldName = 'AREA' Then
       Begin
        DBGrid1.Canvas.Brush.Color := clRed; {imposta il rosso come sfondo}
        DBGrid1.Canvas.Font.Color := clWhite; {imposta il bianco come colore del font}
        DBGrid1.Canvas.FillRect(Rect); {colora lo sfondo di rosso}
        DBGrid1.Canvas.TextOut(Rect.Left+2, Rect.Top+2,

                       Table1.FieldByName(Column.FieldName).AsString); {scrive il testo di colore bianco}
      End;
    End

  Else
  If (Table1.FieldByName('SIZE').AsString = '10') Then
    {altrimenti se il valore della cella SIZE 10 allora ...}
   Begin
    If Column.FieldName = 'AREA' Then
     Begin
       DBGrid1.Canvas.Brush.Color := clMaroon; {imposta il bordeaux come sfondo}
       DBGrid1.Canvas.Font.Color := clGray; {imposta il grigio come colore del font}
       DBGrid1.Canvas.FillRect(Rect); {colora lo sfondo di bordeaux}
       DBGrid1.Canvas.TextOut(Rect.Left+2, Rect.Top+2,

                         Table1.FieldByName(Column.FieldName).AsString); {scrive il testo di colore grigio}
    End;
 End;
End;

Con questa procedura si è impostato il colore di sfondo e del testo del campo AREA in modo differente da tutta la griglia nel caso in cui il campo SIZE del record corrispondente è uguale a 10.

 

SU^

ULTIMO GIORNO DEL MESE

Creiamo una nuova applicazione ed utilizziamo i seguenti componenti : DateTimePicker1, Edit1
Facciamo ora doppio click nella casella a lato dell'evento OnChange del componente DateTimePicker1 creando così l'evento DateTimePicker1Change, quindi andiamo a scrivere le seguenti linee di codice :
 

Procedure TForm1.DateTimePicker1Change(Sender: TObject);
Var  Data : TDate;
        Anno, Mese, Giorno : Word;
Begin
 Data:= DateTimePicker1.Date;
 DecodeDate(Data, Anno, Mese, Giorno);
 If Mese = 12 Then
   Begin
    Mese := 1;
    Anno := Anno + 1;
   End

  Else
   Begin
     Mese := Mese + 1;
   End;
 Giorno := 1;
 Data := EncodeDate(Anno, Mese, Giorno);
 Data := Data - 1.0;
 Edit1.Text := DateToStr(Data);
End;

 

SU^

CANCELLARE UNA DIRECTORY

Qquesta funzione cancella la directory "path" e le sub-directory result=true se tutto Ok

 

Function deltree ( path : string ):boolean;
Var s:Tsearchrec;
Begin
 If path[length(path)]<>'\ Tthen path:=path+'\';
 If findfirst(path+'*.*',faanyfile,s)=0 Then
   repeat
    If (( s.attr and ( FaVolumeID + FaDirectory ) ) = 0) and (s.name[1]<>'.') Then deletefile(path+s.name);
    If (( s.attr and faDirectory ) = faDirectory)and(s.name[1]<>'.') then
     Begin
      deltree(path+s.name);
      RemoveDirectory(pchar(path+s.name));
     End;
   Until findnext(s)<>0;
 findclose(s);
 result:=removeDirectory(pchar(path));
End;

 

SU^

FINDCOMPONENT

Supponiamo di dover porre la proprietà Text di 20 componenti TEdit della Form1 uguale alla stringa nulla. Si potrebbero scrivere le seguenti 20 linee di codice :

Edit1.Text := '';
Edit2.Text := '';
...
Edit20.Text := '';

Tuttavia la funzione FindComponet ( TComponent.FindComponent ) ci permette di scrivere meno codice e di velocizzare eventuali operazioni di modifica.
Per quanto riguarda l'esempio precedente, possiamo sintetizzare le linee di codice nel seguente modo :

For I := 1 to 20 Do
Begin
 TEdit(Form1.FindComponent('Edit'+IntToStr(I))).Text := '';
End;
 

SU^

ESEGUIRE UNA APPLICAZIONE DA UN PROGRAMMA

Esiste un api di windows : shellExecute
 

Procedure TForm1.Button1Click(Sender: TObject);
Var lsprocess : string;
       lsCommandLine : string;
Begin
 lscommandline := '';
 lsprocess := 'd:\Nomeile.exe;
 shellExecute(Form1.Handle,'open',pchar(lsprocess),pchar(lscommandline),nil,sw_Hide);
End;

If WinExec( 'C:\Programmi\haead\nero.exe', WM_SHOW ) > 31 Then showmessage (' APERTO !!!!');

 

SU^

ESEGUIRE WORD O EXCEL DA UN PROGRAMMA

Esiste  il modo di creare un programma che lanci Word o Excel

 

FExcel e un variant.
// Creo L' oggetto OLE di tipo Excel
FExcel := Unassigned;
FExcel := CreateOleObject('Excel.Application');
Fexcel.Visible := True;
FExcel.Workbooks.Add;


SU^

EFFETTUARE IL REBOOT DEL COMPUTER

Il reboot del computer è un evento abbastanza frequente nei programmi di installazione, per esempio dopo la modifica dei parametri del registro di configurazione.
Per effettuare il reboot della macchina è sufficiente invocare la funzione API ExitWindowsEx. Questa funzione viene chiamata anche dallo stesso Windows quando deve effettuare altre operazioni connesse alla chiusura del sistema operativo, per esempio la disconnessione dell'utente o lo spegnimento della macchina.

Per riavviare il computer è sufficiente effettuare questa chiamata:

ExitWindowsEx(EWX_REBOOT, 0);

EWX_REBOOT è una costante che identifica il modo con cui si esce da Windows. Specificando altre costanti è possibile compiere le altre operazioni connesse alla chiusura di Windows.
 

SU^

LEGGERE IL NUMERO SERIALE DI UN DISCO

Uno dei problemi più frequenti per i programmatori è la protezione del software. Il controllo più semplice da realizzare si basa sulla generazione di una chiave univoca di registrazione in base al numero seriale del disco. Qui di seguito illustriamo come ottenere il numero seriale di un disco qualsiasi (A, B, C, D e così via).

Function SerialNumber(const DriveLetter: Char): string;
Var NotUsed: DWord;
       VolumeFlags: DWord;
       VolumeInfo: array [0..MAX_PATH] of Char;
       VolumeSerialNumber: DWord;
Begin
 GetVolumeInformation(PChar(DriveLetter + ':\'), VolumeInfo, SizeOf(VolumeInfo),
                                         @VolumeSerialNumber, NotUsed, VolumeFlags, nil, 0);
 Result := Format('Label = %s VolSer = %8.8X',[VolumeInfo, VolumeSerialNumber])
End;


SU^

LEGGERE LE INFORMAZIONI DI UN FILE MP3

Per chi di voi volesse programmare un bel clone di WinAmp o affini qui di seguito illustreremo come è possibile, con poche righe di codice, ottenere varie informazioni su un file MP3.
Le informazioni contenute nell'ID3-Tag dei file MP3 sono organizzate nel seguente modo:

Byte 1-3 = ID 'TAG'
Byte 4-33 = Titolo
Byte 34-63 = Artista
Byte 64-93 = Album
Byte 94-97 = Anno
Byte 98-127 = Commento
Byte 128 = Genere

Impostiamo quindi una semplice struttura dati dove caricare le informazioni:

Type Mp3Info = record
        ID: string[3];
        Titolo: string[30];
        Artista: string[30];
        Album: string[30];
       Anno: string[4];
       Commento: string[30];
       Genere: Byte;
End;

implementation

Function Mp3GetInfo(NomeFile: String): Mp3Info;
Var FS: TFileStream;
       Buffer:array [1..128] of Char;
Begin
 FS := TFileStream.Create(NomeFile, fmOpenRead or fmShareDenyWrite);
 Try
   FS.Seek(128, soFromEnd);
   FS.Read(Buffer, 128);
   With Result Do

    Begin
     ID := Copy(Buffer, 1, 3);
     Titolo := Copy(Buffer, 4, 30);
     Artista := Copy(Buffer, 34, 30);
     Album := Copy(Buffer, 64, 30);
     Anno := Copy(Buffer, 94, 4);
     Commento := Copy(Buffer, 98, 30);
     Genere := Ord(Buffer[128]);
    End;
 Finally
   FS.Free;
 End;
End;

Per esempio, il risultato della funzione Mp3GetInfo è accessibile nel seguente modo:

Procedure TmyForm.MyButtonClick(Sender: TObject);
Var MyMp3Info: Mp3Info;
Begin
// supponendo di avere 7 label su MyForm che chiameremo lblAutore, lblTitolo, etc.
MyMp3Info := Mp3GetInfo('c:\mymusic\canzone.mp3');
lblAutore.Caption := MyMp3Info.Artista;
lblAlbum.Caption := MyMp3Info.Album;
// ...e così via per tutte le informazioni che vi servono!
End;


SU^

CATTURARE LO SCHERMO IN UNA FORM

Procedure TScrnForm.Cattura;
Var DesktopDC : HDC;
       DesktopCanvas: TCanvas;
       Desktoprect : TRect;
Begin
 DesktopDC := GetWindowDC(getdesktopwindow);
 DesktopCanvas := TCanvas.Create;
 DesktopCanvas.Handle := DesktopDC;
 DesktopRect := Rect(0,0,screen.width, screen.height);
 Canvas.CopyRect(desktopRect, desktopCanvas, DesktopRect);
 ReleaseDC(getdesktopwindow, DesktopDC);
End;

E' possibile applicare una variante, cioè invece di usare il canvas della form, si potrebbe utilizzare un TImage per salvare lo schermo catturato in formato immagine.

 

SU^

CAMBIARE PROPRIETA' COMUNI

Con questa semplice procedura si può cambiare il colore di tutti i componenti della famiglia TEdit presenti sul form. Ovviamente questo metodo può essere applicato a tutti i tipi di componenti e a tutte le proprietà.
 

Procedure TForm1.SetEditsColor(Colore : TColor);
Var i: integer;
Begin
 For i := 0 to (ComponentCount - 1) Do

   Iif (components[i] is TEdit) Then TEdit(Components[i]).Color := Colore;
End;

 

SU^

SPOSTARE UN FILE

Per spostare uno o più files da una parte ad un'altra dello stesso disco, basta rinominare il file:

Esempio: RenameFile('C:\Programmi\App.exe', 'C:\DelphiApps\App.exe');

 

SU^

AVVIO DI UN APPLICAZIONE ALL'AVVIO DI WINDOWS

Una semplice, ma utilissima, procedura che operando sul Registro di Sistema permette di avviare il vostro applicativo all'avvio di Windows
 

Procedure Avvio(TitoloPrg,LineaComando: String; aRunOnce: Boolean);
Var  hKey: string;
        hReg: TRegIniFile;
Begin
 If (aRunOnce) Then hKey := 'Once'
                           Else hKey := '';
 hReg := TRegIniFile.Create('');
 hReg.RootKey := HKEY_LOCAL_MACHINE;
 hReg.WriteString('Software\Microsoft\Windows\CurrenteVersion\Run'+hKey+#0,

                                 TitoloPrg, LineaComando);
 hReg.Destroy;
End;

 

SU^

INDIRIZZO IP
Volete sapere il vostro indirizzo IP?

 

Uses WinSock, SysUtils;

 

Function GetIp: string;
Type p_ulong = ^u_long;
Var v_TWSAData : TWSAData;
      v_PHostEnt : PHostEnt;
      v_TInAddr : TInAddr;
      buffer : Array[0..255] of char;
      fd, rc : integer;
Begin
 result :='';
 rc := WSAStartup($101,v_TWSAData);
 If (rc <> 0) Then raise EsockUtilErr.CreateFmt('Errore (Startup di WSA): %d',[rc])
                    Else

                     Begin
                      GetHostName(buffer, sizeof(buffer));
                      v_PHostEnt := GetHostbyName(buffer);
                      v_TinAddr.S_addr := u_long(p_ulong(v_PHostEnt^.h_addr_list^)^);
                      result := inet_ntoa(v_TInAddr);
                    End;
 fd := WinSock.Socket(PF_INET, SOCK_STREAM, 0);
 If (fd = INVALID_SOCKET) Then
     raise EsockUtilErr.CreateFmt('%d %d: Socket non valido',[fd, WSAGetLastError]);
 SWACleanup;
End;

 

SU^

CONFRONTO DATE

Ecco un modo molto semplice di confrontare due date usando la funzione EncodeDate di Delphi.
 

uses SysUtils;
if (Date > EncodeDate(2002, 12, 15)) then ShowMessage("Buon Compleanno Daemon2k");

 

SU^

DISABILITARE BEEP DI SISTEMA

Attraverso la funzione SystemParametersInfo potete disabilitare/abilitare il beep di sistema.

{ Disabilita } SystemParametersInfo(SPI_SETBEEP, 0, NIL, SPIF_SENDWININICHANGE);
{ Abilita } SystemParametersInfo(SPI_SETBEEP, 1, NIL, SPIF_SENDWININICHANGE);

 

SU^

CURSORI E ICONE

Spesso si desidera utilizzare per il cursore un disegno particolare appropriato per le circostanze in corso. Per fare questo si devono eseguire i seguenti passi:

disegnare un cursore (particolare bitmap 32x32 pixels), se non lo si ha già disposizione, ed eventualmente definirne l’Hotspot;
creare un file di risorse contenente il cursore desiderato;

includere il file di risorse nell’applicativo (usando la direttiva {$R nomefile di risorse});

aggiungere l’handle del cursore nell’elenco dei cursori (Screen.Cursors) usando l’API LoadCursor: Cursors è un’array di handle e all’inizio contiene i cursori forniti di default da Delphi, pertanto è bene che andiate ad inserire il vostro cursore in una casella vuota (lo sono tutte quelle con indice positivo).
A questo punto ogni qual volta durante l’esecuzione vogliate utilizzare il cursore non dovrete far altro che:

Screen.Cursor := indice del vostro cursore;

Esempio: dato un file Curs.Res contenente il cursore chiamato MioCurs, dovete inserire in uno dei file della vostra applicazione la direttiva:

{$R Curs.Res}

ipotizzando che il file risorse si trovi nella stessa directory del codice. Poi dovete caricare il cursore nella tabella supponiamo nella 3a cella:

Screen.Cursors[3] := LoadCursor(HInstance, ‘MIOCURS’);

Infine quando si vuole mostrare questo cursore si farà:

Screen.Cursor := 3;
 

SU^

COME RENDERE TRASPARENTE UN COMPONENTE DERIVATO DA TCustomControl

TCustomControl è la classe per ogni nuovo componente custom in Delphi. Alcune tra le caratteristiche che la contraddistinguono dagli altri discendenti di TWinControl sono:
- disporre di un proprio Device Contect (non solo la Canvas del contenitore);
- contenere altri controlli.
Il supporto di un prorprio Device Context rende impossibile la creazione di nuovi controlli/containers con il background trasparente, al contrario dei più "leggeri" TGraphicControl che sfruttano la Canvas del parent. In realtà, sotto Win32, è possibile rimediare a questa situazione di fatto, semplicemente settando la proprietà WS_EX_TANSPARENT della finestra associato al controllo.
Per far questo ci vengono in aiuto le API Win32 GetWindowLong() e SetWindowsLong(), dichiarate nel seguente modo:
function GetWindowLong(hWnd:HWND; nIndex: Integer): Longint; stdcall;
function SetWindowLong(hWnd: HWNDM; nIndex:Interger;dwNewLong:Longint):Longint;stdcall;
Entrambe necessitano dell'handle della finestra da gestire e l'offset del gruppo di proprietà da gestire (controllare l'SDK). GetWindowLong() restituisce il valore della proprietà richiesta, mentre la sua reciproca necessità di un ulteriore parametro (dwNewLong) che conterrà il valore da settare.- Ecco come dovrebbero essere usate:
Procedure TMyCustomControl.SetTrasparent(Trans_mode : boolean);
Var WinMode : Integer;
Begin
// Leggiamo gli attributi della finestra
winMode:=GetWindowLong(handle, GWL_EXSTYLE);
if trans_mode
then winMode:=winMode or WS_EX_TRANSPARENT
else winMode:= winMode and (not WS_EX_TRANSPARENT);
// Reimpostiamo il tutto...
SetWindowLong(handle, GWL_EXSTYLE, winMode);
End;

 

SU^

COME NASCONDRE UN TASK

Com’è possibile nascondere il nome di un’applicazione al task manager?

In che modo posso evitare che, alla pressione del tasto CTRL + ALT + CANC, si veda il nome di un programma?

 Come faccio ad associare una estensione al mio programma?
 

La funzione da usare per simulare il comportamento di un Servizio sotto Windows95 è RegisterServiceProcess(). Per poter usare questa API è necessario dichiararla staticamente nel seguente modo:

Unit XXX;
Interface
....
const
 // Register Service Process Flags
 RSP_SIMPLE_SERVICE = $00000001;
 RSP_UNREGISTER_SERVICE = $00000000;
 Function RegisterServiceProcess( ProcessID, OpTypeFlag : DWORD ) : DWORD; stdcall;
implementation
....
 Function RegisterServiceProcess; external kernel32 name
 'RegisterServiceProcess';
 

In alternativa si può sfruttare il caricamento dinamico con il seguente codice:

 

Ttype TMyFunction = function( ProcessID, OpTypeFlag : DWORD ) : DWORD; stdcall;
Var RegisterServiceProcess: TMyFunction;
Begin
@RegisterServiceProcess :=GetProcAddress(GetModuleHandle('KERNEL32.DLL'),'RegisterServiceProcess');

Con a disposizione questa chiamata, il codice seguente disabilita la visualizzazione dell'applicativo corrente nel Task-Manager:

RegisterServiceProcess(0, RSP_SIMPLE_SERVICE);

da notare come il Process ID passato sia '0', che indica il processo corrente. Per ripristinare la situazione iniziale si deve usare la chiamata:

RegisterServiceProcess(0, RSP_UNREGISTER_SERVICE);

C'è da dire che questo sistema fa molto più che inibire o meno la visualizzazione nel Task-Manager: infatti, queste chiamate rientrano nell'insieme di funzionalità denominate "Windows 95 Service Control Manager". Per un approfondimento sull'argomento il consiglio è di controllare ladocumentazione dell'SDK.

Per ciò che riguarda il secondo problema, vediamo cosa occorre fare per registrare un estensione e far si che l’Explorer di Windows possa assegnare un'applicazione Container. Questo garantisce che il tuo programma sarà attivato ad ogni richiesta di apertura del documento con l'estensione desiderata. Per ottenere questo risultato è necessario eseguire questi passi:

Creare una chiave nel registry del tipo HKEY_CLASSES_ROOT\MY_APP_ID, dove MY_APP_ID è un identificativo che dobbiamo assegnare arbitrariamente alla nostra applicazione container;

Come valore di default della chiave, è bene assegnare una stringa contenente una descrizione dell'estensione. Quest’informazione, ad esempio, apparirà nella dialog Proprietà sotto la voce Tipo di File;

Se di desidera assegnare un'icona standard all'estensione, aggiungere la sotto chiave HKEY_CLASSES_ROOT\MY_APP_ID\DefaultIcon e assegnare come valore una stringa contenente il percorso del file con l'icona.

Designare le operazione eseguibili dalla Shell di Explorer. Di norma questo equivale a creare un'ulteriore sotto-chiave sotto \MY_APP_ID\Shell\ e qui assegnare le azioni da intraprendere in caso di apertura \Open, stampa \Print o modifica \Edit del documento. Ad esempio, per gestire l'apertura creeremo la chiave HKEY_CLASSES_ROOT\MY_APP_ID\Shell\Open\Command e qui assegneremo il valore stringa E:\MyPath\MyApp.exe "%1";

L'ultimo passo consiste nel creare una chiave con il nome della nostra estensione nel ramo HK_CLS_Root, ad esempio HKEY_CLASSES_ROOT\.MyExt, e assegnare come valore predefinito una stringa con l'App_id del container.

SU^

REGISTRAZIONE AUTOMATICO DEL BDE

Spesso è auspicabile installare in rete un applicativo Delphi, senza dover effettuare alcuna installazione sui vari client.Ciò può essere fatto senza problemi se l'applicativo non accede ad alcun database. Quantunque, se ciò dovesse avverarsi, è possibile installare una copia del BDE in una directory condivisa sul server (per esempio in \\SERVER\BDE), ed inserire PRIMA della inizializzazione dell'applicazione… il codice che permette di registrare, sulla macchina client, il BDE.Attenzione: la BDEPath deve contenere il path al BDE condiviso (al limite potrebbe essere "recuperata" da un file)

Program REGISTRABDE;
Uses Forms, controls, registry, windows, Unit1 in 'Unit1.pas' {Form1},
 

{$R *.RES}
Const BDEPath= '\\SERVER\BDE';
Var r:Tregistry;
 

Begin
 r:=TRegistry.Create;
 try
  r.RootKey:=HKEY_CLASSES_ROOT;
  If r.OpenKey('CLSID\{FB99D700-18B9-11D0-A4CF-00A024C91936}\InprocServer32',true) Then
   Begin
    r.WriteString('(DEFAULT)',BDEPath+'\IDSQL32.DLL');
     r.WriteString('ThreadingModel','Apartment');
   End;
  r.CloseKey;
  If r.OpenKey('CLSID\{FB99D710-18B9-11D0-A4CF-00A024C91936}\InprocServer32',true) Then
   Begin
    r.WriteString('(DEFAULT)',BDEPath+'\IDAPI32.DLL');
    r.WriteString('ThreadingModel','Apartment');
   End;
  r.CloseKey;
  r.RootKey:=HKEY_LOCAL_MACHINE;
  If r.OpenKey('SOFTWARE\Borland\BLW32',true) Then
   Begin
    r.WriteString('BLAPIPATH',BDEPath);
r.WriteString('LOCALE_LIB1',BDEPath+'\usa.bll');r.WriteString('LOCALE_LIB2',BDEPath'\europe.bll');
   r.WriteString('LOCALE_LIB3',BDEPath+'Other.bll');
   r.WriteString('LOCALE_LIB4',BDEPath+'\charset.bll');
   r.WriteString('LOCALE_LIB5',BDEPath+'\ceeurope.bll');
  End;
  r.CloseKey;
 If r.OpenKey('SOFTWARE\Borland\DataBase Enginè,true) Then
  Begin
   r.WriteString('CONFIGFILE01',BDEPath+'\IDAPI32.CFG');
   r.WriteString('DLLPATH',BDEPath);
  End;
 r.closeKey;
 finally
 r.free;
End;
application.initialize;

 

SU^

MODIFICARE LA FORMA DI UNA FINESTRA

L'API di Windows annovera una serie di funzioni molto utili. Una di queste è SetWindowRgn, grazie alla quale è possibile creare finestre d’ogni forma e dimensione, o meglio "ritagliare" il bordo di una finestra a nostro piacimento.
Eccone un esempio che permette di disegnare finestre "non" rettangolari.

Procedure TForm1.FormCreate(Sender: TObject);
Var R: HRgn;
       P: array [0..360] of TPoint;
       x, y, radius,  cx, cy, theta : integer;
Begin
 radius:=200; // raggio del cerchio
 cx:=300; // Coordinate del centro
 cy:=300;
 For theta:=0 To 360 Do

  Begin
   x := cx + round(radius * cos(theta));
   y := cy + round(radius * sin(theta));
   p[theta]:=point(x,y);
 End;
 R := CreatePolygonRgn (P , 360 , WINDING);
 // Crea una finestra rotonda
 SetWindowRgn(Form1.Handle, R , TRUE);
End;
 

SU^

CONTROLLO DELLA PORTA LPT1

Prima di iniziare la stampa di un documento, talvolta è utile verificare lo stato del dispositivo stampante al fine di segnalare a video eventuali problemi.
Una possibile tecnica utile per verificare eventuali anomalie, è usare l'interrupt 17h (servizio 2) del BIOS. Nel registro DH è necessario riportare il numero di "LPT" considerata (LPT1=0; LPT2=1, ecc.).
La seguente funzione è stata verificata in ambiente Windows 95.

Const
 PRT_FREE=128; // Stampante libera
 PRT_PAPEROUT=32; // Paper out
 PRT_SELECTED=16; // Selected
 PRT_OTHER=15; // Other error

Function ControllaStampante:Integer;
Var b:byte;
 Begin
  asm
  mov DX,0 // Stampante LPT1
  mov AH,2 // Servizio 2
  int 17H // IRQ BIOS 17
  mov b,AH
 End;
ControllaStampante:=b;
End;

 

SU^

IDENTIFICAZIONE DEL TIPO DI PIATTAFORMA Win32

Le differenze esistenti tra le diverse implementazioni del set di API WIN 32s, WIN 95, WIN NT risultato di fondamentale importanza nella programmazione di sistema, ed in tutti i casi in cui abbiamo bisogno di lavorare con i meccanismi di protezione/privilegi d'accesso propri di Windows NT e completamente assenti in Windows 95. A tal fine, dalla versione 2 di Delphi è presente la variabile di sistema "Win32Platform", che restituisce il tipo di piattaforma sulla quale l'applicazione è in esecuzione. La dichiarazione è la seguente( unit "sysUtil.pas"):
 

var Win32Platform: integer;

La variabile può assumere i seguenti valori:
VALORE                                                          SIGNIFICATO   NUMERO
VER_PLATFORM_WIN32s                         Win32s.                 0
VER_PLATFORM_WIN32_WINDOWS   Windows 95.        1
VER_PLATFORM_WIN32_NT                   Windows NT.      2

 

SU^