Skip to content

Commit

Permalink
Merge pull request #1010 from SixLabors/feature/visitor
Browse files Browse the repository at this point in the history
Expose visitor through advanced namespace.
  • Loading branch information
JimBobSquarePants authored Sep 17, 2019
2 parents 7cb8a74 + be19bd5 commit 8606c08
Show file tree
Hide file tree
Showing 7 changed files with 50 additions and 30 deletions.
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
// Copyright (c) Six Labors and contributors.
// Licensed under the Apache License, Version 2.0.

using SixLabors.ImageSharp.Advanced;
using SixLabors.ImageSharp.PixelFormats;
using SixLabors.Primitives;

Expand Down
9 changes: 9 additions & 0 deletions src/ImageSharp/Advanced/AdvancedImageExtensions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,15 @@ namespace SixLabors.ImageSharp.Advanced
/// </summary>
public static class AdvancedImageExtensions
{
/// <summary>
/// Accepts a <see cref="IImageVisitor"/> to implement a double-dispatch pattern in order to
/// apply pixel-specific operations on non-generic <see cref="Image"/> instances
/// </summary>
/// <param name="source">The source.</param>
/// <param name="visitor">The visitor.</param>
public static void AcceptVisitor(this Image source, IImageVisitor visitor)
=> source.Accept(visitor);

/// <summary>
/// Gets the configuration for the image.
/// </summary>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,13 @@

using SixLabors.ImageSharp.PixelFormats;

namespace SixLabors.ImageSharp
namespace SixLabors.ImageSharp.Advanced
{
/// <summary>
/// A visitor to implement double-dispatch pattern in order to apply pixel-specific operations
/// on non-generic <see cref="Image"/> instances. The operation is dispatched by <see cref="Image.AcceptVisitor"/>.
/// A visitor to implement a double-dispatch pattern in order to apply pixel-specific operations
/// on non-generic <see cref="Image"/> instances.
/// </summary>
internal interface IImageVisitor
public interface IImageVisitor
{
/// <summary>
/// Provides a pixel-specific implementation for a given operation.
Expand All @@ -19,4 +19,4 @@ internal interface IImageVisitor
void Visit<TPixel>(Image<TPixel> image)
where TPixel : struct, IPixel<TPixel>;
}
}
}
18 changes: 9 additions & 9 deletions src/ImageSharp/Image.cs
Original file line number Diff line number Diff line change
Expand Up @@ -100,8 +100,7 @@ public void Save(Stream stream, IImageEncoder encoder)
Guard.NotNull(encoder, nameof(encoder));
this.EnsureNotDisposed();

var visitor = new EncodeVisitor(encoder, stream);
this.AcceptVisitor(visitor);
this.AcceptVisitor(new EncodeVisitor(encoder, stream));
}

/// <summary>
Expand All @@ -121,13 +120,6 @@ public Image<TPixel2> CloneAs<TPixel2>()
public abstract Image<TPixel2> CloneAs<TPixel2>(Configuration configuration)
where TPixel2 : struct, IPixel<TPixel2>;

/// <summary>
/// Accept a <see cref="IImageVisitor"/>.
/// Implemented by <see cref="Image{TPixel}"/> invoking <see cref="IImageVisitor.Visit{TPixel}"/>
/// with the pixel type of the image.
/// </summary>
internal abstract void AcceptVisitor(IImageVisitor visitor);

/// <summary>
/// Update the size of the image after mutation.
/// </summary>
Expand All @@ -145,6 +137,14 @@ public abstract Image<TPixel2> CloneAs<TPixel2>(Configuration configuration)
/// </summary>
internal abstract void EnsureNotDisposed();

/// <summary>
/// Accepts a <see cref="IImageVisitor"/>.
/// Implemented by <see cref="Image{TPixel}"/> invoking <see cref="IImageVisitor.Visit{TPixel}"/>
/// with the pixel type of the image.
/// </summary>
/// <param name="visitor">The visitor.</param>
internal abstract void Accept(IImageVisitor visitor);

private class EncodeVisitor : IImageVisitor
{
private readonly IImageEncoder encoder;
Expand Down
8 changes: 4 additions & 4 deletions src/ImageSharp/Image{TPixel}.cs
Original file line number Diff line number Diff line change
Expand Up @@ -211,17 +211,17 @@ internal override void EnsureNotDisposed()
}
}

/// <inheritdoc/>
public override string ToString() => $"Image<{typeof(TPixel).Name}>: {this.Width}x{this.Height}";

/// <inheritdoc />
internal override void AcceptVisitor(IImageVisitor visitor)
internal override void Accept(IImageVisitor visitor)
{
this.EnsureNotDisposed();

visitor.Visit(this);
}

/// <inheritdoc/>
public override string ToString() => $"Image<{typeof(TPixel).Name}>: {this.Width}x{this.Height}";

/// <summary>
/// Switches the buffers used by the image and the pixelSource meaning that the Image will "own" the buffer from the pixelSource and the pixelSource will now own the Images buffer.
/// </summary>
Expand Down
33 changes: 21 additions & 12 deletions src/ImageSharp/Processing/Extensions/ProcessingExtensions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -25,8 +25,7 @@ public static void Mutate(this Image source, Action<IImageProcessingContext> ope
Guard.NotNull(operation, nameof(operation));
source.EnsureNotDisposed();

var visitor = new ProcessingVisitor(operation, true);
source.AcceptVisitor(visitor);
source.AcceptVisitor(new ProcessingVisitor(operation, true));
}

/// <summary>
Expand All @@ -42,8 +41,10 @@ public static void Mutate<TPixel>(this Image<TPixel> source, Action<IImageProces
Guard.NotNull(operation, nameof(operation));
source.EnsureNotDisposed();

IInternalImageProcessingContext<TPixel> operationsRunner = source.GetConfiguration().ImageOperationsProvider
.CreateImageProcessingContext(source, true);
IInternalImageProcessingContext<TPixel> operationsRunner
= source.GetConfiguration()
.ImageOperationsProvider.CreateImageProcessingContext(source, true);

operation(operationsRunner);
}

Expand All @@ -60,8 +61,10 @@ public static void Mutate<TPixel>(this Image<TPixel> source, params IImageProces
Guard.NotNull(operations, nameof(operations));
source.EnsureNotDisposed();

IInternalImageProcessingContext<TPixel> operationsRunner = source.GetConfiguration().ImageOperationsProvider
.CreateImageProcessingContext(source, true);
IInternalImageProcessingContext<TPixel> operationsRunner
= source.GetConfiguration()
.ImageOperationsProvider.CreateImageProcessingContext(source, true);

operationsRunner.ApplyProcessors(operations);
}

Expand Down Expand Up @@ -96,8 +99,10 @@ public static Image<TPixel> Clone<TPixel>(this Image<TPixel> source, Action<IIma
Guard.NotNull(operation, nameof(operation));
source.EnsureNotDisposed();

IInternalImageProcessingContext<TPixel> operationsRunner = source.GetConfiguration().ImageOperationsProvider
.CreateImageProcessingContext(source, false);
IInternalImageProcessingContext<TPixel> operationsRunner
= source.GetConfiguration()
.ImageOperationsProvider.CreateImageProcessingContext(source, false);

operation(operationsRunner);
return operationsRunner.GetResultImage();
}
Expand All @@ -116,8 +121,10 @@ public static Image<TPixel> Clone<TPixel>(this Image<TPixel> source, params IIma
Guard.NotNull(operations, nameof(operations));
source.EnsureNotDisposed();

IInternalImageProcessingContext<TPixel> operationsRunner = source.GetConfiguration().ImageOperationsProvider
.CreateImageProcessingContext(source, false);
IInternalImageProcessingContext<TPixel> operationsRunner
= source.GetConfiguration()
.ImageOperationsProvider.CreateImageProcessingContext(source, false);

operationsRunner.ApplyProcessors(operations);
return operationsRunner.GetResultImage();
}
Expand Down Expand Up @@ -157,8 +164,10 @@ public ProcessingVisitor(Action<IImageProcessingContext> operation, bool mutate)
public void Visit<TPixel>(Image<TPixel> image)
where TPixel : struct, IPixel<TPixel>
{
IInternalImageProcessingContext<TPixel> operationsRunner = image.GetConfiguration()
.ImageOperationsProvider.CreateImageProcessingContext(image, this.mutate);
IInternalImageProcessingContext<TPixel> operationsRunner =
image.GetConfiguration()
.ImageOperationsProvider.CreateImageProcessingContext(image, this.mutate);

this.operation(operationsRunner);
this.ResultImage = operationsRunner.GetResultImage();
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
// Copyright (c) Six Labors and contributors.
// Licensed under the Apache License, Version 2.0.

using SixLabors.ImageSharp.Advanced;
using SixLabors.ImageSharp.PixelFormats;
using SixLabors.Primitives;

Expand Down

0 comments on commit 8606c08

Please sign in to comment.