|
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.
using System;
using System.Collections;
using System.Diagnostics;
using System.Xml;
using System.Xml.XPath;
namespace System.Xml.Xsl.XsltOld
{
internal sealed class TemplateManager
{
private readonly XmlQualifiedName _mode;
internal ArrayList? templates;
private readonly Stylesheet _stylesheet; // Owning stylesheet
private sealed class TemplateComparer : IComparer
{
public int Compare(object? x, object? y)
{
Debug.Assert(x != null && x is TemplateAction);
Debug.Assert(y != null && y is TemplateAction);
TemplateAction tx = (TemplateAction)x;
TemplateAction ty = (TemplateAction)y;
Debug.Assert(!double.IsNaN(tx.Priority));
Debug.Assert(!double.IsNaN(ty.Priority));
if (tx.Priority == ty.Priority)
{
Debug.Assert(tx.TemplateId != ty.TemplateId || tx == ty);
return tx.TemplateId - ty.TemplateId;
}
else
{
return tx.Priority > ty.Priority ? 1 : -1;
}
}
}
private static readonly TemplateComparer s_TemplateComparer = new TemplateComparer();
internal XmlQualifiedName Mode
{
get { return _mode; }
}
internal TemplateManager(Stylesheet stylesheet, XmlQualifiedName mode)
{
_mode = mode;
_stylesheet = stylesheet;
}
internal void AddTemplate(TemplateAction template)
{
Debug.Assert(template != null);
Debug.Assert(
((object)_mode == (object?)template.Mode) ||
(template.Mode == null && _mode.Equals(XmlQualifiedName.Empty)) ||
_mode.Equals(template.Mode)
);
this.templates ??= new ArrayList();
this.templates.Add(template);
}
internal void ProcessTemplates()
{
this.templates?.Sort(s_TemplateComparer);
}
internal TemplateAction? FindTemplate(Processor processor, XPathNavigator navigator)
{
if (this.templates == null)
{
return null;
}
Debug.Assert(this.templates != null);
for (int templateIndex = this.templates.Count - 1; templateIndex >= 0; templateIndex--)
{
TemplateAction action = (TemplateAction)this.templates[templateIndex]!;
int matchKey = action.MatchKey;
if (matchKey != Compiler.InvalidQueryKey)
{
if (processor.Matches(navigator, matchKey))
{
return action;
}
}
}
return null;
}
}
}
|