Browse Source

Improved SharedImage API

MarcinZiabek 2 years ago
parent
commit
b74e0327fa

+ 34 - 5
Source/QuestPDF.Examples/ImageExamples.cs

@@ -1,5 +1,6 @@
 using System;
 using System.IO;
+using System.Linq;
 using NUnit.Framework;
 using QuestPDF.Drawing.Exceptions;
 using QuestPDF.Examples.Engine;
@@ -79,11 +80,11 @@ namespace QuestPDF.Examples
                 .ShowResults()
                 .Render(page =>
                 {
-                    page.Padding(10).Column(column =>
+                    page.Padding(15).Column(column =>
                     {
-                        column.Spacing(10);
+                        column.Spacing(15);
                         
-                        column.Item().Image("photo.jpg").WithRasterDpi(16);
+                        column.Item().Image("photo.jpg").WithRasterDpi(16).FitUnproportionally();
                         column.Item().Image("photo.jpg").WithRasterDpi(72);
                     });
                 });
@@ -99,9 +100,9 @@ namespace QuestPDF.Examples
                 .ShowResults()
                 .Render(page =>
                 {
-                    page.Padding(10).Column(column =>
+                    page.Padding(15).Column(column =>
                     {
-                        column.Spacing(10);
+                        column.Spacing(15);
                         
                         column.Item().Image("photo.jpg").WithCompressionQuality(ImageCompressionQuality.VeryLow).WithRasterDpi(72);
                         column.Item().Image("photo.jpg").WithCompressionQuality(ImageCompressionQuality.High).WithRasterDpi(72);
@@ -109,6 +110,34 @@ namespace QuestPDF.Examples
                 });
         }
         
+        [Test]
+        public void ReusingImage_With()
+        {
+            RenderingTest
+                .Create()
+                .PageSize(400, 600)
+                .ProduceImages()
+                .ShowResults()
+                .Render(page =>
+                {
+                    page.Padding(15).Column(column =>
+                    {
+                        column.Spacing(15);
+
+                        var image = Image.FromFile("checkbox.png");
+                        
+                        foreach (var i in Enumerable.Range(0, 5))
+                        {
+                            column.Item().Row(row =>
+                            {
+                                row.AutoItem().Width(24).Image(image);
+                                row.RelativeItem().PaddingLeft(8).AlignMiddle().Text(Placeholders.Label()).FontSize(16);
+                            });
+                        }
+                    });
+                });
+        }
+        
         [Test]
         public void Exception()
         {

+ 3 - 0
Source/QuestPDF.Examples/QuestPDF.Examples.csproj

@@ -38,6 +38,9 @@
       <None Update="photo.jpg">
         <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
       </None>
+      <None Update="checkbox.png">
+        <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
+      </None>
     </ItemGroup>
 
 </Project>

BIN
Source/QuestPDF.Examples/checkbox.png


+ 1 - 1
Source/QuestPDF.UnitTests/ImageTests.cs

@@ -85,7 +85,7 @@ namespace QuestPDF.UnitTests
             {
                 container.Column(column =>
                 {
-                    var sharedImage = DocumentImage.FromBinaryData(photo).DisposeAfterDocumentGeneration();
+                    var sharedImage = DocumentImage.FromBinaryData(photo);
                     
                     foreach (var i in Enumerable.Range(0, 10))
                         column.Item().Image(sharedImage);

+ 3 - 3
Source/QuestPDF/Fluent/ImageExtensions.cs

@@ -109,19 +109,19 @@ namespace QuestPDF.Fluent
     {
         public static ImageDescriptor Image(this IContainer parent, byte[] imageData)
         {
-            var image = Infrastructure.Image.FromBinaryData(imageData).DisposeAfterDocumentGeneration();
+            var image = Infrastructure.Image.FromBinaryData(imageData);
             return parent.Image(image);
         }
         
         public static ImageDescriptor Image(this IContainer parent, string filePath)
         {
-            var image = Infrastructure.Image.FromFile(filePath).DisposeAfterDocumentGeneration();
+            var image = Infrastructure.Image.FromFile(filePath);
             return parent.Image(image);
         }
         
         public static ImageDescriptor Image(this IContainer parent, Stream fileStream)
         {
-            var image = Infrastructure.Image.FromStream(fileStream).DisposeAfterDocumentGeneration();
+            var image = Infrastructure.Image.FromStream(fileStream);
             return parent.Image(image);
         }
         

+ 47 - 10
Source/QuestPDF/Infrastructure/Image.cs

@@ -13,28 +13,29 @@ namespace QuestPDF.Infrastructure
         internal ImageCompressionQuality CompressionQuality { get; set; }
     }
     
-    public class Image : IDisposable
+    public class Image
     {
         internal SKImage SkImage { get; }
         internal ImageSize Size { get; }
-        internal bool IsDocumentScoped { get; set; }
+        internal bool IsDocumentScoped { get; }
         
         internal LinkedList<(GetImageVersionRequest request, SKImage image)> ScaledImageCache { get; } = new();
 
-        private Image(SKImage image)
+        internal Image(SKImage image, bool isDocumentScoped)
         {
             SkImage = image;
+            IsDocumentScoped = isDocumentScoped;
             Size = new ImageSize(image.Width, image.Height);
         }
-
-        public void Dispose()
+        
+        internal void Dispose()
         {
             SkImage.Dispose();
 
             foreach (var cacheKey in ScaledImageCache)
                 cacheKey.image.Dispose();
         } 
-        
+
         #region Scaling Image
 
         internal SKImage GetVersionOfSize(GetImageVersionRequest request)
@@ -79,15 +80,51 @@ namespace QuestPDF.Infrastructure
             if (image == null)
                 throw new DocumentComposeException("Cannot load or decode provided image.");
 
-            return new Image(image);
+            return new Image(image, true);
         }
 
         #endregion
+    }
+
+    public class SharedImage : Image, IDisposable
+    {
+        internal SharedImage(SKImage image) : base(image, false)
+        {
+            
+        }
+        
+        public void Dispose()
+        {
+            base.Dispose();
+        } 
+        
+        #region public constructors
+        
+        public static new SharedImage FromBinaryData(byte[] imageData)
+        {
+            return CreateImage(SKImage.FromEncodedData(imageData));
+        }
 
-        internal Image DisposeAfterDocumentGeneration()
+        public static new SharedImage FromFile(string filePath)
         {
-            IsDocumentScoped = true;
-            return this;
+            return CreateImage(SKImage.FromEncodedData(filePath));
         }
+
+        public static new SharedImage FromStream(Stream fileStream)
+        {
+            return CreateImage(SKImage.FromEncodedData(fileStream));
+        }
+
+        private static SharedImage CreateImage(SKImage? image)
+        {
+            if (image == null)
+                throw new DocumentComposeException("Cannot load or decode provided image.");
+
+            var result = new SharedImage(image);
+            
+            return result;
+        }
+
+        #endregion
     }
 }