BrowsingContext
A simple and lightweight browsing context.
using AngleSharp.Browser;
using AngleSharp.Browser.Dom;
using AngleSharp.Dom;
using System;
using System.Collections.Generic;
namespace AngleSharp
{
public sealed class BrowsingContext : EventTarget, IBrowsingContext, IEventTarget, IDisposable
{
private readonly IEnumerable<object> _originalServices;
private readonly List<object> _services;
private readonly Sandboxes _security;
private readonly IBrowsingContext _parent;
private readonly IDocument _creator;
private readonly IHistory _history;
private readonly Dictionary<string, WeakReference<IBrowsingContext>> _children;
public IDocument Active { get; set; }
public IDocument Creator => _creator;
public IEnumerable<object> OriginalServices => _originalServices;
public IWindow Current => Active?.DefaultView;
public IBrowsingContext Parent => _parent;
public IHistory SessionHistory => _history;
public Sandboxes Security => _security;
public BrowsingContext(IConfiguration configuration = null)
: this((configuration ?? Configuration.Default).Services, Sandboxes.None)
{
}
private BrowsingContext(Sandboxes security)
{
_services = new List<object>();
_originalServices = _services;
_security = security;
_children = new Dictionary<string, WeakReference<IBrowsingContext>>();
}
internal BrowsingContext(IEnumerable<object> services, Sandboxes security)
: this(security)
{
_services.AddRange(services);
_originalServices = services;
_history = GetService<IHistory>();
}
internal BrowsingContext(IBrowsingContext parent, Sandboxes security)
: this(parent.OriginalServices, security)
{
_parent = parent;
_creator = _parent.Active;
}
public T GetService<T>() where T : class
{
int count = _services.Count;
int num = 0;
while (num < count) {
object obj = _services[num];
T val = obj as T;
if (val == null) {
Func<IBrowsingContext, T> func = obj as Func<IBrowsingContext, T>;
if (func == null) {
num++;
continue;
}
val = func(this);
_services[num] = val;
}
return val;
}
return null;
}
public IEnumerable<T> GetServices<T>() where T : class
{
int count = _services.Count;
for (int i = 0; i < count; i++) {
object obj = _services[i];
T val = obj as T;
if (val == null) {
Func<IBrowsingContext, T> func = obj as Func<IBrowsingContext, T>;
if (func == null)
continue;
val = func(this);
_services[i] = val;
}
yield return val;
}
}
public IBrowsingContext CreateChild(string name, Sandboxes security)
{
BrowsingContext browsingContext = new BrowsingContext(this, security);
if (!string.IsNullOrEmpty(name))
_children[name] = new WeakReference<IBrowsingContext>(browsingContext);
return browsingContext;
}
public IBrowsingContext FindChild(string name)
{
IBrowsingContext target = null;
if (!string.IsNullOrEmpty(name) && _children.TryGetValue(name, out WeakReference<IBrowsingContext> value))
value.TryGetTarget(out target);
return target;
}
public static IBrowsingContext New(IConfiguration configuration = null)
{
if (configuration == null)
configuration = Configuration.Default;
return new BrowsingContext(configuration.Services, Sandboxes.None);
}
public static IBrowsingContext NewFrom<TService>(TService instance)
{
return new BrowsingContext(Configuration.Default.WithOnly(instance).Services, Sandboxes.None);
}
void IDisposable.Dispose()
{
Active?.Dispose();
Active = null;
}
}
}