zoukankan      html  css  js  c++  java
  • InteropBitmap指定内存,绑定WPF的Imag控件时刷新问题。

    1.InteropBitmap指定内存,绑定WPF的Imag控件的Source属性

    创建InteropBitmap的时候,像素的格式必须为PixelFormats.Bgr32,

    如果不是的话在绑定到Image控件的Source属性,刷新新界面(BitmapSource.Invalidate())的时候会造成内存泄露。

    2. 内存映射:

        //内存共享类
        internal class Win32Mess
        {
            [DllImport("VCamBridge.dll", EntryPoint = "InitializeCam", CallingConvention = CallingConvention.Cdecl)]
            public static extern byte InitializeCam(string header, string body);
            [DllImport("VCamBridge.dll", EntryPoint = "SetFrameInfo", CallingConvention = CallingConvention.Cdecl)]
            public static extern void SetFrameInfo(int width, int height);
    
            [DllImport("Kernel32.dll", EntryPoint = "RtlMoveMemory")]
            public static extern void CopyMemory(IntPtr Destination, IntPtr Source, int Length);
    
            [DllImport("user32.dll", CharSet = CharSet.Auto)]
            public static extern IntPtr SendMessage(IntPtr hWnd, int Msg, int wParam, IntPtr lParam);
    
            [DllImport("Kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
            public static extern IntPtr CreateFileMapping(int hFile, IntPtr lpAttributes, uint flProtect, uint dwMaxSizeHi, uint dwMaxSizeLow, string lpName);
    
            [DllImport("Kernel32.dll", CharSet = CharSet.Auto)]
            public static extern IntPtr OpenFileMapping(int dwDesiredAccess, [MarshalAs(UnmanagedType.Bool)] bool bInheritHandle, string lpName);
    
            [DllImport("Kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
            public static extern IntPtr MapViewOfFile(IntPtr hFileMapping, uint dwDesiredAccess, uint dwFileOffsetHigh, uint dwFileOffsetLow, uint dwNumberOfBytesToMap);
    
            [DllImport("Kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
            public static extern bool UnmapViewOfFile(IntPtr pvBaseAddress);
    
            [DllImport("Kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
            public static extern bool CloseHandle(IntPtr handle);
    
            [DllImport("kernel32", EntryPoint = "GetLastError")]
            public static extern int GetLastError();
    
            const int ERROR_ALREADY_EXISTS = 183;
    
            const int FILE_MAP_COPY = 0x0001;
            public const int FILE_MAP_WRITE = 0x0002;
            const int FILE_MAP_READ = 0x0004;
            public const int FILE_MAP_ALL_ACCESS = 0x0002 | 0x0004; //0xF001F;
    
            const int PAGE_READONLY = 0x02;
            const int PAGE_READWRITE = 0x04;
            const int PAGE_WRITECOPY = 0x08;
            const int PAGE_EXECUTE = 0x10;
            const int PAGE_EXECUTE_READ = 0x20;
            const int PAGE_EXECUTE_READWRITE = 0x40;
    
            const int SEC_COMMIT = 0x8000000;
            const int SEC_IMAGE = 0x1000000;
            const int SEC_NOCACHE = 0x10000000;
            const int SEC_RESERVE = 0x4000000;
    
            const int INVALID_HANDLE_VALUE = -1;
    
            IntPtr m_hSharedMemoryFile = IntPtr.Zero;
            IntPtr m_pwData = IntPtr.Zero;
            bool m_bAlreadyExist = false;
            bool m_bInit = false;
            public bool IsOpen
            {
                get { return this.m_bInit; }
            }
            long m_MemSize = 0;
    
            public Win32Mess()
            {
            }
            ~Win32Mess()
            {
                Close();
            }
    
            /// 
            /// 初始化共享内存
            /// 
            /// 共享内存名称
            /// 共享内存大小
            /// 
            public int Init(string strName, long lngSize)
            {
                if (lngSize <= 0 || lngSize > 0x00800000) lngSize = 0x00800000;
                m_MemSize = lngSize;
                if (strName.Length > 0)
                {
                    //创建内存共享体(INVALID_HANDLE_VALUE)
                    m_hSharedMemoryFile = CreateFileMapping(INVALID_HANDLE_VALUE, IntPtr.Zero, (uint)PAGE_READWRITE, 0, (uint)lngSize, strName);
                    if (m_hSharedMemoryFile == IntPtr.Zero)
                    {
                        m_bAlreadyExist = false;
                        m_bInit = false;
                        return 2; //创建共享体失败
                    }
                    else
                    {
                        if (GetLastError() == ERROR_ALREADY_EXISTS) //已经创建
                        {
                            m_bAlreadyExist = true;
                        }
                        else                                         //新创建
                        {
                            m_bAlreadyExist = false;
                        }
                    }
                    //---------------------------------------
                    //创建内存映射
                    m_pwData = MapViewOfFile(m_hSharedMemoryFile, FILE_MAP_ALL_ACCESS, 0, 0, (uint)lngSize);
                    if (m_pwData == IntPtr.Zero)
                    {
                        m_bInit = false;
                        CloseHandle(m_hSharedMemoryFile);
                        return 3; //创建内存映射失败
                    }
                    else
                    {
                        m_bInit = true;
                        if (m_bAlreadyExist == false)
                        {
                            //初始化
                        }
                    }
                    //----------------------------------------
                }
                else
                {
                    return 1; //参数错误     
                }
    
                return 0;     //创建成功
            }
            public InteropBitmap GetImage(System.Drawing.Size sizeMemory)
            {
                if (m_bInit)
                    return System.Windows.Interop.Imaging.CreateBitmapSourceFromMemorySection(m_hSharedMemoryFile,
                        (int)sizeMemory.Width, (int)sizeMemory.Height, PixelFormats.Bgr32,
                         (int)(sizeMemory.Width * PixelFormats.Bgr32.BitsPerPixel / 8), 0) as InteropBitmap;
                else
                    return null;
    
            }
    
            /// 
            /// 关闭共享内存
            /// 
            public void Close()
            {
                if (m_bInit)
                {
                    UnmapViewOfFile(m_pwData);
                    CloseHandle(m_hSharedMemoryFile);
                    m_hSharedMemoryFile = IntPtr.Zero;
                    m_bInit = false;
                }
            }
    
            /// 
            /// 读数据
            /// 
            /// 数据
            /// 起始地址
            /// 个数
            /// 
            public int Read(ref byte[] bytData, int lngAddr, int lngSize)
            {
                if (lngAddr + lngSize > m_MemSize) return 2; //超出数据区
                if (m_bInit)
                {
                    Marshal.Copy(m_pwData, bytData, lngAddr, lngSize);
                }
                else
                {
                    return 1; //共享内存未初始化
                }
                return 0;     //读成功
            }
    
            /// 
            /// 写数据
            /// 
            /// 数据
            /// 起始地址
            /// 个数
            /// 
            public int Write(byte[] bytData, int lngAddr, int lngSize)
            {
                if (lngAddr + lngSize > m_MemSize) return 2; //超出数据区
                if (m_bInit)
                {
                    Marshal.Copy(bytData, lngAddr, m_pwData, lngSize);
                }
                else
                {
                    return 1; //共享内存未初始化
                }
                return 0;     //写成功
            }
            public int Write(IntPtr lngAddr, int lngSize)
            {
                if (lngSize > m_MemSize) return 2; //超出数据区
                if (m_bInit)
                {
                    CopyMemory(m_pwData, lngAddr, lngSize);
                }
                else
                {
                    return 1; //共享内存未初始化
                }
                return 0;     //写成功
            }
        }
     
  • 相关阅读:
    lvs持久连接及防火墙标记实现多端口绑定服务
    LVS负载均衡器DR模型的实现
    CentOS 6.5结合busybox完成自制Linux系统及远程登录和nginx安装测试
    CentOS 6.5下的lamp环境rsyslog+MySQL+loganalyzer实现日志集中分析管理
    centos中selinux功能及常用服务配置
    网站遭遇CC及DDOS攻击紧急处理方案
    centos6.5下系统编译定制iptables防火墙扩展layer7应用层访问控制功能及应用限制QQ2016上网
    centos 6.5内核编译步骤及配置详解
    centos系统初始化流程及实现系统裁剪
    iptables实现网络防火墙及地址转换
  • 原文地址:https://www.cnblogs.com/kissfu/p/3817776.html
Copyright © 2011-2022 走看看