Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/xcode/7.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 是否可以修改内存中的WPF位图源';不安全';从另一个线程下载_C#_Wpf_Bitmap_Imaging_Bitmapsource - Fatal编程技术网

C# 是否可以修改内存中的WPF位图源';不安全';从另一个线程下载

C# 是否可以修改内存中的WPF位图源';不安全';从另一个线程下载,c#,wpf,bitmap,imaging,bitmapsource,C#,Wpf,Bitmap,Imaging,Bitmapsource,我想在WPF应用程序中对图像进行一些处理。但是,我想在运行时修改内存中BitmapSource的像素 我目前正设法使用“不安全”代码对一个老式的System.Drawing.Bitmap执行此操作,它完成了一项处理(锁定工作区域,摆弄像素)工作。这篇文章描述了这种方法: 为了在WPF中实现这一点,我将使用以下方法创建一个WPF位图源: BitmapSource destination; IntPtr hBitmap = bitmap.GetHbitmap(); Bitma

我想在WPF应用程序中对图像进行一些处理。但是,我想在运行时修改内存中BitmapSource的像素

我目前正设法使用“不安全”代码对一个老式的System.Drawing.Bitmap执行此操作,它完成了一项处理(锁定工作区域,摆弄像素)工作。这篇文章描述了这种方法:

为了在WPF中实现这一点,我将使用以下方法创建一个WPF位图源:

    BitmapSource destination;
    IntPtr hBitmap = bitmap.GetHbitmap();
    BitmapSizeOptions sizeOptions = BitmapSizeOptions.FromEmptyOptions();
    destination = Imaging.CreateBitmapSourceFromHBitmap(hBitmap, IntPtr.Zero, Int32Rect.Empty, sizeOptions);
    destination.Freeze();
    return destination;
然而,这会在内存中创建大量副本,我真的很想进入其中,处理BitmapSource中的底层位,就像EricGu在位图示例中显示的那样。这可能吗

我意识到像素着色器可能可以做到这一点,但这是一个涉及多线程的学术练习(在不安全模式下编辑位图时支持)


提前谢谢

我会尽我所知告诉你

首先,在将位图返回主线程之前,您似乎已经知道如何冻结位图。这是一个好的开始

我曾经试图通过从BitmapSource派生一个新的实现来减少复制,并重写从位图中复制数据的虚拟函数。它工作正常,但产生了大量内存泄漏。我从来没想过

当然,您也可以直接从字节数组创建BitmapSource(这样会减少GDI位图的开销)

你考虑过一个新的计划吗?这是WPF团队对关于所有复制的常见投诉的回应

编辑:MSDN明确表示(在WritableBitmap.BackBuffer文档中)它可以从后台线程使用:

您可以将BackBuffer指针传递给 外部组件和其他线程 用于处理,但如果您这样做 必须提供自己的线程 协调。特别是,你必须 确保UI线程指定 通过调用 AddDirtyRect方法,并且该UI 线程通过调用 解锁方法


因此,如果让UI线程获得锁和指针,则可以让工作线程写入像素

我在另一台机器上有一些很好的代码。如果你在几个小时内没有得到答复,我就抓住它。不过我相信我用的是BitmaImage。它源于BitmapSource。我不记得很清楚,但我有一种感觉,你总是要把它转换成位图。不过,还有更优雅的转换方式。谢谢,我确实知道WriteableBitmap,但这只能通过单个线程IIRC更新。我真的很想在后台线程中播放图像,我认为这不可能用WritableBitmap实现,对吗?