亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb

首頁 > 學院 > 開發設計 > 正文

CRichEditCtrl實現MSN/QQ動畫表情

2019-11-17 04:59:51
字體:
來源:轉載
供稿:網友
  首先對標題說明一下,在MSN中,聊天的窗口可能是一個自定義的類。大家用Spy ++可以看看。對與自定義窗口,可以使用CreateWindow, SetWindowLong或者是SubclassWindow實現,不過這不是我現在討論的話題?! 『?, 先看看效果再說:
CRichEditCtrl實現MSN/QQ動畫表情


  關于這個的實現。我們首先應該明了,我們必須實現一個OLE對象。而且這個對象能夠播放GIF.對于播放GIF,代碼已經很多了。

  有了這個就完了么?當然不是。你還有寫一個OLE/COM對象。實現IOleObject等。你是用ATL還是MFC呢?我什么也沒有用。在這個目錄下%PRogram file%/tencent/QQ/,你可以看到一個ImageOle.dll,她就是你日夜思念的人!

  好吧,讓我們來看看他的真面目。怎么看?X Ray? 當然不是——OLE/COM Viewer.Click on “All Objects”,View TypeLib... 打開那個文件,你可以看到:
[
uuid(0C1CF2DF-05A3-4FEF-8CD4-F5CFC4355A16),
helpstring("IGifAnimator Interface"),
dual,
nonextensible
]
dispinterface IGifAnimator {
properties:
methods:
[id(0x00000001), helpstring("method LoadFromFile")]
void LoadFromFile([in] BSTR FileName);
[id(0x00000002), helpstring("method TriggerFrameChange")]
VARIANT_BOOL TriggerFrameChange();
[id(0x00000003), helpstring("method GetFilePath")]
BSTR GetFilePath();
[id(0x00000004), helpstring("method ShowText")]
void ShowText([in] BSTR Text);
};
  這個接口就是我們要的。你可以用ActiveX Control Test Container測試一下。還挺管用的。

  以下給出代碼:
  首先我們導入ImageOle.dll
#import "D://Program files//tencent//qq//ImageOle.dll" named_guids  named_guids 表示讓編譯器為我把對應庫的GUID和聲明對應起來。我們就可以用CLSID_GifAnimator引用對應的接口了。不用那一長串的東西。然后它就會為我們生成兩個文件。

更多文章 更多內容請看MSN圖像  MSN專題  QQ表情專題,或
ImageOle.tlh
1// Created by Microsoft (R) C/C++ Compiler Version 12.00.8168.0 (9de7951a).
2//
3// d:/myproject/msger/debug/ImageOle.tlh
4//
5// C++ source equivalent of Win32 type library D://Program files//tencent//qq//ImageOle.dll
6// compiler-generated file created 10/25/04 at 22:00:58 - DO NOT EDIT!
7#pragma once
8#pragma pack(push, 8)
9#include
10
11namespace ImageOleLib {
12
13//
14// Forward references and typedefs
15//
16
17strUCt /* coclass */ GifAnimator;

18struct __declspec(uuid("0c1cf2df-05a3-4fef-8cd4-f5cfc4355a16"))
19/* dual interface */ IGifAnimator;
20
21//
22// Smart pointer typedef declarations
23//
24
25_COM_SMARTPTR_TYPEDEF(IGifAnimator, __uuidof(IGifAnimator));
26
27//
28// Type library items
29//
30
31struct __declspec(uuid("06ada938-0fb0-4bc0-b19b-0a38ab17f182"))
32GifAnimator;
33 // [ default ] interface IGifAnimator
34
35struct __declspec(uuid("0c1cf2df-05a3-4fef-8cd4-f5cfc4355a16"))
36IGifAnimator : IDispatch
37{
38 //
39 // Wrapper methods for error-handling
40 //
41
42 HRESULT LoadFromFile (
43 _bstr_t FileName );
44 VARIANT_BOOL TriggerFrameChange ( );
45 _bstr_t GetFilePath ( );
46 HRESULT ShowText (
47 _bstr_t Text );
48
49 //
50 // Raw methods provided by interface
51 //
52
53 virtual HRESULT __stdcall raw_LoadFromFile (
54 BSTR FileName ) = 0;
55 virtual HRESULT __stdcall raw_TriggerFrameChange (
56 VARIANT_BOOL * pbChanged ) = 0;
57 virtual HRESULT __stdcall raw_GetFilePath (
58 BSTR * pFilePath ) = 0;
59 virtual HRESULT __stdcall raw_ShowText (
60 BSTR Text ) = 0;
61};
62
63//
64// Named GUID constants initializations
65//
66
67extern "C" const GUID __declspec(selectany) LIBID_ImageOleLib =
68 {0x710993a2,0x4f87,0x41d7,{0xb6,0xfe,0xf5,0xa2,0x03,0x68,0x46,0x5f}};
69extern "C" const GUID __declspec(selectany) CLSID_GifAnimator =
70 {0x06ada938,0x0fb0,0x4bc0,{0xb1,0x9b,0x0a,0x38,0xab,0x17,0xf1,0x82}};
71extern "C" const GUID __declspec(selectany) IID_IGifAnimator =
72 {0x0c1cf2df,0x05a3,0x4fef,{0x8c,0xd4,0xf5,0xcf,0xc4,0x35,0x5a,0x16}};
73
74//
75// Wrapper method implementations
76//
77#include "d:/myproject/msger/debug/ImageOle.tli"
78
79} // namespace ImageOleLib
80#pragma pack(pop)

更多文章 更多內容請看MSN圖像  MSN專題  QQ表情專題,或
ImageOle.tli
1// Created by Microsoft (R) C/C++ Compiler Version 12.00.8168.0 (9de7951a).
2//
3// d:/myproject/msger/debug/ImageOle.tli
4//
5// Wrapper implementations for Win32 type library D://Program files//tencent//qq//ImageOle.dll
6// compiler-generated file created 10/25/04 at 22:00:58 - DO NOT EDIT!
7#pragma once
8
9//
10// interface IGifAnimator wrapper method implementations
11//
12
13inline HRESULT IGifAnimator::LoadFromFile ( _bstr_t FileName ) {
14 HRESULT _hr = raw_LoadFromFile(FileName);
15 if (FAILED(_hr)) _com_issue_errorex(_hr, this, __uuidof(this));
16 return _hr;
17}
18
19inline VARIANT_BOOL IGifAnimator::TriggerFrameChange ( ) {

20 VARIANT_BOOL _result;
21 HRESULT _hr = raw_TriggerFrameChange(&_result);
22 if (FAILED(_hr)) _com_issue_errorex(_hr, this, __uuidof(this));
23 return _result;
24}
25
26inline _bstr_t IGifAnimator::GetFilePath ( ) {
27 BSTR _result;
28 HRESULT _hr = raw_GetFilePath(&_result);
29 if (FAILED(_hr)) _com_issue_errorex(_hr, this, __uuidof(this));
30 return _bstr_t(_result, false);
31}
32
33inline HRESULT IGifAnimator::ShowText ( _bstr_t Text ) {
34 HRESULT _hr = raw_ShowText(Text);
35 if (FAILED(_hr)) _com_issue_errorex(_hr, this, __uuidof(this));
36 return _hr;
37}
  有了這些,你使用接口和函數就很方便了。

  然后就這樣:
  WINOLEAPI CoInitializeEx(LPVOID pvReserved, DWord dwCoInit)
  為什么要這樣呢?因為我們使用這個函數。那有必要這樣么?在MSDN是說要 #define _DCOM_ 就行了。可惜我沒有成功。就只好這樣了。

  接著就是實現代碼了。現在看應該沒有很大的問題。假如還是很難明白。那么我你得好好研究CRichEditCtrl和OLE了。聽說Inside OLE和Inside COM很好。我沒有弄到。就看了《COM+編程指南》和潘愛民的《COM原理和應用》,不錯!還有一個好東西。就是 ActiveX Control Test Container 的源代碼。

更多文章 更多內容請看MSN圖像  MSN專題  QQ表情專題,或
  最后該出場的就是實現代碼了。
1 LPLOCKBYTES lpLockBytes = NULL;
2 SCODE sc;
3 HRESULT hr;
4 //print to RichEdit' s IClientSite
5 LPOLECLIENTSITE m_lpClientSite;
6 //A smart point to IAnimator
7 IGifAnimatorPtr m_lpAnimator;
8 //ptr 2 storage
9 LPSTORAGE m_lpStorage;
10 //the object 2 b insert 2
11 LPOLEOBJECT m_lpObject;
12
13 //Create lockbytes
14 sc = ::CreateILockBytesOnHGlobal(NULL, TRUE, &lpLockBytes);
15 if (sc != S_OK)
16 AfxThrowOleException(sc);
17 ASSERT(lpLockBytes != NULL);
18
19 //use lockbytes to create storage
20 sc = ::StgCreateDocfileOnILockBytes(lpLockBytes,
21 STGM_SHARE_EXCLUSIVESTGM_CREATESTGM_READWRITE, 0, &m_lpStorage);
22 if (sc != S_OK)
23 {
24 VERIFY(lpLockBytes->Release() == 0);
25 lpLockBytes = NULL;
26 AfxThrowOleException(sc);
27 }
28 ASSERT(m_lpStorage != NULL);
29
30 //get the ClientSite of the very RichEditCtrl
31 GetIRichEditOle()->GetClientSite(&m_lpClientSite);
32 ASSERT(m_lpClientSite != NULL);
33
34 try
35 {
36 //Initlize COM interface
37 hr = ::CoInitializeEx( NULL, COINIT_APARTMENTTHREADED );
38 if( FAILED(hr) )
39 _com_issue_error(hr);
40
41 //Get GifAnimator object
42 //here, I used a smart point, so I do not need to free it

43 hr = m_lpAnimator.CreateInstance(CLSID_GifAnimator);
44 if( FAILED(hr) )
45 _com_issue_error(hr);
46 //COM Operation need BSTR, so get a BSTR
47 BSTR path = strPicPath.AllocSysString();
48
49 //Load the gif
50 hr = m_lpAnimator->LoadFromFile(path);
51 if( FAILED(hr) )
52 _com_issue_error(hr);
53
54 TRACE0( m_lpAnimator->GetFilePath() );
55
56 //get the IOleObject
57 hr = m_lpAnimator.QueryInterface(IID_IOleObject, (void**)&m_lpObject);
58 if( FAILED(hr) )
59 _com_issue_error(hr);
60
61 //Set it 2 b inserted
62 OleSetContainedObject(m_lpObject, TRUE);
63
64 //2 insert in 2 richedit, you need a struct of REOBJECT
65 REOBJECT reobject;
66 ZeroMemory(&reobject, sizeof(REOBJECT));
67
68 reobject.cbStruct = sizeof(REOBJECT);
69 CLSID clsid;
70 sc = m_lpObject->GetUserClassID(&clsid);
71 if (sc != S_OK)
72 AfxThrowOleException(sc);
73 //set clsid
74 reobject.clsid = clsid;
75 //can be selected
76 reobject.cp = REO_CP_SELECTION;
77 //content, but not static
78 reobject.dvaspect = DVASPECT_CONTENT;
79 //goes in the same line of text line
80 reobject.dwFlags = REO_BELOWBASELINE; //REO_RESIZABLE
81 reobject.dwUser = 0;
82 //the very object
83 reobject.poleobj = m_lpObject;
84 //client site contain the object
85 reobject.polesite = m_lpClientSite;
86 //the storage
87 reobject.pstg = m_lpStorage;
88
89 SIZEL sizel;
90 sizel.cx = sizel.cy = 0;
91 reobject.sizel = sizel;
92 HWND hWndRT = this->m_hWnd;
93 //Sel all text
94// ::SendMessage(hWndRT, EM_SETSEL, 0, -1);
95// DWORD dwStart, dwEnd;
96// ::SendMessage(hWndRT, EM_GETSEL, (WPARAM)&dwStart, (LPARAM)&dwEnd);
97// ::SendMessage(hWndRT, EM_SETSEL, dwEnd+1, dwEnd+1);
98 //Insert after the line of text
99 GetIRichEditOle()->InsertObject(&reobject);
100 ::SendMessage(hWndRT, EM_SCROLLCARET, (WPARAM)0, (LPARAM)0);
101 VARIANT_BOOL ret;
102 //do frame changing
103 ret = m_lpAnimator->TriggerFrameChange();
104 //show it
105 m_lpObject->DoVerb(OLEIVERB_UIACTIVATE, NULL, m_lpClientSite, 0, m_hWnd, NULL);
106 m_lpObject->DoVerb(OLEIVERB_SHOW, NULL, m_lpClientSite, 0, m_hWnd, NULL);
107
108 //redraw the window to show animation
109 RedrawWindow();
110
111 if (m_lpClientSite)
112 {
113 m_lpClientSite->Release();
114 m_lpClientSite = NULL;
115 }
116 if (m_lpObject)
117 {
118 m_lpObject->Release();
119 m_lpObject = NULL;
120 }
121 if (m_lpStorage)
122 {
123 m_lpStorage->Release();
124 m_lpStorage = NULL;
125 }
126
127 SysFreeString(path);
128 }
129 catch( _com_error e )
130 {
131 AfxMessageBox(e.ErrorMessage());
132 ::CoUninitialize();
133 }

更多文章 更多內容請看MSN圖像  MSN專題  QQ表情專題,或

附:Delphi版的實現
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
StdCtrls, ActiveX, ComCtrls, RxRichEd, ImageOleLib_TLB;
//RxRichEd單元是Rxlib下的RxRichEdit,一套增強功能的RichEdit
//ImageOleLib_TLB是從qq的ImageOle.dll引入的類型庫

const
IID_IOleObject: TGUID = (
D1: $00000112; D2: $0000; D3: $0000; D4: ($C0, $00, $00, $00, $00, $00, $00,
$46));
EM_GETOLEINTERFACE= WM_USER + 60;

type
TForm1 = class(TForm)
Button1: TButton;
Editor: TRxRichEdit;
procedure Button1Click(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;

var
Form1: TForm1;
implementation
{$R *.DFM}
procedure TForm1.Button1Click(Sender: TObject);

var
FRTF: IRichEditOle;
FLockBytes: ILockBytes;
FStorage: ISTORAGE;
FClientSite: IOLECLIENTSITE;
m_lpObject: IOleObject;
m_lpAnimator: TGifAnimator;
i_GifAnimator: IGifAnimator;
reobject: TReObject;
clsid: TGuid;
sizel: tagSize;
dwStart, dwEnd: DWORD;
Rect:TRect;

begin
try
if CreateILockBytesOnHGlobal(0, True, FLockBytes) <> S_OK then
begin
showmessage('Error to create Global Heap');
exit;
end;
//建立一個混合文檔存取對象
if StgCreateDocfileOnILockBytes(FLockBytes, STGM_SHARE_EXCLUSIVE or
STGM_CREATE or STGM_READWRITE, 0, FStorage) <> S_OK then
begin
Showmessage('Error to create storage');
exit;
end;
//取得RichEdit的接口
Sendmessage(Editor.handle,EM_GETOLEINTERFACE,0,LongInt(@FRTF));

if FRTF.GetClientSite(FClientSite)<>S_OK then
begin
ShowMessage('Error to get ClentSite');
Exit;
end;

CoInitializeEx(nil, COINIT_APARTMENTTHREADED);
m_lpAnimator := TGifAnimator.Create(Self);
i_GifAnimator := m_lpAnimator.ControlInterface;
i_GifAnimator.LoadFromFile('c:/ti.gif');
i_GifAnimator.QueryInterface(IID_IOleObject, m_lpObject);
OleSetContainedObject(m_lpObject, True);
FillChar(ReObject, SizeOf(ReObject), 0);
ReObject.cbStruct := SizeOf(ReObject);
m_lpObject.GetUserClassID(clsid);
ReObject.clsid := clsid;
reobject.cp := REO_CP_SELECTION;
//content, but not static
reobject.dvaspect := DVASPECT_CONTENT;
//goes in the same line of text line
reobject.dwFlags := REO_BELOWBASELINE; //REO_RESIZABLE
reobject.dwUser := 0;
//the very object
reobject.poleobj := m_lpObject;
//client site contain the object
reobject.polesite := FClientSite;
//the storage
reobject.pstg := FStorage;
sizel.cx := 0;
sizel.cy := 0;
reobject.sizel := sizel;
//Sel all text


SendMessage(Editor.Handle, EM_SETSEL, 0, -1);
SendMessage(Editor.Handle, EM_GETSEL, dwStart, dwEnd);
SendMessage(Editor.Handle, EM_SETSEL, dwEnd + 1, dwEnd + 1);
//Insert after the line of text
FRTF.InsertObject(reobject);
SendMessage(Editor.Handle, EM_SCROLLCARET, 0, 0);
//VARIANT_BOOL ret;
//do frame changing
m_lpAnimator.TriggerFrameChange();
//show it
m_lpObject.DoVerb(OLEIVERB_UIACTIVATE, Nil, FClientSite, 0, Editor.Handle,Rect);
// m_lpObject.DoVerb(
m_lpObject.DoVerb(OLEIVERB_SHOW, Nil, FClientSite, 0, Editor.Handle, Rect);
//redraw the window to show animation
redrawwindow(Handle, nil, 0, RDW_ERASE or RDW_INVALIDATE or RDW_FRAME or RDW_ERASENOW or RDW_ALLCHILDREN);
finally
FRTF:=nil;
FClientSite := nil;
FStorage :=nil;
end;
end;
end
更多文章 更多內容請看MSN圖像  MSN專題  QQ表情專題,或

發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb
国产精品一区二区三区成人| 91精品国产高清久久久久久91| 日韩欧美精品在线观看| 亚洲国产精品系列| 成人精品久久av网站| 日韩av中文字幕在线播放| 热re99久久精品国产66热| 97人人模人人爽人人喊中文字| 日韩欧美中文在线| 九九精品在线播放| 亚洲成人在线视频播放| 亚洲深夜福利在线| 色婷婷久久一区二区| 亚洲桃花岛网站| 国产成人精品免费久久久久| 538国产精品一区二区免费视频| 国自产精品手机在线观看视频| 秋霞午夜一区二区| 国产亚洲a∨片在线观看| 久久久精品美女| 国产精品久久久999| 国产成人av在线| 韩剧1988在线观看免费完整版| 亚洲无线码在线一区观看| 日韩av电影中文字幕| 亚洲色图校园春色| 国产精品最新在线观看| 亚洲精品久久久久久久久久久| 97人洗澡人人免费公开视频碰碰碰| 久久精品国产免费观看| 日本亚洲欧洲色α| 日韩中文字幕在线精品| 国产亚洲精品美女久久久| 亚洲女人天堂色在线7777| 亚洲精品suv精品一区二区| 日韩视频第一页| 久热精品视频在线| 这里只有精品视频| 性金发美女69hd大尺寸| 亚洲一级免费视频| 日韩在线精品视频| 草民午夜欧美限制a级福利片| 日韩在线一区二区三区免费视频| 黑人巨大精品欧美一区二区免费| 一色桃子一区二区| 日韩天堂在线视频| zzjj国产精品一区二区| 精品亚洲一区二区三区| 日韩经典中文字幕| 亚洲aⅴ男人的天堂在线观看| 亚洲区bt下载| www.美女亚洲精品| 亚洲一区av在线播放| 国产欧美日韩中文字幕在线| 美日韩精品免费观看视频| 国产精品三级网站| 精品久久久久久久久久国产| 亚洲毛茸茸少妇高潮呻吟| 国产亚洲精品日韩| 91天堂在线视频| 国产亚洲精品一区二区| 亚洲欧美精品一区二区| 伊人伊成久久人综合网小说| 亚洲国产女人aaa毛片在线| 亚洲国产欧美日韩精品| 日韩天堂在线视频| 亚洲精选在线观看| 国产成人鲁鲁免费视频a| 欧美视频免费在线观看| 成人黄色免费在线观看| 亚洲国产婷婷香蕉久久久久久| 欧美激情第一页xxx| 日韩欧美在线看| 亚洲www永久成人夜色| 亚洲国产天堂久久综合| 亚洲激情成人网| 日韩国产高清污视频在线观看| 欧美午夜性色大片在线观看| 狠狠躁18三区二区一区| 亚洲大胆人体视频| 欧美福利视频在线| 国产精品一二区| 欧美大秀在线观看| 欧美激情伊人电影| 国产在线拍偷自揄拍精品| 国产精品69精品一区二区三区| 91极品女神在线| 美女啪啪无遮挡免费久久网站| 精品爽片免费看久久| 久久精品国产亚洲精品2020| 97视频免费看| 日韩欧美极品在线观看| 国产精品国产福利国产秒拍| 久久亚洲国产精品成人av秋霞| 91色精品视频在线| 亚洲精品一区二区在线| 日韩欧美在线免费| 国产精品www色诱视频| 久久久亚洲欧洲日产国码aⅴ| 亚洲一区999| 亚洲精品久久久久久久久久久久| 色噜噜狠狠狠综合曰曰曰88av| 性色av一区二区三区红粉影视| 国产精品免费久久久久久| 自拍偷拍亚洲欧美| 综合欧美国产视频二区| 亚洲一区二区三区久久| 亚洲最大av在线| 久久99热精品这里久久精品| 中文字幕精品一区二区精品| 国产做受69高潮| 日韩av黄色在线观看| 亚洲精品资源在线| 91精品久久久久久久久青青| 亚洲伊人久久大香线蕉av| 久久中文字幕在线| 久久青草精品视频免费观看| 国产精品视频成人| 日韩有码在线视频| 亚洲国产欧美久久| 亚洲乱码av中文一区二区| 欧美性极品xxxx娇小| 亚洲一区二区免费在线| 日韩一区二区在线视频| 日本久久久久久久久久久| 国产精品电影网站| 欧美激情喷水视频| 亚洲综合在线做性| 欧美激情精品久久久久久黑人| 国产精品2018| 亚洲精品一区二区在线| 国语自产精品视频在线看| 欧美理论电影网| 国产亚洲人成a一在线v站| 亚洲跨种族黑人xxx| 国产精品视频99| 欧洲成人午夜免费大片| 国产精品久久久久秋霞鲁丝| 欧美成人性生活| 成人欧美一区二区三区黑人| 国产精品中文字幕在线观看| 在线观看日韩视频| 伊人久久久久久久久久久| 韩剧1988免费观看全集| 国产一区二区激情| 国产精品观看在线亚洲人成网| 久久影院免费观看| 国产精品电影网| 欧美成人免费观看| 亚洲精品视频在线播放| 国产亚洲精品久久久久久777| 亚洲无线码在线一区观看| 亚洲国产欧美在线成人app| 国产精品一区二区久久久久| 狠狠躁夜夜躁人人爽超碰91| 欧美寡妇偷汉性猛交| 国产一区二区精品丝袜| www国产亚洲精品久久网站| 日韩最新在线视频| 亚洲va欧美va在线观看| 亚洲自拍偷拍色片视频| 海角国产乱辈乱精品视频| 欧美在线视频网| 国产精品69久久久久|