zoukankan      html  css  js  c++  java
  • Delphi7 从资源文件中载入GDI+对象

    GDI+的Image及派生类中涉及到IStream流,在Delphi和C++Builder中广泛使用的TStream不能直接作为参数进行传递,VCL提供了一个TStreamAdapter类,用于把VCL流TStream转换为IStream。TStreamAdapter的构造过程原型如下:

    constructor Create(Stream: TStream; Ownership: TStreamOwnership = soReference);

    其中的TStreamOwnership枚举类型有2个值:soReference和,如果是soOwned,TStream对象由TStreamAdapter释放,否则由用户自己处理。请看下面的用流建立Image的Delphi代码:

    var
       Stream: TMemoryStream;
       Adapter: TStreamAdapter;
       Image: TGpImage;
    begin
       Stream := TMemoryStream.Create;
       Stream.LoadFromFile('Test.jpg');
       Adapter := TStreamAdapter.Create(Stream, soOwned);
       Image := TGpImage.Create(Adapter);
      try
         .....
      finally
         Image.Free;
       end;
    end;
            代码中,首先建立一个内存流,并从磁盘中装入一个图像文件,然后用TStreamAdapter将这个流封装起来,转换为IStream,供建立TGpImage使用。注意,我在建立TStreamAdapter对象时使用了soOwned,这样,由Adapter负责释放Stream,否则,必须在Image.Free后面Stream.Free。但是TStreamAdapter对象Adapter为什么没有释放代码呢?因为TStreamAdapter是个接口实现类,作为IStream传递给TGpImage.Create后,由系统自动跟踪释放,如果我们将它Free,会引起错误,如果非要显式释放它,必须用var I: IStream; I := Adapter; I := nil;的方法释放,而且必须在Image.Free之前,因为在Image.Free的同时,Adapter也随着IStream一起被释放掉了。


    上面的代码在Delphi7 调试状态下会出现错误,在网上找了个C的代码,现在改为Pascal的,在个人机子上调试稳定:

    function LoadGPImageFormRes(aHMoudle: DWORD; ResName, ResType: string):
        TGPImage;
    var
    HRes: HRSRC;
    sResName: string;
    sResType: string;
    Len: DWORD;
    lpRsrc: PByte;
    m_hMem: HGLOBAL;
    pMem: PByte;
    pstm: IStream;
    begin
    Result := nil;
    sResName := ResName;
    sResType := ResType;
    HRes := FindResource(HInstance, PChar(sResName), PChar(sResType));
    if HRes <> 0 then
    begin
        Len := SizeofResource(HInstance, HRes);
        lpRsrc := PByte(LoadResource(HInstance, HRes));
        try
          if lpRsrc <> nil then
          begin

            m_hMem := GlobalAlloc(GMEM_FIXED, Len);
            pMem := Pbyte(GlobalLock(m_hMem));
            CopyMemory(pMem, lpRsrc, Len);
            CreateStreamOnHGlobal(m_hMem, False, pstm);
            Result := TGPImage.Create(pstm);
            GlobalUnlock(m_hMem);
            pstm := nil;
            FreeResource(Dword(lpRsrc));
          end;
        except
          if Assigned(Result) then
          begin
            FreeAndNil(Result);
          end;
        end;

    end;

    end;

  • 相关阅读:
    Java验证码
    Java内存泄漏问题
    Java常见异常总结
    Java编码与乱码问题
    Spring:源码解读Spring IOC原理
    Quartz 定时邮件发送多个备份文件
    spring-boot 多线程
    java并发基础
    Java多线程中wait语句的具体使用技巧
    多线程的死锁
  • 原文地址:https://www.cnblogs.com/MaxWoods/p/1848479.html
Copyright © 2011-2022 走看看