CollectionExtensions
A bunch of methods for getting DOM elements.
using AngleSharp.Dom;
using AngleSharp.Html;
using System;
using System.Collections.Generic;
namespace AngleSharp.Extensions
{
internal static class CollectionExtensions
{
public static IEnumerable<T> Concat<T>(this IEnumerable<T> items, T element)
{
foreach (T item in items) {
yield return item;
}
yield return element;
}
public static IEnumerable<T> GetElements<T>(this INode parent, bool deep = true, Predicate<T> predicate = null) where T : class, INode
{
predicate = (predicate ?? ((Predicate<T>)((T m) => true)));
if (!deep)
return parent.GetDescendendElements(predicate);
return parent.GetAllElements(predicate);
}
public static T GetItemByIndex<T>(this IEnumerable<T> items, int index)
{
if (index >= 0) {
int num = 0;
foreach (T item in items) {
if (num++ == index)
return item;
}
}
throw new ArgumentOutOfRangeException("index");
}
public static IElement GetElementById(this INodeList children, string id)
{
for (int i = 0; i < children.Length; i++) {
IElement element = children[i] as IElement;
if (element != null) {
if (element.Id.Is(id))
return element;
element = element.ChildNodes.GetElementById(id);
if (element != null)
return element;
}
}
return null;
}
public static void GetElementsByName(this INodeList children, string name, List<IElement> result)
{
for (int i = 0; i < children.Length; i++) {
IElement element = children[i] as IElement;
if (element != null) {
if (element.GetAttribute(null, AttributeNames.Name).Is(name))
result.Add(element);
element.ChildNodes.GetElementsByName(name, result);
}
}
}
public static bool Accepts(this FilterSettings filter, INode node)
{
switch (node.NodeType) {
case NodeType.Attribute:
return (filter & FilterSettings.Attribute) == FilterSettings.Attribute;
case NodeType.CharacterData:
return (filter & FilterSettings.CharacterData) == FilterSettings.CharacterData;
case NodeType.Comment:
return (filter & FilterSettings.Comment) == FilterSettings.Comment;
case NodeType.Document:
return (filter & FilterSettings.Document) == FilterSettings.Document;
case NodeType.DocumentFragment:
return (filter & FilterSettings.DocumentFragment) == FilterSettings.DocumentFragment;
case NodeType.DocumentType:
return (filter & FilterSettings.DocumentType) == FilterSettings.DocumentType;
case NodeType.Element:
return (filter & FilterSettings.Element) == FilterSettings.Element;
case NodeType.Entity:
return (filter & FilterSettings.Entity) == FilterSettings.Entity;
case NodeType.EntityReference:
return (filter & FilterSettings.EntityReference) == FilterSettings.EntityReference;
case NodeType.ProcessingInstruction:
return (filter & FilterSettings.ProcessingInstruction) == FilterSettings.ProcessingInstruction;
case NodeType.Notation:
return (filter & FilterSettings.Notation) == FilterSettings.Notation;
case NodeType.Text:
return (filter & FilterSettings.Text) == FilterSettings.Text;
default:
return filter == FilterSettings.All;
}
}
public static IEnumerable<T> GetElements<T>(this INode parent, FilterSettings filter) where T : class, INode
{
return parent.GetElements(true, (T node) => filter.Accepts(node));
}
public static T GetElementById<T>(this IEnumerable<T> elements, string id) where T : class, IElement
{
foreach (T element in elements) {
if (element.Id.Is(id))
return element;
}
foreach (T element2 in elements) {
if (element2.GetAttribute(null, AttributeNames.Name).Is(id))
return element2;
}
return null;
}
private static IEnumerable<T> GetAllElements<T>(this INode parent, Predicate<T> predicate) where T : class, INode
{
for (int i = 0; i < parent.ChildNodes.Length; i++) {
T val = parent.ChildNodes[i] as T;
if (val != null && predicate(val))
yield return val;
foreach (T allElement in CollectionExtensions.GetAllElements<T>(parent.ChildNodes[i], predicate)) {
yield return allElement;
}
}
}
private static IEnumerable<T> GetDescendendElements<T>(this INode parent, Predicate<T> predicate) where T : class, INode
{
for (int i = 0; i < parent.ChildNodes.Length; i++) {
T val = parent.ChildNodes[i] as T;
if (val != null && predicate(val))
yield return val;
}
}
}
}