DynamicImageHelpers.cs 4.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132
  1. using ImageMagickSharp;
  2. using MediaBrowser.Common.Configuration;
  3. using MediaBrowser.Common.IO;
  4. using System;
  5. using System.Collections.Generic;
  6. using System.IO;
  7. using System.Linq;
  8. using System.Threading.Tasks;
  9. namespace MediaBrowser.Server.Implementations.Photos
  10. {
  11. public static class DynamicImageHelpers
  12. {
  13. public static async Task<Stream> GetThumbCollage(List<string> files,
  14. IFileSystem fileSystem,
  15. int width,
  16. int height, IApplicationPaths appPaths)
  17. {
  18. if (files.Any(string.IsNullOrWhiteSpace))
  19. {
  20. throw new ArgumentException("Empty file found in files list");
  21. }
  22. if (files.Count == 0)
  23. {
  24. return null;
  25. }
  26. if (files.Count < 3)
  27. {
  28. return await GetSingleImage(files, fileSystem).ConfigureAwait(false);
  29. }
  30. const int rows = 1;
  31. const int cols = 3;
  32. int cellWidth = 2 * (width / 3);
  33. int cellHeight = height;
  34. var index = 0;
  35. using (var wand = new MagickWand(width, height, new PixelWand(ColorName.None, 1)))
  36. {
  37. for (var row = 0; row < rows; row++)
  38. {
  39. for (var col = 0; col < cols; col++)
  40. {
  41. var x = col * (cellWidth / 2);
  42. var y = row * cellHeight;
  43. if (files.Count > index)
  44. {
  45. using (var innerWand = new MagickWand(files[index]))
  46. {
  47. innerWand.CurrentImage.ResizeImage(cellWidth, cellHeight);
  48. wand.CurrentImage.CompositeImage(innerWand, CompositeOperator.OverCompositeOp, x, y);
  49. }
  50. }
  51. index++;
  52. }
  53. }
  54. return GetStream(wand, appPaths);
  55. }
  56. }
  57. public static async Task<Stream> GetSquareCollage(List<string> files,
  58. IFileSystem fileSystem,
  59. int size, IApplicationPaths appPaths)
  60. {
  61. if (files.Any(string.IsNullOrWhiteSpace))
  62. {
  63. throw new ArgumentException("Empty file found in files list");
  64. }
  65. if (files.Count == 0)
  66. {
  67. return null;
  68. }
  69. if (files.Count < 4)
  70. {
  71. return await GetSingleImage(files, fileSystem).ConfigureAwait(false);
  72. }
  73. const int rows = 2;
  74. const int cols = 2;
  75. int singleSize = size / 2;
  76. var index = 0;
  77. using (var wand = new MagickWand(size, size, new PixelWand(ColorName.None, 1)))
  78. {
  79. for (var row = 0; row < rows; row++)
  80. {
  81. for (var col = 0; col < cols; col++)
  82. {
  83. var x = col * singleSize;
  84. var y = row * singleSize;
  85. using (var innerWand = new MagickWand(files[index]))
  86. {
  87. innerWand.CurrentImage.ResizeImage(singleSize, singleSize);
  88. wand.CurrentImage.CompositeImage(innerWand, CompositeOperator.OverCompositeOp, x, y);
  89. }
  90. index++;
  91. }
  92. }
  93. return GetStream(wand, appPaths);
  94. }
  95. }
  96. private static Task<Stream> GetSingleImage(List<string> files, IFileSystem fileSystem)
  97. {
  98. return Task.FromResult<Stream>(fileSystem.GetFileStream(files[0], FileMode.Open, FileAccess.Read, FileShare.Read));
  99. }
  100. internal static Stream GetStream(MagickWand image, IApplicationPaths appPaths)
  101. {
  102. var tempFile = Path.Combine(appPaths.TempDirectory, Guid.NewGuid().ToString("N") + ".png");
  103. Directory.CreateDirectory(Path.GetDirectoryName(tempFile));
  104. image.CurrentImage.CompressionQuality = 100;
  105. image.SaveImage(tempFile);
  106. return File.OpenRead(tempFile);
  107. }
  108. }
  109. }