Tema: TXMLDocument
Ver Mensaje Individual
  #3  
Antiguo 07-11-2006
Avatar de dec
dec dec is offline
Moderador
 
Registrado: dic 2004
Ubicación: Alcobendas, Madrid, España
Posts: 13.107
Reputación: 34
dec Tiene un aura espectaculardec Tiene un aura espectacular
Hola,

Hace cierto tiempo escribí un componente al que dí el original e imaginativo nombre de "XmlComoIni"... creo que puede servirte para hacerte una idea, por lo menos, de ciertos aspectos del componente "TXmlDocument".

Código Delphi [-]
{ *********************************************************************** }
{                                                                         }
{ DecComp - Unos sencillos componentes                                    }
{                                                                         }
{ Copyright (c) 2005 dec - davidesperalta@gmail.com                       }
{ bajo la licencia GNU GPL >> ver en "licencia.txt"                       }
{                                                                         }
{ Créditos: A Lepe, del ClubDelphi.com ;-)                                }
{                                                                         }
{ *********************************************************************** }

unit UXmlComoIni;

interface

uses
  // Delphi 7
  //
  Classes, SysUtils, Graphics, XMLIntf, XMLDoc,

  // Pertenece al proyecto
  //
  UTypesDecComp;

type
  TXmlComoIni = class(TComponent)
  private
    FAcercade: TAcercade;
  published
    property Acercade: TAcercade read
      FAcercade write FAcercade stored false;
  private
    FFileName: TFileName;
    FDocXml: TXMLDocument;
    procedure CrearDocXml;
    procedure AbrirDocXml;
    procedure GuardarDocXml;
  public
    constructor Create(AOwner: TComponent); reintroduce; overload; override;
    constructor Create(AOwner: TComponent; const fileName: TFileName); reintroduce; overload;
    destructor Destroy; override;
    procedure UpdateFile;
    procedure DeleteKey(const seccion, clave: string);
    function SectionExists(const seccion: string) : boolean;
    function KeyExists(const seccion, clave: string) : boolean;
    procedure ReadSections(strings: TStrings);
    procedure DeleteSection(const seccion: string);
    procedure ReadSection(const seccion: string; strings: TStrings);
    procedure ReadSectionValues(const seccion: string; strings: TStrings);
    procedure WriteString(const seccion, clave, valor: string);
    function ReadString(const seccion, clave, defecto: string): string;
    procedure WriteInteger(const seccion, clave: string; const valor: integer);
    function ReadInteger(const seccion, clave: string; const defecto: integer) : integer;
    procedure WriteColor(const seccion, clave: string; const valor: TColor);
    function ReadColor(const seccion, clave: string; const defecto: TColor) : integer;
    procedure WriteBool(const seccion, clave: string; const valor: boolean);
    function ReadBool(const seccion, clave: string; const defecto: boolean) : boolean;
    procedure WriteDateTime(const seccion, clave: string; const valor: TDateTime);
    function ReadDateTime(const seccion, clave: string; const defecto: TDateTime) : TDateTime;
    procedure WriteFloat(const seccion, clave: string; valor: Double);
    function ReadFloat(const seccion, clave: string; const defecto: Double) : Double;
  end;

implementation

// Recursos/cadenas
//
{$I ..\inc\rsDecComp.inc}

{ TXmlComoIni }

// Constructor del componente.
//
constructor TXmlComoIni.Create(AOwner: TComponent);
begin
  inherited;
  FFileName := rsFileName;
  if not (csDesigning in ComponentState) then
  begin
    CrearDocXml;
    FFileName := ChangeFileExt(ParamStr(0), rsExtXml);
    AbrirDocXml;
  end;
end;

// Otro constructor del componente: en
// realidad desde el primero, como puede
// verse, llamamos a este otro.
//
constructor TXmlComoIni.Create(AOwner:
  TComponent; const fileName: TFileName);
begin
  CrearDocXml;
  if (fileName <> EmptyStr) then
    FFileName := fileName
  else
    FFileName := ChangeFileExt(ParamStr(0), rsExtXml);
  AbrirDocXml;
end;

// Destructor del componente.
//
destructor TXmlComoIni.Destroy;
begin
  if not (csDesigning in
    ComponentState) then
      GuardarDocXml;
  FDocXml.Free;
  inherited;
end;

// Crear el documento XML.
//
procedure TXmlComoIni.CrearDocXml;
begin
  FDocXml :=  TXMLDocument.Create(Self);
  FDocXml.Options := [doNodeAutoIndent];
end;

// Guardar el documento XML.
//
procedure TXmlComoIni.GuardarDocXml;
begin
  if FDocXml.Modified then
  begin
    FDocXml.SaveToFile(FFileName);
  end;
end;

// Actualizar el archivo XML.
//
procedure TXmlComoIni.UpdateFile;
begin
  GuardarDocXml;
end;

// Abrir el archivo XML.
//
procedure TXmlComoIni.AbrirDocXml;
begin
  if FileExists(FFileName) then
    FDocXml.LoadFromFile(FFileName)
  else
  begin
    FDocXml.Active := true;
    FDocXml.Version := '1.0';
    FDocXml.AddChild(rsRaizXml);
  end;
end;

// Leer el texto contenido en una determinada
// sección (nodo XML) dentro de una determinada
// clave (nodo XML).
//
function TXmlComoIni.ReadString(const
  seccion, clave, defecto: string): string;
var
  nodoClave,
  nodoSeccion: IXMLNode;
begin
  Result := defecto;
  with FDocXml.DocumentElement do
    nodoSeccion := ChildNodes.FindNode(seccion);
  if not Assigned(nodoSeccion) then
    Exit; // No existe la sección
  with nodoSeccion do
    nodoClave := ChildNodes.FindNode(clave);
  if not Assigned(nodoClave) then
    Exit; // No existe la clave
  Result := nodoClave.Text;
end;

// Escribir una cadena en una
// determinada sección y clave.
//
procedure TXmlComoIni.WriteString(const
  seccion, clave, valor: string);
var
  nodoClave,
  nodoSeccion: IXMLNode;
begin
  if ReadString(seccion, clave, EmptyStr) = valor then
    Exit; // El valor a escribir y el actual coinciden
  with FDocXml.DocumentElement do begin
    nodoSeccion := ChildNodes.FindNode(seccion);
    if not Assigned(nodoSeccion) then
      nodoSeccion := AddChild(seccion);
  end;
  with nodoSeccion do begin
    nodoClave := ChildNodes.FindNode(clave);
    if not Assigned(nodoClave) then
      nodoClave := AddChild(clave);
  end;
  nodoClave.Text := valor;
end;

// Leer una cadena del documento XML pero
// devolverla como una valor de tipo Integer.
//
function TXmlComoIni.ReadInteger(const seccion,
  clave: string; const defecto: integer): integer;
begin
  Result := StrToInt(ReadString(
    seccion, clave, IntToStr(defecto)));
end;

// Escribir una cadena en el documento XML
// obteniendo el valor de la misma de un Integer.
//
procedure TXmlComoIni.WriteInteger(const seccion,
  clave: string; const valor: integer);
begin
  WriteString(seccion, clave, IntToStr(valor));
end;

// Leer una cadena del documento XML pero
// devolverla como una valor de tipo TColor.
//
function TXmlComoIni.ReadColor(const seccion,
  clave: string; const defecto: TColor): integer;
begin
  Result := StringToColor(ReadString(
    seccion, clave, ColorToString(defecto)));
end;

// Escribir una cadena en el documento XML
// obteniendo el valor de la misma de un TColor.
//
procedure TXmlComoIni.WriteColor(const seccion,
  clave: string; const valor: TColor);
begin
  WriteString(seccion, clave, ColorToString(valor));
end;

// Leer una cadena del documento XML pero
// devolverla como una valor de tipo boolean.
//
function TXmlComoIni.ReadBool(const seccion,
  clave: string; const defecto: boolean): boolean;
begin
  Result := StrToBool(ReadString(
    seccion, clave, BoolToStr(defecto)));
end;

// Escribir una cadena en el documento XML
// obteniendo el valor de la misma de un boolean.
//
procedure TXmlComoIni.WriteBool(const seccion,
  clave: string; const valor: boolean);
begin
  WriteString(seccion, clave, BoolToStr(valor));
end;

// Leer una cadena del documento XML pero
// devolverla como una valor de tipo TDateTime.
//
function TXmlComoIni.ReadDateTime(const seccion,
  clave: string; const defecto: TDateTime): TDateTime;
begin
  Result := StrToDateTime(ReadString(
    seccion, clave, DateTimeToStr(defecto)));
end;

// Escribir una cadena en el documento XML
// obteniendo el valor de la misma de un TDateTime.
//
procedure TXmlComoIni.WriteDateTime(const seccion,
  clave: string; const valor: TDateTime);
begin
  WriteString(seccion, clave, DateTimeToStr(valor));
end;

// Leer una cadena del documento XML pero
// devolverla como una valor de tipo Double.
//
function TXmlComoIni.ReadFloat(const seccion,
  clave: string; const defecto: Double): Double;
begin
  Result := StrToFloat(ReadString(
    seccion, clave, FloatToStr(defecto)));
end;

// Escribir una cadena en el documento XML
// obteniendo el valor de la misma de un Double.
//
procedure TXmlComoIni.WriteFloat(const
  seccion, clave: string; valor: Double);
begin
  WriteString(seccion, clave, FloatToStr(valor));
end;

// Borrar una determinada clave (nodo XML).
//
procedure TXmlComoIni.DeleteKey(const
  seccion, clave: string);
var
  nodoClave,
  nodoSeccion: IXMLNode;
begin
  with FDocXml.DocumentElement do
    nodoSeccion := ChildNodes.FindNode(seccion);
  if Assigned(nodoSeccion) then
  begin
    nodoClave := nodoSeccion.ChildNodes.FindNode(clave);
    if Assigned(nodoClave) then
      nodoSeccion.ChildNodes.Delete(nodoClave.NodeName);
  end;
end;

// Comprobar la existencia de una
// determinda clave (nodo XML).
//
function TXmlComoIni.KeyExists(const
  seccion, clave: string) : boolean;
var
  nodoSeccion: IXMLNode;
begin
  with FDocXml.DocumentElement do
    nodoSeccion := ChildNodes.FindNode(seccion);
  if Assigned(nodoSeccion) then
  begin
    with nodoSeccion do
      Result := (ChildNodes.IndexOf(clave)<>-1);
  end
  else
    Result := false;
end;

// Comprobar la existencia de una
// determinada sección (nodo XML).
//
function TXmlComoIni.SectionExists(const
  seccion: string) : boolean;
var
  nodoSeccion: IXMLNode;
begin
  with FDocXml.DocumentElement do
    nodoSeccion := ChildNodes.FindNode(seccion);
  Result := Assigned(nodoSeccion);
end;

// Leer los valores (strings) de una determinada
// sección o, como queda dicho, nodo XML. ;-)
// 
procedure TXmlComoIni.ReadSectionValues(const
  seccion: string; strings: TStrings);
var
  i: integer;
  nodoClave,
  nodoSeccion: IXMLNode;
begin
  with FDocXml.DocumentElement do
    nodoSeccion := ChildNodes.FindNode(seccion);
  if Assigned(nodoSeccion) then
  begin
    strings.Clear;
    for i := 0 to nodoSeccion.ChildNodes.Count-1 do
    begin
      nodoClave := nodoSeccion.ChildNodes[i];
      if Assigned(nodoClave)  and
        (nodoClave.IsTextElement) then
          strings.Add(nodoClave.Text);
    end;
  end;
end;

// Leer los nombres de las diferentes secciones.
//
procedure TXmlComoIni.ReadSections(strings: TStrings);
var
  i: integer;
  nodoSeccion: IXMLNode;
begin
  nodoSeccion := FDocXml.DocumentElement;
  if Assigned(nodoSeccion) then
  begin
    strings.Clear;
    for i := 0 to nodoSeccion.ChildNodes.Count-1 do
      strings.Add(nodoSeccion.ChildNodes[i].NodeName);
  end;
end;

// Leer las claves de una determinada sección.
//
procedure TXmlComoIni.ReadSection(const
  seccion: string; strings: TStrings);
var
  i: integer;
  nodoClave,
  nodoSeccion: IXMLNode;
begin
  with FDocXml.DocumentElement do
    nodoSeccion := ChildNodes.FindNode(seccion);
  if Assigned(nodoSeccion) then
  begin
    strings.Clear;
    for i := 0 to nodoSeccion.ChildNodes.Count-1 do
    begin
      nodoClave := nodoSeccion.ChildNodes[i];
      strings.Add(nodoClave.NodeName);
    end;
  end;
end;

// Borrar una sección (nodo XML) completa.
//
procedure TXmlComoIni.DeleteSection(const seccion: string);
var
  nodoSeccion: IXMLNode;
begin
  nodoSeccion := FDocXml.DocumentElement.ChildNodes.FindNode(seccion);
  if Assigned(nodoSeccion) then
    FDocXml.DocumentElement.ChildNodes.Delete(nodoSeccion.NodeName);
end;

end.
__________________
David Esperalta
www.decsoftutils.com
Responder Con Cita