Chinaunix首页 | 论坛 | 博客
  • 博客访问: 2647424
  • 博文数量: 416
  • 博客积分: 10220
  • 博客等级: 上将
  • 技术积分: 4193
  • 用 户 组: 普通用户
  • 注册时间: 2006-12-15 09:47
文章分类

全部博文(416)

文章存档

2022年(1)

2021年(1)

2020年(1)

2019年(5)

2018年(7)

2017年(6)

2016年(7)

2015年(11)

2014年(1)

2012年(5)

2011年(7)

2010年(35)

2009年(64)

2008年(48)

2007年(177)

2006年(40)

我的朋友

分类: C/C++

2007-12-08 09:12:12

曾经在VCKbase(VC知识库)网站看到过一篇关于Flash的文章,叫做《在VC中使用 Flash 美化你的程序》,文章中介绍的是使用Flash控件在对话框程序中播放Flash文件。由于以前的工作需要曾经接触过使用Scoket通信在VC的Exe程序和Flash程序中通信的相关技术。在这里介绍给大家。相比上面的那篇文章,其有一下有点:
1、  界面上更加优美。所有的界面部分都是直接使用Flash。
2、  所能完成的功能更加完备。几乎所有能在VC的程序中能使用的功能都可以使用。
要做到以上两点所要做的工作也是很简单的,使用的技术也很简单。只要求以下几点:
1、  会使用简单的Flash编辑工具。会写简单的Flash Script脚本。
2、  Socket编程的相关知识。
程序的原理就是:VC程序(对话框程序)在启动以后最小化的任务栏,并建立一个Socket Server进行侦听,在建立完Socket和设置好相关的处理函数以后,启动编译为Exe的Flash程序,Flash程序通过Socket于VC程序建立连接,将Flash界面上的操作转换为Socket通信,让VC程序处理完成以后将结果返回给Flash程序。其简单的步骤为:
1、  在VC程序端(或者其他任何编程语言的程序):建立一个对话框程序,在APP类的InitInstance()函数中添加Scoket初始化:
if (!AfxSocketInit())
       {
              AfxMessageBox(IDP_SOCKETS_INIT_FAILED);
              return FALSE;
}
2、  在对话框类的OnInitDialog()函数中添加处理界面部分的程序段:
MoveWindow(0,0,0,0);  //将对话框程序界面改变为0
ShowWindow(SW_SHOWMINIMIZED);   //使界面最小化到任务栏
OnOK(); //调用对话框的OnOK函数
3、  在对话框类的OnOK()函数中建立Socket server并侦听:
WSADATA wsaData;
    int iErrorCode;
    if (WSAStartup(MAKEWORD(2,1),&wsaData)) //Windows Sockets DLL
       {
               AfxMessageBox("Winsock can not initialize.",MB_ICONSTOP);
         WSACleanup();
               SendMessage(WM_CLOSE,NULL,NULL);//关闭对话框程序
         return;
       }
 
       //Create server Socket,type is SOCK_STREAM,
       ServerSocket = socket(PF_INET,SOCK_STREAM,0);   
    if(ServerSocket == INVALID_SOCKET)
       {
              AfxMessageBox("Could not create server Socket.",MB_ICONSTOP);
              SendMessage(WM_CLOSE,NULL,NULL); //关闭对话框程序
         return;
       }
m_sockServerAddr.sin_family = AF_INET;
//IP 设置为广播
    m_sockServerAddr.sin_addr.s_addr = inet_addr("127.0.0.1");
       //使用9813端口,自己编程的时候可以随意选择,最好使用5000以后的
    m_sockServerAddr.sin_port = htons(9813);
 
//绑定Socket
    if (bind(ServerSocket,(LPSOCKADDR)&m_sockServerAddr,sizeof(m_sockServerAddr)) == SOCKET_ERROR) //
    {
              AfxMessageBox("Could not bind Server socket.",MB_ICONSTOP);
              SendMessage(WM_CLOSE,NULL,NULL); //关闭对话框程序
        return;
       }
    iErrorCode = WSAAsyncSelect(ServerSocket,m_hWnd,WM_CLIENT_ACCEPT,FD_ACCEPT);
    if (iErrorCode == SOCKET_ERROR)
       {
              AfxMessageBox("Could not select socket.",MB_ICONSTOP);
           SendMessage(WM_CLOSE,NULL,NULL); //关闭对话框程序
         return;
       }
 
    if (listen(ServerSocket,1) == SOCKET_ERROR) //begin listen client
       {
              AfxMessageBox("Could not listen.",MB_ICONSTOP);
              SendMessage(WM_CLOSE,NULL,NULL);
        return;
       }
       //启动Flash程序
       CString FlashExePath;
       char DialogExePath[256];
   //获得对话框程序的路径,包含文件名
       ::GetModuleFileName(0, DialogExePath, sizeof(DialogExePath));
       FlashExePath = DialogExePath;
   //去除对话框程序文件名,获得所在目录路径
       int Len = FlashExePath.ReverseFind('\\');
       FlashExePath = FlashExePath.Left(Len);
       // Sample.exe为编译好的Flash程序,存放在和VC程序同一目录下
       FlashExePath  += ""; 
   WinExec(FlashExePath,1);
      
       return;
}
相关变量定义在对话框类的头文件中,作为成员变量:
SOCKET Client;        //客户的连接请求
       SOCKET ServerSocket;             //SOCKET
       SOCKADDR_IN m_sockServerAddr;  //SOCKET 结构
4.在对话框程序中添加Socket的处理函数:
头文件中添加:
#define WM_CLIENT_ACCEPT WM_USER+101
#define WM_CLIENT_READCLOSE WM_USER+102

LRESULT OnAccept(WPARAM wParam, LPARAM lParam);
LRESULT OnReadClose(WPARAM wParam,LPARAM lParam);
在CPP文件中添加消息映射宏和相关函数的实现:
       ON_MESSAGE(WM_CLIENT_ACCEPT,OnAccept)
       ON_MESSAGE(WM_CLIENT_READCLOSE,OnReadClose)

LRESULT CSetupDlg::OnAccept(WPARAM wParam,LPARAM lParam)
{
//出错返回
       if (WSAGETSELECTERROR(lParam))
       {
              return 0L;
       }
      
       if(WSAGETSELECTEVENT(lParam) == FD_ACCEPT)
       {
           Client = accept(ServerSocket,(LPSOCKADDR)&m_sockServerAddr,0);
 
           if (Client == INVALID_SOCKET)
              {
                     AfxMessageBox("INVALID_SOCKET.",MB_ICONSTOP);
                     return 0L;
              }
              WSAAsyncSelect(Client,m_hWnd,WM_CLIENT_READCLOSE,FD_READ|FD_CLOSE);
       }
      
       return 0L;
}
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
LRESULT CSetupDlg::OnReadClose(WPARAM wParam,LPARAM lParam)
{  
//在这里接收从Flash发送来的数据包,并解析它们,根据包中的数据不同通过Swith执行相//关的操作,可以调用其他的函数,需要将执行的结果返回(发送)给Flash。
       CString str;
       switch (WSAGETSELECTEVENT(lParam))
       {
       //这里的msg和msg中的相关定义都是自定义的结构体
       case FD_READ:
              if(recv(Client,(char *)&msg,sizeof(msg),0) == SOCKET_ERROR)
              {
                     return 0;
              }
              str.Format("%s",msg.msg);
              list.InsertString(0,str);
              {     
                     PSockmsg recmsg=(PSockmsg)msg.msg;
                     str=recmsg->msg;
                     switch(recmsg->action)
                     {
                            case 'D':
                                   break;          
                            case 'W':
                                   break;
                            default:
                     }
              }
              break;
       case FD_CLOSE:
              str = _T("client close.");
              closesocket(Client);//关闭Socket
              SendMessage(WM_CLOSE,NULL,NULL);//发送消息结束程序
              break;
       }
       return 0L;
}
这段函数我就不多解释了,注意在OnOK中的WSAAsyncSelect调用确定了当收到发生Socket事件的时候发出WM_CLIENT_ACCEPT消息。第二个消息处理函数中用到了一些自定义的结构体,这是在和Flash统一以后确定的一些结构体,用于在Flash和VC程序之间传递消息参数的,这也是其重要的部分,需要根据实际的情况确定。
 
2.在Flash端:需要进行Socket连接,并组织并发送相关的Socket包,接收VC端返回的结果。参考代码:
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
function onsock(success) {
        if (success) {
            _root.gotoAndPlay(2);
        } else {
            _root.gSock.connect("127.0.0.1", 9813);//连接VC程序
         }
    }
    function onsockclose() {
        fscommand ("quit");
    }
    stop();
    fscommand ("fullscreen", false);
    fscommand ("allowscale", false);
    fscommand ("showmenu", false);
    Stage.showMenu = false;
    var gSock = new XMLSocket ();//new一个Socket对象
    var installed = false;
    var usethreeside = false;
    var havewireless = false;
    var finished = false;
    var osys = true;
    var mem = true;
    var processor = true;
    var harddisk = true;
    var network = true;
    gSock.onClose = onsockclose;//指定Socket的相关回调函数
    _root.gSock.connect("127.0.0.1", 9813);//调用自定义的函数
_root.gSock.onConnect = onsock;
///////////////////////////////////////////////////////////////
//接收并判断相关的在VC程序段执行的结果。
function onrecv(XMLDoc) {
        var _local2;
        _local2 = XMLDoc.toString();
        if (_local2 == "failed") {
            _root.osys = false;
        }
        _root.gotoAndPlay(196);
    }
    _root.stop();
    _root.gSock.onXML = onrecv;
    var local1;
    local1 = "Wcheckos";//相关的信息组织
    _root.gSock.send(local1);//发送数据
 
就写这么多了,也许相关的说明不是很清楚,主要是因为在做这个工作的时候,Flash端都是公司的美工做的,我对Flash也不是很熟悉。一直想给大家做一个Demo程序,但是真的是由于本人对Flash的操作实在是有限,如果有相关的Flash高手愿意,可以联系我一起给大家做一个Demo。我现在的Mail为:。这种应用一般使用在安装程序上的比较多,通过Socket通信在VC程序端调用相关的函数执行一些在Flash中很难执行的操作,比如检测硬件,写系统注册表,Copy文件,调用第三方的程序等等。
阅读(1140) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~