IDS peak ICV v1.3.0
Loading...
Searching...
No Matches
Image.cs
Go to the documentation of this file.
1using System.Runtime.InteropServices;
5using Microsoft.Win32.SafeHandles;
6
8
17public class Image : IDisposable, IHasSafeHandle
18{
19 private readonly uint _bufferSize;
20 internal readonly Handle _handle;
21 SafeHandle IHasSafeHandle.Handle => _handle;
22 private Metadata? _metadata;
23
24 internal Image(Handle handle)
25 {
26 _handle = handle;
27
28 var cImageInfo = new Backend.Types.peak_icv_image_info();
29 DllHelper.ExecuteAndMapReturnCodes(() =>
30 CInterface.peak_icv_Image_GetInfo(_handle, out cImageInfo,
31 (nuint) Marshal.SizeOf(cImageInfo)));
32
33 Size = new Size(cImageInfo.size.width, cImageInfo.size.height);
34 PixelFormat = cImageInfo.pixelFormat;
35
36 _bufferSize = (uint) cImageInfo.bufferSize;
37 Data = cImageInfo.buffer;
38 }
39
51 public Image(IImageView imageView) : this(CreateFromImageView(imageView))
52 {
53 Metadata = imageView.Metadata.Clone();
54 }
55
66 public Image(PixelFormat pixelFormat, Size imageSize) : this(CreateFromSize(pixelFormat, imageSize))
67 {
68 }
69
89 public Image(PixelFormat pixelFormat, Size imageSize, IntPtr buffer, uint bufferSize) : this(
90 CreateFromBuffer(pixelFormat, imageSize, buffer, bufferSize))
91 {
92 }
93
142 public Image(string filePath) : this(CreateFromFile(filePath))
143 {
144 }
145
200 public Image(string filePath, PixelFormat pixelFormat) : this(CreateFromFile(filePath, pixelFormat))
201 {
202 }
203
204 internal Image(Image other)
205 : this(new Handle(other._handle.DangerousGetHandle()))
206 {
207 DllHelper.ExecuteAndMapReturnCodes(() =>
208 CInterface.peak_icv_Image_IncreaseUseCount(_handle));
209
210 _metadata = other._metadata;
211 }
212
217 public PixelFormat PixelFormat { get; }
218
223 public Size Size { get; }
224
229 public uint Width => Size.Width;
230
235 public uint Height => Size.Height;
236
241 public IntPtr Data { get; }
242
247 public long SizeInBytes => _bufferSize;
248
254 {
255 get
256 {
257 if (_metadata != null)
258 {
259 return _metadata;
260 }
261
262 var cCaptureInformation = new Backend.Types.peak_icv_capture_information();
263 DllHelper.ExecuteAndMapReturnCodes(() =>
264 CInterface.peak_icv_Image_GetCaptureInformation(_handle, out cCaptureInformation,
265 (nuint) Marshal.SizeOf(cCaptureInformation)));
266
267 _metadata = CaptureInformation.ToMetadata(cCaptureInformation);
268
269 _metadata.Changed += (_, _) =>
270 {
271 Backend.Types.peak_icv_capture_information cCaptureInformation =
272 CaptureInformation.FromMetadata(_metadata, Size);
273 CInterface.peak_icv_Image_SetCaptureInformation(_handle, cCaptureInformation,
274 (nuint) Marshal.SizeOf(cCaptureInformation));
275 };
276
277 return _metadata;
278 }
279
280 set
281 {
282 Backend.Types.peak_icv_capture_information cCaptureInformation =
283 CaptureInformation.FromMetadata(value, Size);
284
285 DllHelper.ExecuteAndMapReturnCodes(() =>
286 CInterface.peak_icv_Image_SetCaptureInformation(_handle, cCaptureInformation,
287 (nuint) Marshal.SizeOf(cCaptureInformation)));
288
289 _metadata = value.Clone();
290 CaptureInformation.MergeWithMetadata(cCaptureInformation, _metadata);
291 }
292 }
293
301 {
302 get
303 {
304 var region = new Region();
305 DllHelper.ExecuteAndMapReturnCodes(() =>
306 CInterface.peak_icv_Image_GetRegion(_handle, ref region._handle));
307
308 return region;
309 }
310 set { DllHelper.ExecuteAndMapReturnCodes(() => CInterface.peak_icv_Image_SetRegion(_handle, value._handle)); }
311 }
312
317 public void Dispose()
318 {
319 _handle.Dispose();
320 GC.SuppressFinalize(this);
321 }
322
327 public void ResetRegion()
328 {
329 DllHelper.ExecuteAndMapReturnCodes(() => CInterface.peak_icv_Image_ResetRegion(_handle));
330 }
331
336 public Image Copy()
337 {
338 var image = new Image(PixelFormat, Size);
339 unsafe
340 {
341 Buffer.MemoryCopy((void*) Data, (void*) image.Data, (int) _bufferSize, (int) _bufferSize);
342 }
343
344
345 image.Metadata = Metadata.Clone();
346 return image;
347 }
348
389 {
390 var outputImage = new Image(pixelFormat, Size);
391 DllHelper.ExecuteAndMapReturnCodes(() =>
392 CInterface.peak_icv_Image_ConvertPixelFormat(_handle, pixelFormat,
393 outputImage._handle));
394 return outputImage;
395 }
396
420 public Image ConvertPixelFormatWithFactor(PixelFormat pixelFormat, double factor)
421 {
422 var outputImage = new Image(pixelFormat, Size);
423 DllHelper.ExecuteAndMapReturnCodes(() =>
424 CInterface.peak_icv_Image_ConvertPixelFormatWithFactor(_handle, pixelFormat, factor,
425 outputImage._handle));
426 return outputImage;
427 }
428
448 public Image Subtract(Image subtrahend)
449 {
450 var outputImage = new Image(PixelFormat, Size);
451
452 DllHelper.ExecuteAndMapReturnCodes(() =>
453 CInterface.peak_icv_Image_Subtract(_handle, subtrahend._handle,
454 outputImage._handle));
455 return outputImage;
456 }
457
476 public static Image operator -(Image minuend, Image subtrahend)
477 {
478 return minuend.Subtract(subtrahend);
479 }
480
481 private static Handle CreateFromSize(PixelFormat pixelFormat, Size imageSize)
482 {
483 var imageHandle = new Handle();
484 DllHelper.ExecuteAndMapReturnCodes(() => CInterface.peak_icv_Image_Create(out imageHandle,
485 pixelFormat, new Backend.Types.peak_common_size
486 { width = imageSize.Width, height = imageSize.Height }));
487
488 return imageHandle;
489 }
490
491 private static Handle CreateFromBuffer(PixelFormat pixelFormat, Size imageSize, IntPtr buffer, nuint bufferSize)
492 {
493 var imageHandle = new Handle();
494
495 var imageInfo = new Backend.Types.peak_icv_image_info
496 {
497 pixelFormat = pixelFormat,
498 size = new Backend.Types.peak_common_size { width = imageSize.Width, height = imageSize.Height },
499 bufferSize = bufferSize,
500 buffer = buffer
501 };
502 DllHelper.ExecuteAndMapReturnCodes(() =>
503 CInterface.peak_icv_Image_CreateFromImageInfo(out imageHandle, imageInfo,
504 (nuint) Marshal.SizeOf(imageInfo)));
505
506 return imageHandle;
507 }
508
509 private static Handle CreateFromFile(string filePath)
510 {
511 var imageHandle = new Handle();
512 DllHelper.ExecuteAndMapReturnCodes(() =>
513 CInterface.peak_icv_Image_CreateFromFile(out imageHandle, Utils.ToUtf8(filePath)));
514
515 return imageHandle;
516 }
517
518 private static Handle CreateFromFile(string filePath, PixelFormat forcePixelFormat)
519 {
520 var imageHandle = new Handle();
521 DllHelper.ExecuteAndMapReturnCodes(() =>
522 CInterface.peak_icv_Image_CreateFromFileWithPixelFormat(out imageHandle, Utils.ToUtf8(filePath),
523 forcePixelFormat));
524
525 return imageHandle;
526 }
527
528 private static Handle CreateFromImageView(IImageView imageView)
529 {
530 Size imageViewSize = imageView.Size;
531 nuint lineStartOffset = imageView.LineStartOffset;
532 var validBytesPerLine = (nuint)new PixelFormatInfo(imageView.PixelFormat)
533 .GetSizeInBytes(new Size(imageViewSize.Width, 1 ));
534
535 if (lineStartOffset == 0 && validBytesPerLine == imageView.BytesPerLine)
536 {
537 return CreateFromBuffer(imageView.PixelFormat, imageViewSize, imageView.Data, imageView.SizeInBytes);
538 }
539
540 Handle handle = CreateFromSize(imageView.PixelFormat, imageViewSize);
541
542 try
543 {
544 DllHelper.ExecuteAndMapReturnCodes(() =>
545 CInterface.peak_icv_Buffer_CutBytes(imageView.Data, lineStartOffset, imageView.BytesPerLine,
546 validBytesPerLine, imageViewSize.Height, handle));
547 }
548 catch (Exception)
549 {
550 handle.Dispose();
551 throw;
552 }
553
554 return handle;
555 }
556
557 private sealed class ImageEqualityComparer : IEqualityComparer<Image>
558 {
559 public bool Equals(Image x, Image y)
560 {
561 if (ReferenceEquals(x, y))
562 {
563 return true;
564 }
565
566 if (ReferenceEquals(x, null))
567 {
568 return false;
569 }
570
571 if (ReferenceEquals(y, null))
572 {
573 return false;
574 }
575
576 var isEqual = false;
577 DllHelper.ExecuteAndMapReturnCodes(() =>
578 CInterface.peak_icv_Image_Compare(x._handle, y._handle, out isEqual));
579
580 return isEqual;
581 }
582
583 public int GetHashCode(Image obj)
584 {
585 var width = obj.Size.Width;
586 var height = obj.Size.Height;
587
588 unsafe
589 {
590 var ptr = (byte*) obj.Data;
591
592 var p1 = ptr[0];
593 var p2 = ptr[width - 1];
594 var p3 = ptr[height / 2 + width / 2];
595 var p4 = ptr[height - 1];
596 var p5 = ptr[height - 1 + (width - 1)];
597
598 return (obj.Size, obj.PixelFormat, p1, p2, p3, p4, p5).GetHashCode();
599 }
600 }
601 }
602
607 public static IEqualityComparer<Image> Comparer { get; } = new ImageEqualityComparer();
608
620 public List<Image> Deinterleave()
621 {
622 nuint numOutputImages = 0;
623
624 DllHelper.ExecuteAndMapReturnCodes(() =>
625 CInterface.peak_icv_Image_Deinterleave_GetOutputImageCount(PixelFormat, ref numOutputImages));
626
627 PixelFormat pixelFormat = PixelFormat.Mono8;
628
629 DllHelper.ExecuteAndMapReturnCodes(() =>
630 CInterface.peak_icv_Image_Deinterleave_GetOutputPixelFormat(PixelFormat, ref pixelFormat));
631
632 var cInputImageSize = new Backend.Types.peak_common_size { width = Size.Width, height = Size.Height };
633 var cOutputImageSize = new Backend.Types.peak_common_size();
634
635 DllHelper.ExecuteAndMapReturnCodes(() =>
636 CInterface.peak_icv_Image_Deinterleave_GetOutputImageSize(PixelFormat, cInputImageSize,
637 out cOutputImageSize));
638
639 var outputImages = new List<Image>();
640 for (var i = 0; i < (int) numOutputImages; i++)
641 {
642 outputImages.Add(new Image(pixelFormat, new Size(cOutputImageSize.width, cOutputImageSize.height)));
643 }
644
645 IntPtr[] outputHandles = SafeHandles.ExtractHandles(
646 outputImages,
647 out Action release);
648
649 try
650 {
651 DllHelper.ExecuteAndMapReturnCodes(() =>
652 CInterface.peak_icv_Image_Deinterleave(_handle, outputHandles, (nuint) outputHandles.Length));
653 }
654 finally
655 {
656 release();
657 }
658
659 return outputImages;
660 }
661
662 internal sealed class Handle : SafeHandleZeroOrMinusOneIsInvalid
663 {
664 public Handle() : base(true)
665 {
666 }
667
668 public Handle(IntPtr handle) : base(true)
669 {
670 SetHandle(handle);
671 }
672
673 protected override bool ReleaseHandle()
674 {
675 return CInterface.peak_icv_Image_Destroy(handle) ==
676 Backend.Types.peak_icv_status.PEAK_ICV_STATUS_SUCCESS;
677 }
678 }
679
680 private static class CInterface
681 {
682 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
683 public static extern Backend.Types.peak_icv_status peak_icv_Image_SetRegion(Handle image_handle,
684 Region.Handle region_handle);
685
686 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
687 public static extern Backend.Types.peak_icv_status peak_icv_Image_ResetRegion(Handle image_handle);
688
689 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
690 public static extern Backend.Types.peak_icv_status peak_icv_Image_Create(out Handle image_handle,
691 PixelFormat pixel_format, Backend.Types.peak_common_size image_size);
692
693 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
694 public static extern Backend.Types.peak_icv_status peak_icv_Image_CreateFromImageInfo(
695 out Handle image_handle,
696 Backend.Types.peak_icv_image_info image_info, nuint image_info_size);
697
698 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
699 public static extern Backend.Types.peak_icv_status peak_icv_Image_GetInfo(Handle image_handle,
700 out Backend.Types.peak_icv_image_info image_info, nuint image_info_size);
701
702 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
703 public static extern Backend.Types.peak_icv_status peak_icv_Image_GetRegion(
704 Handle image_handle, ref Region.Handle region_handle);
705
706 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
707 public static extern Backend.Types.peak_icv_status peak_icv_Image_Destroy(IntPtr image_handle);
708
709 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
710 public static extern Backend.Types.peak_icv_status peak_icv_Image_SetCaptureInformation(Handle image_handle,
711 Backend.Types.peak_icv_capture_information capture_information, nuint capture_information_size);
712
713 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
714 public static extern Backend.Types.peak_icv_status peak_icv_Image_GetCaptureInformation(Handle image_handle,
715 out Backend.Types.peak_icv_capture_information capture_information, nuint capture_information_size);
716
717 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
718 public static extern Backend.Types.peak_icv_status peak_icv_Image_Compare(Handle image_handle_lhs,
719 Handle image_handle_rhs, [MarshalAs(UnmanagedType.I1)] out bool is_equal);
720
721 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
722 public static extern Backend.Types.peak_icv_status peak_icv_Image_IncreaseUseCount(Handle image_handle);
723
724 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
725 public static extern Backend.Types.peak_icv_status peak_icv_Image_CreateFromFile(out Handle image_handle,
726 byte[] file_path);
727
728 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
729 public static extern Backend.Types.peak_icv_status peak_icv_Image_ConvertPixelFormat(Handle input_handle,
730 PixelFormat pixel_format, Handle output_handle);
731
732 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
733 public static extern Backend.Types.peak_icv_status peak_icv_Image_ConvertPixelFormatWithFactor(
734 Handle input_handle,
735 PixelFormat pixel_format, double factor, Handle output_handle);
736
737 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
738 public static extern Backend.Types.peak_icv_status peak_icv_Image_Subtract(Handle input_handle,
739 Handle subtrahend_handle, Handle output_handle);
740
741 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
742 public static extern Backend.Types.peak_icv_status peak_icv_Image_CreateFromFileWithPixelFormat(
743 out Handle image_handle,
744 byte[] file_path, PixelFormat forced_pixelformat);
745
746 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
747 public static extern Backend.Types.peak_icv_status peak_icv_Image_Deinterleave_GetOutputImageCount(
748 PixelFormat input_pixel_format, ref nuint output_image_count);
749
750 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
751 public static extern Backend.Types.peak_icv_status peak_icv_Image_Deinterleave_GetOutputPixelFormat(
752 PixelFormat input_pixel_format, ref PixelFormat output_pixel_format);
753
754 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
755 public static extern Backend.Types.peak_icv_status peak_icv_Image_Deinterleave_GetOutputImageSize(
756 PixelFormat input_pixel_format, Backend.Types.peak_common_size input_image_size,
757 out Backend.Types.peak_common_size output_image_size);
758
759 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
760 public static extern Backend.Types.peak_icv_status peak_icv_Image_Deinterleave(
761 Handle input_image_handle, IntPtr[] output_image_handles, nuint output_image_count);
762
763 [DllImport(Global.LibraryName, CallingConvention = Global.CallingConvention)]
764 public static extern Backend.Types.peak_icv_status peak_icv_Buffer_CutBytes(IntPtr data,
765 nuint line_start_offset, nuint bytes_per_line, nuint valid_bytes_per_line, nuint number_of_lines,
766 Handle output_image_handle);
767 }
768}
T Width
Gets the width of the size.
Definition Size.cs:37
T Height
Gets the height of the size.
Definition Size.cs:42
Represents a size with integer width and height values.
Definition Size.cs:107
Strongly typed container for image acquisition metadata.
Definition Metadata.cs:233
Metadata Clone()
Creates a copy of this Metadata instance.
Definition Metadata.cs:442
Provides information and utility functions for pixel formats. The PixelFormatInfo class offers method...
ulong GetSizeInBytes(Size size)
Calculates the memory size in bytes for a given image size.
Constructs an Image from an IImageView Instance.
Definition Image.cs:18
Size Size
Gets the image size in pixels from the image.
Definition Image.cs:223
Image(PixelFormat pixelFormat, Size imageSize, IntPtr buffer, uint bufferSize)
Constructs an Image from a pointer to a buffer.
Definition Image.cs:89
List< Image > Deinterleave()
Splits an image with an interleaved pixel format into individual images. The function separates e....
Definition Image.cs:620
Region Region
Gets or sets a region of interest (ROI) for the specified image handle, which defines a sub-area of t...
Definition Image.cs:301
void ResetRegion()
Resets the region on the image to the complete image.
Definition Image.cs:327
uint Height
Gets the image height in pixels from the image.
Definition Image.cs:235
void Dispose()
Releases the resources used by the Image class.
Definition Image.cs:317
uint Width
Gets the image width in pixels from the image.
Definition Image.cs:229
Image Subtract(Image subtrahend)
Subtracts the specified subtrahend image pixel-wise from the current image and returns the resulting...
Definition Image.cs:448
static IEqualityComparer< Image > Comparer
Gets a default equality comparer for comparing Image data values.
Definition Image.cs:607
Image(string filePath, PixelFormat pixelFormat)
Constructs an Image from a file path with a specified pixel format.
Definition Image.cs:200
Image(string filePath)
Constructs an Image from a file path.
Definition Image.cs:142
Image(IImageView imageView)
Constructs an Image from an IImageView instance.
Definition Image.cs:51
Image Copy()
Creates a deep copy of the current Image.
Definition Image.cs:336
Image(PixelFormat pixelFormat, Size imageSize)
Constructs an Image with a given size in pixels and pixel format.
Definition Image.cs:66
Image ConvertPixelFormatWithFactor(PixelFormat pixelFormat, double factor)
Converts an image into another pixel format with a factor multiplied to every pixel.
Definition Image.cs:420
long SizeInBytes
Gets the size of the image data in bytes.
Definition Image.cs:247
Image ConvertPixelFormat(PixelFormat pixelFormat)
Converts the image to a different pixel format.
Definition Image.cs:388
IntPtr Data
Gets the image buffer from the image.
Definition Image.cs:241
static Image operator-(Image minuend, Image subtrahend)
Performs pixel-wise subtraction of two images.
Definition Image.cs:476
Represents a region defined by a set of points in the image plane.
Definition Region.cs:43
PixelFormat
Each enumerator represents a specific pixel layout and bit-depth, used for interpreting raw image dat...
Interface for viewing image pixel data from arbitrary sources.
Definition IImageView.cs:21
PixelFormat PixelFormat
Returns the pixel format used by the image.
Definition IImageView.cs:40
nuint SizeInBytes
Returns the total size number of bytes occupied by the image in the buffer.
Definition IImageView.cs:30
nuint LineStartOffset
The byte offset to the first pixel of a line.
Definition IImageView.cs:35
Size Size
Returns the overall size of the image (width × height).
Definition IImageView.cs:53
Metadata Metadata
Metadata associated with the image.
Definition IImageView.cs:84
nuint BytesPerLine
Returns the number of bytes in a single image row.
Definition IImageView.cs:79
IntPtr Data
Returns the pointer to the beginning of the image buffer.
Definition IImageView.cs:25