wpf 如何将图像文件绘制/覆盖到位图图像?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/21915705/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-13 10:57:05  来源:igfitidea点击:

How to draw/overlay an image file to a bitmap image?

c#wpfimagebitmapoverlay

提问by Brian J

I have a video feed from a Kinect sensor hosted by an image stored as a bitmap. My question is how do I overlay an image, for example a .pngon to the video feed.

我有一个来自 Kinect 传感器的视频源,由存储​​为位图的图像托管。我的问题是如何叠加图像,例如.png在视频源上叠加。

The video feed is shown like show below as bitmap source, I know how to draw a line to the bitmap but how do I draw an image from resources to the it?

视频源显示如下所示作为位图源,我知道如何在位图上画一条线,但如何从资源中绘制图像到它?

KinectVideo.Source = BitmapSource.Create(colorFrame.Width, colorFrame.Height, 96, 96,
                    PixelFormats.Bgr32, null, colorData, colorFrame.Width * colorFrame.BytesPerPixel); 

Below is a mock up of what I'm trying to achieve by placing the image over the video feed:

下面是我试图通过将图像放在视频源上来实现的模拟:

The boxing bag is the image I want to overlay to the video feed.

拳击袋是我想叠加到视频源的图像。

Updated implementation of drawing method,I don't think this is the correct implementation also I'm getting invalid argument error when adding image path to .DrawImage:

更新了绘图方法的实现,我认为这不是正确的实现,而且我在将图像路径添加到.DrawImage以下内容时遇到无效参数错误:

void myKinect_ColorFrameReady(object sender, ColorImageFrameReadyEventArgs e)
        {
            using (ColorImageFrame colorFrame = e.OpenColorImageFrame())
            {

                if (colorFrame == null) return;
                byte[] colorData = new byte[colorFrame.PixelDataLength];
                colorFrame.CopyPixelDataTo(colorData);

                 KinectVideo.Source = BitmapSource.Create(colorFrame.Width, colorFrame.Height, 96, 96,
                    PixelFormats.Bgr32, null, colorData, colorFrame.Width * colorFrame.BytesPerPixel);

                Rect destRect2;

               //drawing image overlay to video feed
                 var drawingVisual = new DrawingVisual();
                 var drawingContext = drawingVisual.RenderOpen();
                 drawingContext.DrawImage(BitmapSource.Create(colorFrame.Width, colorFrame.Height, 96, 96, PixelFormats.Bgr32, null, colorData, colorFrame.Width * colorFrame.BytesPerPixel),
                                           new Rect(new Size(colorFrame.Width, colorFrame.Height)));
                 drawingContext.DrawImage("Images/boxbag.jpg", destRect2);
                 drawingContext.Close();
                 var mergedImage = new RenderTargetBitmap(colorFrame.Width, colorFrame.Height, 96, 96, PixelFormats.Pbgra32);
                 mergedImage.Render(drawingVisual);

                 KinectVideo.Source = mergedImage; 


            }
        }

回答by dkozl

To create merged image you can use DrawingContextthat gives you methods like DrawTextor DrawImageand then render it using RenderTargetBitmap.Render:

要创建合并图像,您可以使用DrawingContext它为您提供类似DrawText或的方法DrawImage,然后使用RenderTargetBitmap.Render以下方法渲染它:

var drawingVisual = new DrawingVisual();
var drawingContext = drawingVisual.RenderOpen();
drawingContext.DrawImage(BitmapSource.Create(colorFrame.Width, colorFrame.Height, 96, 96, PixelFormats.Bgr32, null, colorData, colorFrame.Width * colorFrame.BytesPerPixel), 
                          new Rect(new Size(colorFrame.Width, colorFrame.Height)));
var overlayImage = new BitmapImage(new Uri("Images/boxbag.jpg"));
drawingContext.DrawImage(overlayImage, 
                          new Rect(x, y, overlayImage.Width, overlayImage.Height));
drawingContext.Close();
var mergedImage = new RenderTargetBitmap(colorFrame.Width, colorFrame.Height, 96, 96, PixelFormats.Pbgra32);
mergedImage.Render(drawingVisual);

KinectVideo.Source = mergedImage;

回答by Sheridan

If you just want display an Imageon top of another UI control, then you can either just declare one afterthe other UI elements, or set the Panel.ZIndexproperty:

如果您只想Image在另一个 UI 控件之上显示一个,那么您可以在其他 UI 元素之后声明一个,或者设置Panel.ZIndex属性:

<Grid>
    <Border Background="Black" />
    <Image Source="/AppName;component/Images/ImageName.jpg" Width="50" Height="50" />
</Grid>

Or:

或者:

<Grid>
    <Image Source="/AppName;component/Images/ImageName.jpg" 
        Width="50" Height="50" Panel.ZIndex="1" />
    <Border Background="Black" />
</Grid>

To find out how to data bind a BitmapImageto an Image.ItemsSourceproperty, please see the Bind Xaml bitmap imagequestion here on StackOverflow. To position the Imagein a specific place, you can either use the Image.Marginproperty or put it in a Canvasand use the Canvas.Leftand Canvas.Topproperties.

要了解如何将数据绑定BitmapImageImage.ItemsSource属性,请参阅StackOverflow 上的绑定 Xaml 位图图像问题。要将Image放置在特定位置,您可以使用该Image.Margin属性或将其放入 aCanvas并使用Canvas.LeftandCanvas.Top属性。