ExtractLayerTask.cs 4.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103
  1. using System;
  2. using System.Collections.Generic;
  3. using PDNWrapper;
  4. using UnityEngine;
  5. using Unity.Collections;
  6. using Unity.Collections.LowLevel.Unsafe;
  7. using Unity.Jobs;
  8. namespace UnityEditor.U2D.PSD
  9. {
  10. class ExtractLayerTask
  11. {
  12. struct ConvertBufferJob : IJobParallelFor
  13. {
  14. [ReadOnly]
  15. [DeallocateOnJobCompletion]
  16. public NativeArray<IntPtr> original;
  17. [ReadOnly]
  18. [DeallocateOnJobCompletion]
  19. public NativeArray<int> width;
  20. [ReadOnly]
  21. [DeallocateOnJobCompletion]
  22. public NativeArray<int> height;
  23. [DeallocateOnJobCompletion]
  24. public NativeArray<IntPtr> output;
  25. public unsafe void Execute(int index)
  26. {
  27. Color32* originalColor = (Color32*)original[index];
  28. Color32* otuputColor = (Color32*)output[index];
  29. for (int i = 0; i < height[index]; ++i)
  30. {
  31. int originalYOffset = i * width[index];
  32. int outputYOffset = (height[index] - i - 1) * width[index];
  33. for (int j = 0; j < width[index]; ++j)
  34. {
  35. otuputColor[j + outputYOffset] = originalColor[j + originalYOffset];
  36. }
  37. }
  38. }
  39. }
  40. public static unsafe void Execute(List<PSDLayer> extractedLayer, List<BitmapLayer> layers, bool importHiddenLayer)
  41. {
  42. UnityEngine.Profiling.Profiler.BeginSample("ExtractLayer_PrepareJob");
  43. var tempExtractLayer = new List<PSDLayer>();
  44. int layerWithBuffer = ExtractLayer(tempExtractLayer, layers, importHiddenLayer);
  45. if (layerWithBuffer == 0)
  46. return;
  47. var job = new ConvertBufferJob();
  48. job.original = new NativeArray<IntPtr>(layerWithBuffer, Allocator.TempJob);
  49. job.output = new NativeArray<IntPtr>(layerWithBuffer, Allocator.TempJob);
  50. job.width = new NativeArray<int>(layerWithBuffer, Allocator.TempJob);
  51. job.height = new NativeArray<int>(layerWithBuffer, Allocator.TempJob);
  52. for (int i = 0, jobIndex = 0; i < tempExtractLayer.Count; ++i)
  53. {
  54. var el = tempExtractLayer[i];
  55. if (el.texture.Length == 0 || el.width == 0 || el.height == 0)
  56. {
  57. extractedLayer.Add(el);
  58. continue;
  59. }
  60. job.original[jobIndex] = new IntPtr(el.texture.GetUnsafeReadOnlyPtr());
  61. el.texture = new NativeArray<Color32>(el.texture.Length, Allocator.Persistent);
  62. extractedLayer.Add(el);
  63. job.output[jobIndex] = new IntPtr(el.texture.GetUnsafePtr());
  64. job.width[jobIndex] = el.width;
  65. job.height[jobIndex] = el.height;
  66. ++jobIndex;
  67. }
  68. var jobsPerThread = layerWithBuffer / (SystemInfo.processorCount == 0 ? 8 : SystemInfo.processorCount);
  69. jobsPerThread = Mathf.Max(jobsPerThread, 1);
  70. var handle = job.Schedule(layerWithBuffer, jobsPerThread);
  71. UnityEngine.Profiling.Profiler.EndSample();
  72. handle.Complete();
  73. }
  74. static int ExtractLayer(List<PSDLayer> extractedLayer, List<BitmapLayer> layers, bool importHiddenLayer)
  75. {
  76. // parent is the previous element in extracedLayer
  77. int parentGroupIndex = extractedLayer.Count - 1;
  78. int actualLayerWithBuffer = 0;
  79. foreach (var l in layers)
  80. {
  81. if (!importHiddenLayer && !l.Visible)
  82. continue;
  83. if (l.IsGroup)
  84. {
  85. extractedLayer.Add(new PSDLayer(new NativeArray<Color32>(0, Allocator.Persistent), parentGroupIndex, l.IsGroup, l.Name, 0, 0, l.LayerID));
  86. actualLayerWithBuffer += ExtractLayer(extractedLayer, l.ChildLayer, importHiddenLayer);
  87. }
  88. else
  89. {
  90. extractedLayer.Add(new PSDLayer(l.Surface.color, parentGroupIndex, l.IsGroup, l.Name, l.Surface.width, l.Surface.height, l.LayerID));
  91. ++actualLayerWithBuffer;
  92. }
  93. }
  94. return actualLayerWithBuffer;
  95. }
  96. }
  97. }