Explorar o código

Two more DOM Level 3 functions + tests for them:
+ TDOMNode.lookupPrefix()
+ TDOMNode.isDefaultNamespaceURI()

git-svn-id: trunk@13800 -

sergei %!s(int64=16) %!d(string=hai) anos
pai
achega
0c41473f7b
Modificáronse 2 ficheiros con 112 adicións e 33 borrados
  1. 105 31
      packages/fcl-xml/src/dom.pp
  2. 7 2
      packages/fcl-xml/tests/api.xml

+ 105 - 31
packages/fcl-xml/src/dom.pp

@@ -255,7 +255,9 @@ type
     property Prefix: DOMString read GetPrefix write SetPrefix;
     property Prefix: DOMString read GetPrefix write SetPrefix;
     // DOM level 3
     // DOM level 3
     property TextContent: DOMString read GetTextContent write SetTextContent;
     property TextContent: DOMString read GetTextContent write SetTextContent;
+    function LookupPrefix(const nsURI: DOMString): DOMString;
     function LookupNamespaceURI(const APrefix: DOMString): DOMString;
     function LookupNamespaceURI(const APrefix: DOMString): DOMString;
+    function IsDefaultNamespace(const nsURI: DOMString): Boolean;
     // Extensions to DOM interface:
     // Extensions to DOM interface:
     function CloneNode(deep: Boolean; ACloneOwner: TDOMDocument): TDOMNode; overload; virtual;
     function CloneNode(deep: Boolean; ACloneOwner: TDOMDocument): TDOMNode; overload; virtual;
     function FindNode(const ANodeName: DOMString): TDOMNode; virtual;
     function FindNode(const ANodeName: DOMString): TDOMNode; virtual;
@@ -576,6 +578,7 @@ type
     function GetNodeType: Integer; override;
     function GetNodeType: Integer; override;
     function GetAttributes: TDOMNamedNodeMap; override;
     function GetAttributes: TDOMNamedNodeMap; override;
     procedure AttachDefaultAttrs;
     procedure AttachDefaultAttrs;
+    function InternalLookupPrefix(const nsURI: DOMString; Original: TDOMElement): DOMString;
     procedure RestoreDefaultAttr(AttrDef: TDOMAttr);
     procedure RestoreDefaultAttr(AttrDef: TDOMAttr);
   public
   public
     destructor Destroy; override;
     destructor Destroy; override;
@@ -1141,10 +1144,17 @@ function GetAncestorElement(n: TDOMNode): TDOMElement;
 var
 var
   parent: TDOMNode;
   parent: TDOMNode;
 begin
 begin
-  parent := n.ParentNode;
-  while Assigned(parent) and (parent.NodeType <> ELEMENT_NODE) do
-    parent := parent.ParentNode;
-  Result := TDOMElement(parent);
+  case n.nodeType of
+    DOCUMENT_NODE:
+      result := TDOMDocument(n).documentElement;
+    ATTRIBUTE_NODE:
+      result := TDOMAttr(n).OwnerElement;
+  else
+    parent := n.ParentNode;
+    while Assigned(parent) and (parent.NodeType <> ELEMENT_NODE) do
+      parent := parent.ParentNode;
+    Result := TDOMElement(parent);
+  end;  
 end;
 end;
 
 
 // TODO: specs prescribe to return default namespace if APrefix=null,
 // TODO: specs prescribe to return default namespace if APrefix=null,
@@ -1159,40 +1169,74 @@ begin
   Result := '';
   Result := '';
   if Self = nil then
   if Self = nil then
     Exit;
     Exit;
-  case NodeType of
-    ELEMENT_NODE:
+  if nodeType = ELEMENT_NODE then
+  begin
+    if (nfLevel2 in FFlags) and (TDOMElement(Self).Prefix = APrefix) then
     begin
     begin
-      if (nfLevel2 in FFlags) and (TDOMElement(Self).Prefix = APrefix) then
-      begin
-        result := Self.NamespaceURI;
-        Exit;
-      end;
-      if HasAttributes then
+      result := Self.NamespaceURI;
+      Exit;
+    end;
+    if HasAttributes then
+    begin
+      Map := Attributes;
+      for I := 0 to Map.Length-1 do
       begin
       begin
-        Map := Attributes;
-        for I := 0 to Map.Length-1 do
+        Attr := TDOMAttr(Map[I]);
+        // should ignore level 1 atts here
+        if ((Attr.Prefix = 'xmlns') and (Attr.localName = APrefix)) or
+           ((Attr.localName = 'xmlns') and (APrefix = '')) then
         begin
         begin
-          Attr := TDOMAttr(Map[I]);
-          // should ignore level 1 atts here
-          if ((Attr.Prefix = 'xmlns') and (Attr.localName = APrefix)) or
-             ((Attr.localName = 'xmlns') and (APrefix = '')) then
-          begin
-            result := Attr.NodeValue;
-            Exit;
-          end;
-        end
-      end;
-      result := GetAncestorElement(Self).LookupNamespaceURI(APrefix);
+          result := Attr.NodeValue;
+          Exit;
+        end;
+      end
     end;
     end;
-    DOCUMENT_NODE:
-      result := TDOMDocument(Self).documentElement.LookupNamespaceURI(APrefix);
-
-    ATTRIBUTE_NODE:
-      result := TDOMAttr(Self).OwnerElement.LookupNamespaceURI(APrefix);
+  end;  
+  result := GetAncestorElement(Self).LookupNamespaceURI(APrefix);
+end;
 
 
+function TDOMNode.LookupPrefix(const nsURI: DOMString): DOMString;
+begin
+  Result := '';
+  if (nsURI = '') or (Self = nil) then
+    Exit;
+  if nodeType = ELEMENT_NODE then
+    result := TDOMElement(Self).InternalLookupPrefix(nsURI, TDOMElement(Self))
   else
   else
-    Result := GetAncestorElement(Self).LookupNamespaceURI(APrefix);
+    result := GetAncestorElement(Self).LookupPrefix(nsURI);
+end;
+
+function TDOMNode.IsDefaultNamespace(const nsURI: DOMString): Boolean;
+var
+  Attr: TDOMAttr;
+  Map: TDOMNamedNodeMap;
+  I: Integer;
+begin
+  Result := False;
+  if Self = nil then
+    Exit;
+  if nodeType = ELEMENT_NODE then
+  begin
+    if TDOMElement(Self).FNSI.PrefixLen = 0 then
+    begin
+      result := (nsURI = namespaceURI);
+      Exit;
+    end  
+    else if HasAttributes then
+    begin
+      Map := Attributes;
+      for I := 0 to Map.Length-1 do
+      begin
+        Attr := TDOMAttr(Map[I]);
+        if Attr.LocalName = 'xmlns' then
+        begin
+          result := (Attr.Value = nsURI);
+          Exit;
+        end;
+      end;
+    end;
   end;
   end;
+  result := GetAncestorElement(Self).IsDefaultNamespace(nsURI);
 end;
 end;
 
 
 //------------------------------------------------------------------------------
 //------------------------------------------------------------------------------
@@ -2678,6 +2722,36 @@ begin
   end;
   end;
 end;
 end;
 
 
+function TDOMElement.InternalLookupPrefix(const nsURI: DOMString; Original: TDOMElement): DOMString;
+var
+  I: Integer;
+  Attr: TDOMAttr;
+begin
+  result := '';
+  if Self = nil then
+    Exit;
+  if (nfLevel2 in FFlags) and (namespaceURI = nsURI) and (FNSI.PrefixLen > 0) then
+  begin
+    Result := Prefix;
+    if Original.LookupNamespaceURI(result) = nsURI then
+      Exit;
+  end;
+  if Assigned(FAttributes) then
+  begin
+    for I := 0 to FAttributes.Length-1 do
+    begin
+      Attr := TDOMAttr(FAttributes[I]);
+      if (Attr.Prefix = 'xmlns') and (Attr.Value = nsURI) then
+      begin
+        result := Attr.LocalName;
+        if Original.LookupNamespaceURI(result) = nsURI then
+          Exit;
+      end;
+    end;
+  end;
+  result := GetAncestorElement(Self).InternalLookupPrefix(nsURI, Original);
+end;
+
 procedure TDOMElement.RestoreDefaultAttr(AttrDef: TDOMAttr);
 procedure TDOMElement.RestoreDefaultAttr(AttrDef: TDOMAttr);
 var
 var
   Attr: TDOMAttr;
   Attr: TDOMAttr;

+ 7 - 2
packages/fcl-xml/tests/api.xml

@@ -262,6 +262,7 @@
 <item id="isId"/>
 <item id="isId"/>
 <item id="documentURI" type="prop"/>
 <item id="documentURI" type="prop"/>
 <!--
 <!--
+<item id="baseURI"/>
 // assertNotEquals
 // assertNotEquals
 // assertLowerSeverity
 // assertLowerSeverity
 
 
@@ -273,9 +274,13 @@
 <item id="lookupNamespaceURI">
 <item id="lookupNamespaceURI">
   <arg>prefix</arg>
   <arg>prefix</arg>
 </item>
 </item>
+<item id="lookupPrefix">
+  <arg>namespaceURI</arg>
+</item>
+<item id="isDefaultNamespace">
+  <arg>namespaceURI</arg>
+</item>  
 <!--
 <!--
-<item id="lookupPrefix"/>
-<item id="isDefaultNamespace"/>
 <item id="adoptNode"/>
 <item id="adoptNode"/>
 <item id="renameNode"/>
 <item id="renameNode"/>
 <item id="replaceWholeText"/>
 <item id="replaceWholeText"/>