mirror of https://github.com/SixLabors/ImageSharp
15 changed files with 573 additions and 83 deletions
@ -0,0 +1,35 @@ |
|||
// Copyright (c) Six Labors.
|
|||
// Licensed under the Six Labors Split License.
|
|||
|
|||
namespace SixLabors.ImageSharp.Formats; |
|||
|
|||
/// <summary>
|
|||
/// A metadata format designed to allow conversion between different image format frames.
|
|||
/// </summary>
|
|||
public class FormatConnectingFrameMetadata |
|||
{ |
|||
/// <summary>
|
|||
/// Gets or sets the frame color table.
|
|||
/// </summary>
|
|||
public ReadOnlyMemory<Color>? ColorTable { get; set; } |
|||
|
|||
/// <summary>
|
|||
/// Gets or sets the frame color table mode.
|
|||
/// </summary>
|
|||
public FrameColorTableMode ColorTableMode { get; set; } |
|||
|
|||
/// <summary>
|
|||
/// Gets or sets the duration of the frame.
|
|||
/// </summary>
|
|||
public TimeSpan Duration { get; set; } |
|||
|
|||
/// <summary>
|
|||
/// Gets or sets the frame alpha blending mode.
|
|||
/// </summary>
|
|||
public FrameBlendMode BlendMode { get; set; } |
|||
|
|||
/// <summary>
|
|||
/// Gets or sets the frame disposal mode.
|
|||
/// </summary>
|
|||
public FrameDisposalMode DisposalMode { get; set; } |
|||
} |
|||
@ -0,0 +1,65 @@ |
|||
// Copyright (c) Six Labors.
|
|||
// Licensed under the Six Labors Split License.
|
|||
|
|||
using SixLabors.ImageSharp.PixelFormats; |
|||
|
|||
namespace SixLabors.ImageSharp.Formats; |
|||
|
|||
/// <summary>
|
|||
/// A metadata format designed to allow conversion between different image formats.
|
|||
/// </summary>
|
|||
public class FormatConnectingMetadata |
|||
{ |
|||
/// <summary>
|
|||
/// Gets the quality.
|
|||
/// </summary>
|
|||
/// <remarks>
|
|||
/// The value is usually between 1 and 100. Defaults to 100.
|
|||
/// </remarks>
|
|||
public int Quality { get; init; } = 100; |
|||
|
|||
/// <summary>
|
|||
/// Gets information about the encoded pixel type.
|
|||
/// </summary>
|
|||
public PixelTypeInfo PixelTypeInfo { get; init; } |
|||
|
|||
/// <summary>
|
|||
/// Gets the shared color table.
|
|||
/// </summary>
|
|||
public ReadOnlyMemory<Color>? ColorTable { get; init; } |
|||
|
|||
/// <summary>
|
|||
/// Gets the shared color table mode.
|
|||
/// </summary>
|
|||
/// <remarks>
|
|||
/// Defaults to <see cref="FrameColorTableMode.Global"/>.
|
|||
/// </remarks>
|
|||
public FrameColorTableMode ColorTableMode { get; init; } |
|||
|
|||
/// <summary>
|
|||
/// Gets the default background color of the canvas when animating.
|
|||
/// This color may be used to fill the unused space on the canvas around the frames,
|
|||
/// as well as the transparent pixels of the first frame.
|
|||
/// The background color is also used when the disposal mode is <see cref="FrameDisposalMode.RestoreToBackground"/>.
|
|||
/// </summary>
|
|||
/// <remarks>
|
|||
/// Defaults to <see cref="Color.Transparent"/>.
|
|||
/// </remarks>
|
|||
public Color BackgroundColor { get; init; } = Color.Transparent; |
|||
|
|||
/// <summary>
|
|||
/// Gets the number of times any animation is repeated.
|
|||
/// </summary>
|
|||
/// <remarks>
|
|||
/// 0 means to repeat indefinitely, count is set as repeat n-1 times. Defaults to 1.
|
|||
/// </remarks>
|
|||
public ushort RepeatCount { get; init; } = 1; |
|||
|
|||
/// <summary>
|
|||
/// Gets a value indicating whether the root frame is shown as part of the animated sequence.
|
|||
/// </summary>
|
|||
/// <remarks>
|
|||
/// Defaults to <see langword="true"/>.
|
|||
/// </remarks>
|
|||
public bool AnimateRootFrame { get; init; } = true; |
|||
} |
|||
@ -0,0 +1,23 @@ |
|||
// Copyright (c) Six Labors.
|
|||
// Licensed under the Six Labors Split License.
|
|||
|
|||
namespace SixLabors.ImageSharp.Formats; |
|||
|
|||
/// <summary>
|
|||
/// Provides a way to specify how the current frame should be blended with the previous frame in the animation sequence.
|
|||
/// </summary>
|
|||
public enum FrameBlendMode |
|||
{ |
|||
/// <summary>
|
|||
/// Do not blend. Render the current frame on the canvas by overwriting the rectangle covered by the current frame.
|
|||
/// </summary>
|
|||
Source = 0, |
|||
|
|||
/// <summary>
|
|||
/// Blend the current frame with the previous frame in the animation sequence within the rectangle covered
|
|||
/// by the current frame.
|
|||
/// If the current has any transparent areas, the corresponding areas of the previous frame will be visible
|
|||
/// through these transparent regions.
|
|||
/// </summary>
|
|||
Over = 1 |
|||
} |
|||
@ -0,0 +1,20 @@ |
|||
// Copyright (c) Six Labors.
|
|||
// Licensed under the Six Labors Split License.
|
|||
|
|||
namespace SixLabors.ImageSharp.Formats; |
|||
|
|||
/// <summary>
|
|||
/// Provides a way to specify how the color table is used by the frame.
|
|||
/// </summary>
|
|||
public enum FrameColorTableMode |
|||
{ |
|||
/// <summary>
|
|||
/// The frame uses the shared color table specified by the image metadata.
|
|||
/// </summary>
|
|||
Global, |
|||
|
|||
/// <summary>
|
|||
/// The frame uses a color table specified by the frame metadata.
|
|||
/// </summary>
|
|||
Local |
|||
} |
|||
@ -0,0 +1,38 @@ |
|||
// Copyright (c) Six Labors.
|
|||
// Licensed under the Six Labors Split License.
|
|||
|
|||
namespace SixLabors.ImageSharp.Formats; |
|||
|
|||
/// <summary>
|
|||
/// Provides a way to specify how the current frame should be disposed of before rendering the next frame.
|
|||
/// </summary>
|
|||
public enum FrameDisposalMode |
|||
{ |
|||
/// <summary>
|
|||
/// No disposal specified.
|
|||
/// The decoder is not required to take any action.
|
|||
/// </summary>
|
|||
Unspecified = 0, |
|||
|
|||
/// <summary>
|
|||
/// Do not dispose. The current frame is not disposed of, or in other words, not cleared or altered when moving to
|
|||
/// the next frame. This means that the next frame is drawn over the current frame, and if the next frame contains
|
|||
/// transparency, the previous frame will be visible through these transparent areas.
|
|||
/// </summary>
|
|||
DoNotDispose = 1, |
|||
|
|||
/// <summary>
|
|||
/// Restore to background color. When transitioning to the next frame, the area occupied by the current frame is
|
|||
/// filled with the background color specified in the image metadata.
|
|||
/// This effectively erases the current frame by replacing it with the background color before the next frame is displayed.
|
|||
/// </summary>
|
|||
RestoreToBackground = 2, |
|||
|
|||
/// <summary>
|
|||
/// Restore to previous. This method restores the area affected by the current frame to what it was before the
|
|||
/// current frame was displayed. It essentially "undoes" the current frame, reverting to the state of the image
|
|||
/// before the frame was displayed, then the next frame is drawn. This is useful for animations where only a small
|
|||
/// part of the image changes from frame to frame.
|
|||
/// </summary>
|
|||
RestoreToPrevious = 3 |
|||
} |
|||
@ -0,0 +1,33 @@ |
|||
// Copyright (c) Six Labors.
|
|||
// Licensed under the Six Labors Split License.
|
|||
|
|||
namespace SixLabors.ImageSharp.Formats; |
|||
|
|||
/// <summary>
|
|||
/// An interface that provides metadata for a specific image format frames.
|
|||
/// </summary>
|
|||
public interface IFormatFrameMetadata : IDeepCloneable |
|||
{ |
|||
/// <summary>
|
|||
/// Converts the metadata to a <see cref="FormatConnectingFrameMetadata"/> instance.
|
|||
/// </summary>
|
|||
/// <returns>The <see cref="FormatConnectingFrameMetadata"/>.</returns>
|
|||
FormatConnectingFrameMetadata ToFormatConnectingFrameMetadata(); |
|||
} |
|||
|
|||
/// <summary>
|
|||
/// An interface that provides metadata for a specific image format frames.
|
|||
/// </summary>
|
|||
/// <typeparam name="TSelf">The metadata type implementing this interface.</typeparam>
|
|||
public interface IFormatFrameMetadata<TSelf> : IFormatMetadata, IDeepCloneable<TSelf> |
|||
where TSelf : class, IFormatFrameMetadata, new() |
|||
{ |
|||
/// <summary>
|
|||
/// Creates a new instance of the <typeparamref name="TSelf"/> class from the given <see cref="FormatConnectingFrameMetadata"/>.
|
|||
/// </summary>
|
|||
/// <param name="metadata">The <see cref="FormatConnectingFrameMetadata"/>.</param>
|
|||
/// <returns>The <typeparamref name="TSelf"/>.</returns>
|
|||
#pragma warning disable CA1000 // Do not declare static members on generic types
|
|||
static abstract TSelf FromFormatConnectingFrameMetadata(FormatConnectingFrameMetadata metadata); |
|||
#pragma warning restore CA1000 // Do not declare static members on generic types
|
|||
} |
|||
@ -0,0 +1,33 @@ |
|||
// Copyright (c) Six Labors.
|
|||
// Licensed under the Six Labors Split License.
|
|||
|
|||
namespace SixLabors.ImageSharp.Formats; |
|||
|
|||
/// <summary>
|
|||
/// An interface that provides metadata for a specific image format.
|
|||
/// </summary>
|
|||
public interface IFormatMetadata : IDeepCloneable |
|||
{ |
|||
/// <summary>
|
|||
/// Converts the metadata to a <see cref="FormatConnectingMetadata"/> instance.
|
|||
/// </summary>
|
|||
/// <returns>The <see cref="FormatConnectingMetadata"/>.</returns>
|
|||
FormatConnectingMetadata ToFormatConnectingMetadata(); |
|||
} |
|||
|
|||
/// <summary>
|
|||
/// An interface that provides metadata for a specific image format.
|
|||
/// </summary>
|
|||
/// <typeparam name="TSelf">The metadata type implementing this interface.</typeparam>
|
|||
public interface IFormatMetadata<TSelf> : IFormatMetadata, IDeepCloneable<TSelf> |
|||
where TSelf : class, IFormatMetadata, new() |
|||
{ |
|||
/// <summary>
|
|||
/// Creates a new instance of the <typeparamref name="TSelf"/> class from the given <see cref="FormatConnectingMetadata"/>.
|
|||
/// </summary>
|
|||
/// <param name="metadata">The <see cref="FormatConnectingMetadata"/>.</param>
|
|||
/// <returns>The <typeparamref name="TSelf"/>.</returns>
|
|||
#pragma warning disable CA1000 // Do not declare static members on generic types
|
|||
static abstract TSelf FromFormatConnectingMetadata(FormatConnectingMetadata metadata); |
|||
#pragma warning restore CA1000 // Do not declare static members on generic types
|
|||
} |
|||
@ -0,0 +1,255 @@ |
|||
// Copyright (c) Six Labors.
|
|||
// Licensed under the Six Labors Split License.
|
|||
|
|||
using SixLabors.ImageSharp.PixelFormats; |
|||
|
|||
namespace SixLabors.ImageSharp.Tests.PixelFormats; |
|||
|
|||
public class PixelColorTypeTests |
|||
{ |
|||
[Fact] |
|||
public void PixelColorType_RedFlag_ShouldBeSet() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.Red; |
|||
Assert.True(colorType.HasFlag(PixelColorType.Red)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_GreenFlag_ShouldBeSet() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.Green; |
|||
Assert.True(colorType.HasFlag(PixelColorType.Green)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_BlueFlag_ShouldBeSet() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.Blue; |
|||
Assert.True(colorType.HasFlag(PixelColorType.Blue)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_AlphaFlag_ShouldBeSet() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.Alpha; |
|||
Assert.True(colorType.HasFlag(PixelColorType.Alpha)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_GrayscaleFlag_ShouldBeSet() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.Grayscale; |
|||
Assert.True(colorType.HasFlag(PixelColorType.Grayscale)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_RGBFlags_ShouldBeSet() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.RGB; |
|||
Assert.True(colorType.HasFlag(PixelColorType.Red)); |
|||
Assert.True(colorType.HasFlag(PixelColorType.Green)); |
|||
Assert.True(colorType.HasFlag(PixelColorType.Blue)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.BGR)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_BGRFlags_ShouldBeSet() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.BGR; |
|||
Assert.True(colorType.HasFlag(PixelColorType.Blue)); |
|||
Assert.True(colorType.HasFlag(PixelColorType.Green)); |
|||
Assert.True(colorType.HasFlag(PixelColorType.Red)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.RGB)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_LuminanceFlag_ShouldBeSet() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.Luminance; |
|||
Assert.True(colorType.HasFlag(PixelColorType.Luminance)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_ChrominanceBlueFlag_ShouldBeSet() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.ChrominanceBlue; |
|||
Assert.True(colorType.HasFlag(PixelColorType.ChrominanceBlue)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_ChrominanceRedFlag_ShouldBeSet() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.ChrominanceRed; |
|||
Assert.True(colorType.HasFlag(PixelColorType.ChrominanceRed)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_YCbCrFlags_ShouldBeSet() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.YCbCr; |
|||
Assert.True(colorType.HasFlag(PixelColorType.Luminance)); |
|||
Assert.True(colorType.HasFlag(PixelColorType.ChrominanceBlue)); |
|||
Assert.True(colorType.HasFlag(PixelColorType.ChrominanceRed)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_CyanFlag_ShouldBeSet() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.Cyan; |
|||
Assert.True(colorType.HasFlag(PixelColorType.Cyan)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_MagentaFlag_ShouldBeSet() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.Magenta; |
|||
Assert.True(colorType.HasFlag(PixelColorType.Magenta)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_YellowFlag_ShouldBeSet() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.Yellow; |
|||
Assert.True(colorType.HasFlag(PixelColorType.Yellow)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_KeyFlag_ShouldBeSet() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.Key; |
|||
Assert.True(colorType.HasFlag(PixelColorType.Key)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_CMYKFlags_ShouldBeSet() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.CMYK; |
|||
Assert.True(colorType.HasFlag(PixelColorType.Cyan)); |
|||
Assert.True(colorType.HasFlag(PixelColorType.Magenta)); |
|||
Assert.True(colorType.HasFlag(PixelColorType.Yellow)); |
|||
Assert.True(colorType.HasFlag(PixelColorType.Key)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_YCCKFlags_ShouldBeSet() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.YCCK; |
|||
Assert.True(colorType.HasFlag(PixelColorType.Luminance)); |
|||
Assert.True(colorType.HasFlag(PixelColorType.ChrominanceBlue)); |
|||
Assert.True(colorType.HasFlag(PixelColorType.ChrominanceRed)); |
|||
Assert.True(colorType.HasFlag(PixelColorType.Key)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_Other_ShouldBeSet() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.Other; |
|||
Assert.True(colorType.HasFlag(PixelColorType.Other)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_None_ShouldBeZero() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.None; |
|||
Assert.Equal(0, (int)colorType); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_RGB_ShouldNotContainOtherFlags() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.RGB; |
|||
Assert.False(colorType.HasFlag(PixelColorType.Grayscale)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Luminance)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.ChrominanceBlue)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.ChrominanceRed)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Cyan)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Magenta)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Yellow)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Key)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Other)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_BGR_ShouldNotContainOtherFlags() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.BGR; |
|||
Assert.False(colorType.HasFlag(PixelColorType.Grayscale)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Luminance)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.ChrominanceBlue)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.ChrominanceRed)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Cyan)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Magenta)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Yellow)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Key)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Other)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_YCbCr_ShouldNotContainOtherFlags() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.YCbCr; |
|||
Assert.False(colorType.HasFlag(PixelColorType.Red)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Green)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Blue)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Alpha)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Grayscale)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Cyan)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Magenta)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Yellow)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Key)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Other)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_CMYK_ShouldNotContainOtherFlags() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.CMYK; |
|||
Assert.False(colorType.HasFlag(PixelColorType.Red)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Green)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Blue)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Alpha)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Grayscale)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Luminance)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.ChrominanceBlue)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.ChrominanceRed)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Other)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_YCCK_ShouldNotContainOtherFlags() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.YCCK; |
|||
Assert.False(colorType.HasFlag(PixelColorType.Red)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Green)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Blue)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Alpha)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Grayscale)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Cyan)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Magenta)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Yellow)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Other)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void PixelColorType_Other_ShouldNotContainPreviousFlags() |
|||
{ |
|||
const PixelColorType colorType = PixelColorType.Other; |
|||
Assert.False(colorType.HasFlag(PixelColorType.Red)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Green)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Blue)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Alpha)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Grayscale)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.RGB)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.BGR)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Luminance)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.ChrominanceBlue)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.ChrominanceRed)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.YCbCr)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Cyan)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Magenta)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Yellow)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.Key)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.CMYK)); |
|||
Assert.False(colorType.HasFlag(PixelColorType.YCCK)); |
|||
} |
|||
} |
|||
Loading…
Reference in new issue