mirror of
https://gitlab.com/freepascal.org/fpc/source.git
synced 2025-12-06 15:07:27 +01:00
* Modified helper TLoader class to access reader node data via an interface, instead of using fields directly.
git-svn-id: trunk@20777 -
This commit is contained in:
parent
34a4ee46ff
commit
bed154d366
@ -276,7 +276,7 @@ type
|
|||||||
|
|
||||||
TEntityEvent = procedure(Sender: TXMLTextReader; AEntity: TEntityDecl) of object;
|
TEntityEvent = procedure(Sender: TXMLTextReader; AEntity: TEntityDecl) of object;
|
||||||
|
|
||||||
TXMLTextReader = class(TXMLReader, IXmlLineInfo)
|
TXMLTextReader = class(TXMLReader, IXmlLineInfo, IGetNodeDataPtr)
|
||||||
private
|
private
|
||||||
FSource: TXMLCharSource;
|
FSource: TXMLCharSource;
|
||||||
FNameTable: THashTable;
|
FNameTable: THashTable;
|
||||||
@ -406,6 +406,7 @@ type
|
|||||||
function GetHasLineInfo: Boolean;
|
function GetHasLineInfo: Boolean;
|
||||||
function GetLineNumber: Integer;
|
function GetLineNumber: Integer;
|
||||||
function GetLinePosition: Integer;
|
function GetLinePosition: Integer;
|
||||||
|
function CurrentNodePtr: PPNodeData;
|
||||||
public
|
public
|
||||||
function Read: Boolean; override;
|
function Read: Boolean; override;
|
||||||
function MoveToFirstAttribute: Boolean; override;
|
function MoveToFirstAttribute: Boolean; override;
|
||||||
@ -473,13 +474,16 @@ type
|
|||||||
destructor Destroy; override;
|
destructor Destroy; override;
|
||||||
procedure AfterConstruction; override;
|
procedure AfterConstruction; override;
|
||||||
property OnEntity: TEntityEvent read FOnEntity write FOnEntity;
|
property OnEntity: TEntityEvent read FOnEntity write FOnEntity;
|
||||||
|
{ needed for TLoader }
|
||||||
|
property Standalone: Boolean read FStandalone write FStandalone;
|
||||||
|
property DtdSchemaInfo: TDTDModel read FDocType write FDocType;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
TLoader = object
|
TLoader = object
|
||||||
doc: TDOMDocument;
|
doc: TDOMDocument;
|
||||||
reader: TXMLTextReader;
|
reader: TXMLTextReader;
|
||||||
function DoCDSect(ch: PWideChar; Count: Integer): TDOMNode;
|
function CreateCDATANode(currnode: PNodeData): TDOMNode;
|
||||||
function CreatePINode: TDOMNode;
|
function CreatePINode(currnode: PNodeData): TDOMNode;
|
||||||
procedure ParseContent(cursor: TDOMNode_WithChildren);
|
procedure ParseContent(cursor: TDOMNode_WithChildren);
|
||||||
|
|
||||||
procedure ProcessXML(ADoc: TDOMDocument; AReader: TXMLTextReader);
|
procedure ProcessXML(ADoc: TDOMDocument; AReader: TXMLTextReader);
|
||||||
@ -1329,7 +1333,7 @@ begin
|
|||||||
Inc(FSource.FBuf);
|
Inc(FSource.FBuf);
|
||||||
if FSource.FBuf >= FSource.FBufEnd then
|
if FSource.FBuf >= FSource.FBufEnd then
|
||||||
FSource.Reload;
|
FSource.Reload;
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TXMLTextReader.SkipQuote(out Delim: WideChar; required: Boolean);
|
procedure TXMLTextReader.SkipQuote(out Delim: WideChar; required: Boolean);
|
||||||
@ -1502,7 +1506,7 @@ begin
|
|||||||
reader.FState := rsProlog;
|
reader.FState := rsProlog;
|
||||||
reader.FFragmentMode := False;
|
reader.FFragmentMode := False;
|
||||||
ParseContent(doc);
|
ParseContent(doc);
|
||||||
doc.XMLStandalone := reader.FStandalone;
|
doc.XMLStandalone := reader.Standalone;
|
||||||
|
|
||||||
if reader.FValidate then
|
if reader.FValidate then
|
||||||
reader.ValidateIdRefs;
|
reader.ValidateIdRefs;
|
||||||
@ -1523,7 +1527,7 @@ begin
|
|||||||
reader.FXML11 := doc.XMLVersion = '1.1';
|
reader.FXML11 := doc.XMLVersion = '1.1';
|
||||||
DoctypeNode := TDOMDocumentTypeEx(doc.DocType);
|
DoctypeNode := TDOMDocumentTypeEx(doc.DocType);
|
||||||
if Assigned(DoctypeNode) then
|
if Assigned(DoctypeNode) then
|
||||||
reader.FDocType := DocTypeNode.FModel.Reference;
|
reader.DtdSchemaInfo := DocTypeNode.FModel.Reference;
|
||||||
ParseContent(aOwner as TDOMNode_WithChildren);
|
ParseContent(aOwner as TDOMNode_WithChildren);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@ -1559,7 +1563,10 @@ end;
|
|||||||
procedure TLoader.ParseContent(cursor: TDOMNode_WithChildren);
|
procedure TLoader.ParseContent(cursor: TDOMNode_WithChildren);
|
||||||
var
|
var
|
||||||
element: TDOMElement;
|
element: TDOMElement;
|
||||||
|
currnodeptr: PPNodeData;
|
||||||
|
currnode: PNodeData;
|
||||||
begin
|
begin
|
||||||
|
currnodeptr := (reader as IGetNodeDataPtr).CurrentNodePtr;
|
||||||
if reader.ReadState = rsInitial then
|
if reader.ReadState = rsInitial then
|
||||||
begin
|
begin
|
||||||
if not reader.Read then
|
if not reader.Read then
|
||||||
@ -1577,27 +1584,28 @@ begin
|
|||||||
if FValidate then
|
if FValidate then
|
||||||
ValidateCurrentNode;
|
ValidateCurrentNode;
|
||||||
|
|
||||||
case FCurrNode^.FNodeType of
|
currnode := currnodeptr^;
|
||||||
|
case currnode^.FNodeType of
|
||||||
ntText:
|
ntText:
|
||||||
cursor.InternalAppend(doc.CreateTextNodeBuf(FValue.Buffer, FValue.Length, False));
|
cursor.InternalAppend(doc.CreateTextNodeBuf(currnode^.FValueStart, currnode^.FValueLength, False));
|
||||||
|
|
||||||
ntWhitespace, ntSignificantWhitespace:
|
ntWhitespace, ntSignificantWhitespace:
|
||||||
if FPreserveWhitespace then
|
if FPreserveWhitespace then
|
||||||
cursor.InternalAppend(doc.CreateTextNodeBuf(FValue.Buffer, FValue.Length, FCurrNode^.FNodeType = ntWhitespace));
|
cursor.InternalAppend(doc.CreateTextNodeBuf(currnode^.FValueStart, currnode^.FValueLength, currnode^.FNodeType = ntWhitespace));
|
||||||
|
|
||||||
ntCDATA:
|
ntCDATA:
|
||||||
cursor.InternalAppend(DoCDSect(FValue.Buffer, FValue.Length));
|
cursor.InternalAppend(CreateCDATANode(currnode));
|
||||||
|
|
||||||
ntProcessingInstruction:
|
ntProcessingInstruction:
|
||||||
cursor.InternalAppend(CreatePINode);
|
cursor.InternalAppend(CreatePINode(currnode));
|
||||||
|
|
||||||
ntComment:
|
ntComment:
|
||||||
if not FIgnoreComments then
|
if not FIgnoreComments then
|
||||||
cursor.InternalAppend(doc.CreateCommentBuf(FCurrNode^.FValueStart, FCurrNode^.FValueLength));
|
cursor.InternalAppend(doc.CreateCommentBuf(currnode^.FValueStart, currnode^.FValueLength));
|
||||||
|
|
||||||
ntElement:
|
ntElement:
|
||||||
begin
|
begin
|
||||||
element := LoadElement(doc, FCurrNode, reader.FAttrCount);
|
element := LoadElement(doc, currnode, reader.FAttrCount);
|
||||||
cursor.InternalAppend(element);
|
cursor.InternalAppend(element);
|
||||||
cursor := element;
|
cursor := element;
|
||||||
end;
|
end;
|
||||||
@ -1606,11 +1614,11 @@ begin
|
|||||||
cursor := TDOMNode_WithChildren(cursor.ParentNode);
|
cursor := TDOMNode_WithChildren(cursor.ParentNode);
|
||||||
|
|
||||||
ntDocumentType:
|
ntDocumentType:
|
||||||
cursor.InternalAppend(TDOMDocumentType.Create(doc, FDocType));
|
cursor.InternalAppend(TDOMDocumentType.Create(doc, DtdSchemaInfo));
|
||||||
|
|
||||||
ntEntityReference:
|
ntEntityReference:
|
||||||
begin
|
begin
|
||||||
cursor.InternalAppend(doc.CreateEntityReference(FCurrNode^.FQName^.Key));
|
cursor.InternalAppend(doc.CreateEntityReference(currnode^.FQName^.Key));
|
||||||
{ Seeing an entity reference while expanding means that the entity
|
{ Seeing an entity reference while expanding means that the entity
|
||||||
fails to expand. }
|
fails to expand. }
|
||||||
if not FExpandEntities then
|
if not FExpandEntities then
|
||||||
@ -1618,7 +1626,7 @@ begin
|
|||||||
{ Make reader iterate through contents of the reference,
|
{ Make reader iterate through contents of the reference,
|
||||||
to ensure correct validation events and character counts. }
|
to ensure correct validation events and character counts. }
|
||||||
ResolveEntity;
|
ResolveEntity;
|
||||||
while FCurrNode^.FNodeType <> ntEndEntity do
|
while currnodeptr^^.FNodeType <> ntEndEntity do
|
||||||
Read;
|
Read;
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
@ -1626,20 +1634,19 @@ begin
|
|||||||
until not Read;
|
until not Read;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TLoader.CreatePINode: TDOMNode;
|
function TLoader.CreatePINode(currnode: PNodeData): TDOMNode;
|
||||||
var
|
var
|
||||||
NameStr, ValueStr: DOMString;
|
s: DOMString;
|
||||||
begin
|
begin
|
||||||
SetString(NameStr, reader.FName.Buffer, reader.FName.Length);
|
SetString(s, currnode^.FValueStart, currnode^.FValueLength);
|
||||||
SetString(ValueStr, reader.FValue.Buffer, reader.FValue.Length);
|
result := Doc.CreateProcessingInstruction(currnode^.FQName^.Key, s);
|
||||||
result := Doc.CreateProcessingInstruction(NameStr, ValueStr);
|
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TLoader.DoCDSect(ch: PWideChar; Count: Integer): TDOMNode;
|
function TLoader.CreateCDATANode(currnode: PNodeData): TDOMNode;
|
||||||
var
|
var
|
||||||
s: XMLString;
|
s: XMLString;
|
||||||
begin
|
begin
|
||||||
SetString(s, ch, Count);
|
SetString(s, currnode^.FValueStart, currnode^.FValueLength);
|
||||||
result := doc.CreateCDATASection(s);
|
result := doc.CreateCDATASection(s);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@ -1754,7 +1761,7 @@ begin
|
|||||||
else if (Length = 4) and (Buffer[1] = 'p') and (Buffer[2] = 'o') and
|
else if (Length = 4) and (Buffer[1] = 'p') and (Buffer[2] = 'o') and
|
||||||
(Buffer[3] = 's') then
|
(Buffer[3] = 's') then
|
||||||
wc := ''''
|
wc := ''''
|
||||||
else Exit;
|
else Exit;
|
||||||
end
|
end
|
||||||
else if (Length = 4) and (Buffer[0] = 'q') and (Buffer[1] = 'u') and
|
else if (Length = 4) and (Buffer[0] = 'q') and (Buffer[1] = 'u') and
|
||||||
(Buffer[2] = 'o') and (Buffer[3] ='t') then
|
(Buffer[2] = 'o') and (Buffer[3] ='t') then
|
||||||
@ -2905,9 +2912,9 @@ end;
|
|||||||
|
|
||||||
procedure TLoader.ProcessDTD(ADoc: TDOMDocument; AReader: TXMLTextReader);
|
procedure TLoader.ProcessDTD(ADoc: TDOMDocument; AReader: TXMLTextReader);
|
||||||
begin
|
begin
|
||||||
AReader.FDocType := TDTDModel.Create(AReader.FNameTable);
|
AReader.DtdSchemaInfo := TDTDModel.Create(AReader.FNameTable);
|
||||||
// TODO: DTD labeled version 1.1 will be rejected - must set FXML11 flag
|
// TODO: DTD labeled version 1.1 will be rejected - must set FXML11 flag
|
||||||
doc.AppendChild(TDOMDocumentType.Create(doc, AReader.FDocType));
|
doc.AppendChild(TDOMDocumentType.Create(doc, AReader.DtdSchemaInfo));
|
||||||
AReader.FSource.Initialize;
|
AReader.FSource.Initialize;
|
||||||
AReader.ParseMarkupDecl;
|
AReader.ParseMarkupDecl;
|
||||||
end;
|
end;
|
||||||
@ -3033,6 +3040,11 @@ begin
|
|||||||
result := FTokenStart.LinePos;
|
result := FTokenStart.LinePos;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
function TXMLTextReader.CurrentNodePtr: PPNodeData;
|
||||||
|
begin
|
||||||
|
result := @FCurrNode;
|
||||||
|
end;
|
||||||
|
|
||||||
function TXMLTextReader.LookupNamespace(const APrefix: XMLString): XMLString;
|
function TXMLTextReader.LookupNamespace(const APrefix: XMLString): XMLString;
|
||||||
begin
|
begin
|
||||||
if Assigned(FNSHelper) then
|
if Assigned(FNSHelper) then
|
||||||
|
|||||||
@ -158,6 +158,7 @@ type
|
|||||||
|
|
||||||
{ generic node info record, shared between DOM and reader }
|
{ generic node info record, shared between DOM and reader }
|
||||||
|
|
||||||
|
PPNodeData = ^PNodeData;
|
||||||
PNodeData = ^TNodeData;
|
PNodeData = ^TNodeData;
|
||||||
TNodeData = record
|
TNodeData = record
|
||||||
FNext: PNodeData;
|
FNext: PNodeData;
|
||||||
@ -178,6 +179,10 @@ type
|
|||||||
FDenormalized: Boolean; // Whether attribute value changes by normalization
|
FDenormalized: Boolean; // Whether attribute value changes by normalization
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
IGetNodeDataPtr = interface(IInterface)['{81F6ADA2-8F5E-41D7-872D-226163FF4E45}']
|
||||||
|
function CurrentNodePtr: PPNodeData;
|
||||||
|
end;
|
||||||
|
|
||||||
{ TNSSupport provides tracking of prefix-uri pairs and namespace fixup for writer }
|
{ TNSSupport provides tracking of prefix-uri pairs and namespace fixup for writer }
|
||||||
|
|
||||||
TBinding = class
|
TBinding = class
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user