ActiveX控件

1.新建工程

新建一个MFC ActiveX ControlWizard,取名:Clock,完成,编译运行,点击黑三角块,选择ActiveX Control Test Coontainer,再选择Edit –> Insert Control… -> Clock Control -> OK

注:在编译的时候,VC自动给生成的ActiveX控件注册了,在运行框中输入:

Regsvr32 /u D:\c programs\C_WORKSPACE\Clock\Debug\Clock.ocx 即可反注册。

2.编辑时钟控件

编辑CClockCtrl::OnDraw

void CClockCtrl::OnDraw(  
            CDC* pdc, const CRect& rcBounds, const CRect& rcInvalid)  
{  
    // TODO: Replace the following code with your own drawing code.  
    //pdc->FillRect(rcBounds, CBrush::FromHandle((HBRUSH)GetStockObject(WHITE_BRUSH)));//
填充背景  
    //pdc->Ellipse(rcBounds); //
画椭圆  
    CTime time=CTime::GetCurrentTime();//
获取当前系统时间  
    CString str=time.Format("%H:%M:%S");//
将时间格式化并存放到字符串变量中  
    pdc->TextOut(0,0,str);//
(0,0)的位置将时间输出  
}

CClockCtrl类上添加消息处理函数WM_CREATEWM_TIMER,编辑:

int CClockCtrl::OnCreate(LPCREATESTRUCT lpCreateStruct)   
{  
    if (COleControl::OnCreate(lpCreateStruct) == -1)  
        return -1;  
    SetTimer(1,1000,NULL);//
设置时间间隔  
    return 0;  


void CClockCtrl::OnTimer(UINT nIDEvent)   
{  
    // TODO: Add your message handler code here and/or call default  
    //Invalidate();//
使窗口无效,让窗口重绘  
    InvalidateControl();//
使整个时钟控件重绘  
    COleControl::OnTimer(nIDEvent);  
}

运行,添加控件,测试。也可以在其它程序中测试,如在VB中测试。

3.给控件添加背景色与前景色

    ClassWizard…. -> Automation -> Add Property…. -> 再选择一种属性,这样添加BackColorForeColor,并选中Stock选项。

    ActiveX控件的四种属性:

CClockCtrl::OnDraw函数中编辑:

void CClockCtrl::OnDraw( 
            CDC* pdc, const CRect& rcBounds, const CRect& rcInvalid) 

    // TODO: Replace the following code with your own drawing code. 
    //pdc->FillRect(rcBounds, CBrush::FromHandle((HBRUSH)GetStockObject(WHITE_BRUSH)));//
填充背景 
    //pdc->Ellipse(rcBounds); //
画椭圆 
 
    CBrush brush(TranslateColor(GetBackColor())); 
    //
获得控件的背景色OLE_COLOR,并将其转换成COLORREF,再设置到创建的画刷上 
    pdc->FillRect(rcBounds, &brush);//
填充背景色 
    //
注意:SetBkColor()是用于设置背景色的属性值 
    pdc->SetBkMode(TRANSPARENT);//
将文字的背景色设置成透明 
    pdc->SetTextColor(TranslateColor(GetForeColor()));//
设置前景色 
 
    CTime time=CTime::GetCurrentTime();//
获取当前系统时间 
    CString str=time.Format("%H:%M:%S");//
将时间格式化并存放到字符串变量中 
    pdc->TextOut(0,0,str);//
(0,0)的位置将时间输出 
}

4.在属性表中添加设置颜色的属性页

ClockCtl.cpp中编辑:

// Property pages 
 
// TODO: Add more property pages as needed.  Remember to increase the count! 
BEGIN_PROPPAGEIDS(CClockCtrl, 2)//2
表示属性页的数量 
    PROPPAGEID(CClockPropPage::guid) 
    PROPPAGEID(CLSID_CColorPropPage) //
添加颜色属性页 
END_PROPPAGEIDS(CClockCtrl)

运行,测试OK !

5.自定义属性页

ClassWizard…. -> Automation -> Add Property…. -> 手动添加一种属性Interval ,类型选择short,implementation选择Member variable,编辑CClockCtrl::OnIntervalChanged函数:

void CClockCtrl::OnIntervalChanged()  

    // TODO: Add notification handler code 
    if(m_interval<0||m_interval>6000
    { 
        m_interval=1000
    } 
    else 
    { 
        m_interval=m_interval/1000*1000;//
将用户的输入取整 
        KillTimer(1);//
销毁先前的定时器 
        SetTimer(1,m_interval,NULL);//
设置定时器 
    }
 
    SetModifiedFlag(); 
}

编辑IDD_PROPPAGE_CLOCK属性对话框,如下图:

并对编辑框关联一个变量,右键-> ClassWizard… ,如下图:

6.给控件添加方法和事件

添加方法:

View->classwizard->Automation()->Add Method -> (Extendal name:Hello,Interval name:Hello,Return type:void)-> OK ->OK

编辑CClockCtrl::Hello()函数:

void CClockCtrl::Hello()  

    MessageBox("Hello World !"); 
}

添加标准事件:

View->classwizard->ActiveX Events->(External name:Click,Implementation:Stock)->OK->OK

添加自定义事件:

DClockEvents->右键->Add Event… ->(External name:NewMinute),接着在CClockCtrl::OnDraw中编辑:

void CClockCtrl::OnDraw( 
            CDC* pdc, const CRect& rcBounds, const CRect& rcInvalid) 

    ............ 
    ............ 
    CTime time=CTime::GetCurrentTime();//
获取当前系统时间 
    if(0==time.GetSecond())//
当秒数到达,进入另一分钟时 
    { 
        FireNewMinute();//
发出事件通知 
    } 
    CString str=time.Format("%H:%M:%S");//
将时间格式化并存放到字符串变量中 
    pdc->TextOut(0,0,str);//
(0,0)的位置将时间输出 
}

7.使控件自定义的属性持久保存

CClockCtrl::DoPropExchange函数中编辑:

void CClockCtrl::DoPropExchange(CPropExchange* pPX) 

    ExchangeVersion(pPX, MAKELONG(_wVerMinor, _wVerMajor)); 
    COleControl::DoPropExchange(pPX); 
     // TODO: Call PX_ functions for each persistent custom property. 
    PX_Short(pPx,"Interval",m_interval,1000);//
使Interval属性具有持久性 
}

并将CClockCtrl::OnCreate函数中修改:

SetTimer(1,m_interval,NULL);//设置时间间隔

在属性值改变时通知容器,在CClockCtrl::OnIntervalChanged函数中编辑:

void CClockCtrl::OnIntervalChanged()  

    .......... 
    .......... 
        SetTimer(1,m_interval,NULL);//
设置定时器 
        BoundPropertyChanged(0x1);//
通知容器调度ID1的属性发生了改变 
    } 
    SetModifiedFlag(); 
}

调度id说明:

     [ uuid(DA664AEC-9974-4A9E-9A14-9F29A64C9910), 
      helpstring("Dispatch interface for Clock Control"), hidden ] 
    dispinterface _DClock 
    { 
        properties: 
            // NOTE - ClassWizard will maintain property information here. 
            //    Use extreme caution when editing this section. 
            //{{AFX_ODL_PROP(CClockCtrl) 
            [id(DISPID_BACKCOLOR), bindable, requestedit] OLE_COLOR BackColor; 
            [id(DISPID_FORECOLOR), bindable, requestedit] OLE_COLOR ForeColor; 
            [id(1)] short Interval; //1表示属性的调度ID 
            //}}AFX_ODL_PROP 
 
        methods: 
            // NOTE - ClassWizard will maintain method information here. 
            //    Use extreme caution when editing this section. 
            //{{AFX_ODL_METHOD(CClockCtrl) 
            [id(2)] void Hello(); 
            //}}AFX_ODL_METHOD 
 
            [id(DISPID_ABOUTBOX)] void AboutBox(); 
    }; 

8.让时间值只在运行时走动

CClockCtrl::OnTimer中编辑:

void CClockCtrl::OnTimer(UINT nIDEvent)  

    // TODO: Add your message handler code here and/or call default 
    if(AmbientUserMode())//
如果返回为真,则表明是在运行时,重绘 
    {
 
        //Invalidate();//
使窗口无效,让窗口重绘 
        InvalidateControl();//
使整个时钟控件重绘 
    } 
    COleControl::OnTimer(nIDEvent); 
}

9.编写一个控件测试程序

新建一个基于对话框的MFC的对话框应用程序,取名ClockTest.

在对话框资源上右键->插入ActiveX控件… ->clock control …. ,然后再按ctrl+T测试。插入控件:Project->add to project->conponents and controls…-> Registered ActiveX Controls-> Clock Control->OK->OK,这样VC就会给这个工程添加一个CClock类,在资源中添加一个按钮,双击添加命令消息响应,在CClockTestDlg类上添加一个成员变量:

private
    CClock m_clock;

并在ClockTestDlg.h中包含一个:#include "clock.h" 头文件。

编辑CClockTestDlg::OnButton1

void CClockTestDlg::OnButton1()  

    // TODO: Add your control notification handler code here 
    m_clock.Create("Clock",WS_CHILD|WS_VISIBLE,CRect(0,0,100,50), 
        this,123);//
创建一个时钟控件 
    //m_clock.Hello();//
调用ActiveX控件中的Hello方法 
    m_clock.SetBackColor(RGB(0,0,255));//
设置背景色 
    m_clock.SetForeColor(RGB(255,0,0));//
设置前景色 
}

在程序中对控件的点击事件进行访问

Clock控件上点右键->事件->(分别给ClickNewMinute添加消息响应),编辑:

void CClockTestDlg::OnClickClockctrl2()  
{     

MessageBox("控件被点击了"); 

 
void CClockTestDlg::OnNewMinuteClockctrl2()  
{     

MessageBox("New Minute"); 
}

运行, OK!!!

 

原文地址:https://www.cnblogs.com/luowei010101/p/2052278.html