delphi 与 C++ 进程之间的命名管道通信

以C++生成的程序作为服务端,delphi生成的程序为客户端,实现客户端发送数据,服务端接受数据并处理。

 

客户端:

unit Unit1;



interface



uses

  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,

  Dialogs, StdCtrls,ShellAPI,ComCtrls, xmldom, XMLIntf, msxmldom, XMLDoc;



type

  TForm1 = class(TForm)

    GroupBox1: TGroupBox;

    PageControl1: TPageControl;

    TabSheet1: TTabSheet;

    TabSheet2: TTabSheet;

    Label1: TLabel;

    Label2: TLabel;

    Label3: TLabel;

    OpenDialog1: TOpenDialog;

    Button1: TButton;

    Button3: TButton;

    GroupBox2: TGroupBox;

    XMLDocument1: TXMLDocument;

    Button9: TButton;

    Label4: TLabel;

    Edit1: TEdit;

    Label5: TLabel;

    Edit2: TEdit;

    Edit3: TEdit;

    Edit4: TEdit;

    Edit5: TEdit;

    Edit6: TEdit;

    Edit7: TEdit;

    Edit8: TEdit;

    Edit9: TEdit;

    Label7: TLabel;

    Label8: TLabel;

    Edit10: TEdit;

    GroupBox4: TGroupBox;

    Label9: TLabel;

    ComboBox1: TComboBox;

    Label10: TLabel;

    ComboBox2: TComboBox;

    TabSheet3: TTabSheet;

    GroupBox5: TGroupBox;

    ListBox1: TListBox;

    GroupBox3: TGroupBox;

    RadioButton1: TRadioButton;

    RadioButton2: TRadioButton;

    Label6: TLabel;

    Button2: TButton;

    Edit11: TEdit;

    Button4: TButton;

    Button5: TButton;

    Button6: TButton;

    procedure Button1Click(Sender: TObject);

    procedure FormCreate(Sender: TObject);

    procedure Button9Click(Sender: TObject);

    procedure Button4Click(Sender: TObject);

    procedure Button2Click(Sender: TObject);

    procedure ComboBox1Exit(Sender: TObject);

    procedure ComboBox2Exit(Sender: TObject);

    procedure ListBox1EndDrag(Sender, Target: TObject; X, Y: Integer);

    procedure ListBox1DragOver(Sender, Source: TObject; X, Y: Integer;

      State: TDragState; var Accept: Boolean);

    procedure Button3Click(Sender: TObject);

  private

    { Private declarations }

  public

    { Public declarations }

  end;



var

  Form1: TForm1;

  par, index: Integer; //判断是否存在config.xml



implementation



{$R *.dfm}



//选择图片(基本动作)

procedure TForm1.Button1Click(Sender: TObject);

begin

  form1.OpenDialog1.DefaultExt:='png'; //设置缺省扩展名

  form1.OpenDialog1.Title:='请选择一个png文件';  //设置对话框标题

  form1.OpenDialog1.Filter:='Text files(*.png)|*.png'; //设置文件过滤条件

  form1.OpenDialog1.Execute;   //打开对话框

  edit10.Clear;

  edit10.text:=OpenDialog1.FileName;

end;



//载入配置文件config.xml,并打开ConfigAction.win32.exe

procedure TForm1.FormCreate(Sender: TObject);

var

  nodelist: ixmlnodelist;

  node: ixmlnode;

  i: integer;

begin

  XMLDocument1.LoadFromFile(ExtractFilePath(Application.ExeName)+'config\config.xml');

  combobox1.Clear;

  nodelist:= XMLDocument1.DocumentElement.ChildNodes;

  

  for i := 0 to nodelist.count - 1 do

  begin

    node := nodeList[i];

    combobox1.Items.add(node.nodename);

  end;



  ShellExecute(handle, 'open','E:\ios\study\action\2012-4-1\ConfigAction\ConfigAction\Debug.win32\ConfigAction.win32.exe', '',nil, SW_SHOWNORMAL); 

end;



//将基本动作配置参数存入config.xml

procedure TForm1.Button9Click(Sender: TObject);

var

  nodelist: ixmlnodelist;

  node: ixmlnode;

begin

  node:= xmldocument1.documentelement.childnodes['move'];

  XMLDocument1.Options := [doNodeAutoIndent];  //换行

  node:= node.AddChild('item');

  node.Attributes['id']:= FormatDateTime( 'YYYYMMDDHHmmss ', Now);

  node.Attributes['beginPoint']:= edit1.Text+':'+edit2.Text;

  node.Attributes['controlPoint1']:= edit3.Text+':'+edit4.Text;

  node.Attributes['controlPoint2']:= edit5.Text+':'+edit6.Text;

  node.Attributes['endPoint']:= edit7.Text+':'+edit8.Text;

  node.Attributes['time']:= edit9.text;

  node.Attributes['png']:= edit10.text;

  XMLDocument1.Options := [doNodeAutoIndent];  //换行

  XMLDocument1.SaveToFile(ExtractFilePath(Application.Exename) + 'config\config.xml');

  FormCreate(nil); //重新载入

end;



//将复杂动作配置参数存入config.xml

procedure TForm1.Button4Click(Sender: TObject);

var

  nodelist: ixmlnodelist;

  node: ixmlnode;

  i: integer;

  typeStr:string;

begin

  if(radiobutton1.checked) then

  begin

    typeStr:= '1';

  end

  else if (radiobutton2.checked) then

  begin

    typeStr:='2';

  end

  else

    showmessage('请选择动作类型!');



  node:= xmldocument1.documentelement.childnodes['complex'];

  XMLDocument1.Options := [doNodeAutoIndent];  //换行

  node:= node.AddChild('item');

  node.Attributes['id']:= FormatDateTime( 'YYYYMMDDHHmmss ', Now);

  node.Attributes['type']:= typeStr;



  for i:=0 to listbox1.Items.Count-1 do

  begin

    node.Attributes['action' + inttostr(i+1)]:= listbox1.Items[i];

  end;



  node.Attributes['png']:= edit11.text;

  XMLDocument1.Options := [doNodeAutoIndent];  //换行

  XMLDocument1.SaveToFile(ExtractFilePath(Application.Exename) + 'config\config.xml');

end;



//选择图片(复杂动作)

procedure TForm1.Button2Click(Sender: TObject);

begin

  form1.OpenDialog1.DefaultExt:='png'; //设置缺省扩展名

  form1.OpenDialog1.Title:='请选择一个png文件';  //设置对话框标题

  form1.OpenDialog1.Filter:='Text files(*.png)|*.png'; //设置文件过滤条件

  form1.OpenDialog1.Execute;   //打开对话框

  edit11.Clear;

  edit11.text:=OpenDialog1.FileName;

end;



//选择动作类型并将其下的动作项add到combobox2下

procedure TForm1.ComboBox1Exit(Sender: TObject);

var

 nodelist: ixmlnodelist;

 node: ixmlnode;

 i,j,num: integer;

begin

  combobox2.Clear;

  nodelist:= xmldocument1.DocumentElement.ChildNodes;



  for i:=0 to nodelist.Count-1 do

  begin

    if nodelist[i].NodeName = combobox1.Text then

    break;

  end;



  if booltostr(nodelist[i].HasChildNodes)<>'0' then

  begin

    nodelist:=nodelist[i].ChildNodes;

    for j := 0 to nodelist.Count-1 do

    begin

      combobox2.Items.add(nodelist[j].Attributes['id']);

    end;

  end;

end;



//添加基本动作项到listbox1

procedure TForm1.ComboBox2Exit(Sender: TObject);

begin

listbox1.items.Add(combobox2.text);

end;



//实现listbox里的项的拖拉排序

procedure TForm1.ListBox1EndDrag(Sender, Target: TObject; X, Y: Integer); 

var

Tmp: string;

begin

Tmp:=ListBox1.Items[ListBox1.ItemIndex];

ListBox1.Items[ListBox1.ItemIndex]:=ListBox1.Items[Index];

ListBox1.Items[Index]:=Tmp;

ListBox1.OnEndDrag:=nil;

end;



//实现listbox里的项的拖拉排序

procedure TForm1.ListBox1DragOver(Sender, Source: TObject; X, Y: Integer;

  State: TDragState; var Accept: Boolean); 

begin

Index:=TListBox(Source).ItemIndex;

ListBox1.OnEndDrag:=ListBox1EndDrag;

if State<>dsDragMove then

    Accept:=false;

end;



//预览,发送数据给服务端。

procedure TForm1.Button3Click(Sender: TObject);

var

  pipehandle:hwnd;

  byteswrite:dword;

  pipenamestr, dataStr:string;



begin

  //打开exe

  ShellExecute(handle, 'open','E:\ios\study\action\2012-4-1\ConfigAction\ConfigAction\Debug.win32\ConfigAction.win32.exe', '',nil, SW_SHOWNORMAL);

  //管道名

  pipenamestr:='\\.\pipe\demo';

  //发送的数据,以','为分隔符

  dataStr:= edit1.Text+','+edit2.Text+','+edit3.Text+','+edit4.Text+','+edit5.Text+','+edit6.Text+','+edit7.Text+','+edit8.Text+','+edit9.Text+','+edit10.Text;

  //等待管道的出现

  if waitnamedpipe(pchar(pipenamestr),nmpwait_wait_forever)=false then

  begin

    showmessage(format('waitnamedpipe faile with error %d',[getlasterror()]));

    exit;

  end;



  //打开一个通信端口

  pipehandle:= createfile(pchar(pipenamestr),generic_read or generic_write,

    file_share_write,nil,open_existing,file_attribute_normal,0);

  if pipehandle=invalid_handle_value then

  begin

    showmessage(format('createfile faile with error %d',[getlasterror()]));

    exit;

  end;



  //发送数据

  if writefile(pipehandle,pchar(dataStr)^,length(dataStr),byteswrite,nil)=

    false then

  begin

    showmessage(format('writefile faile with error %d',[getlasterror()]));

    exit;

  end;

  //关闭串行口

  closehandle(pipehandle);

end;



end.

 

 

服务端主要代码:

/**************接收客户端发来的数据****************/

#include "GetParameter.h"

#include <iostream>



using namespace std;



GetParameter::GetParameter(void)

{



}



GetParameter::~GetParameter(void)

{

}



int GetParameter::commWithClient(void)

{

	//创建命名管道

	h=CreateNamedPipe(_T("\\\\.\\pipe\\demo"), PIPE_ACCESS_DUPLEX | FILE_FLAG_OVERLAPPED, 0, 1, 1024, 1024, 0, NULL);

	if(INVALID_HANDLE_VALUE==h)

	{

		//cout<<"创建命名管道失败!"<<endl;

		return 1;

	}



	if(ConnectNamedPipe(h, NULL)==NULL)

	{

		//cout<<"连接失败!"<<endl;

		return 2;

	}

	

	return 0;

}



int GetParameter::readDataFromPipe()

{

	DWORD len=0;

	if(ReadFile(h, buf, sizeof(buf), &len, NULL)==TRUE)

	{

	    //管道连接成功,读取数据

		buf[len] = '\0';

		//cout << buf<< endl;

		CloseHandle(h);

		return 0;

	}

	CloseHandle(h);

	return 1;

}



char* GetParameter::getBuf(void)

{

	return buf;

}





/******获取数据并分离处理,并使用数据进行 贝塞尔曲线 演示********/





#include "DemoLayer.h"

#include "GetParameter.h"



using namespace cocos2d;



DemoLayer::DemoLayer(void)

{

}



DemoLayer::~DemoLayer(void)

{

}



bool DemoLayer::init(void)

{

	GetParameter* k= new GetParameter();

	k->commWithClient();

	k->readDataFromPipe();



	//获取客户端发来的数据

	char* m = k->getBuf();



	//分离出各个字符串(以","为分隔符)

	char *token = NULL, *p[10];

	int i = 0;

	p[i] = strtok(m, ",");   

	while ((token = strtok(NULL, ",")) != NULL)

	{

		p[++i] = token;

	}



	//使用p[]数据。

	bool bRet = false;

	do 

	{

		CC_BREAK_IF(! CCLayer::init());



		CCSize s = CCDirector::sharedDirector()->getWinSize();

		CCMenuItemImage* quit = CCMenuItemImage::itemFromNormalImage("CloseNormal.png", "CloseSelected.png", this, menu_selector(DemoLayer::onQuit));

		CC_BREAK_IF(! quit);

		quit->setPosition(ccp(s.width-20, 20));



		CCMenu* pMenu = CCMenu::menuWithItems(quit, NULL);

		CC_BREAK_IF(! pMenu);

		pMenu->setPosition(CCPointZero);

		this->addChild(pMenu, 0, 1);



		bgSprite = CCSprite::spriteWithFile("bg.png");

		CC_BREAK_IF(! bgSprite);

		//bgSprite->setAnchorPoint(CCPointZero);

		this->addChild(bgSprite, -1, 2);



	    pSprite = CCSprite::spriteWithFile(p[9]);

		CC_BREAK_IF(! pSprite);

		pSprite->setPosition(CCPointMake(atoi(p[0]), atoi(p[1])));

		this->addChild(pSprite, 1, 3);



		//ActionBezier 测试

		ccBezierConfig bezier;

		bezier.controlPoint_1 = CCPointMake(atoi(p[2]), atoi(p[3]));

		bezier.controlPoint_2 = CCPointMake(atoi(p[4]), atoi(p[5]));

		bezier.endPosition = CCPointMake(atoi(p[6]), atoi(p[7]));



		CCActionInterval*  bezierTo = CCBezierTo::actionWithDuration(atoi(p[8]), bezier);	

		pSprite->runAction(bezierTo);



		this->setIsTouchEnabled(true);



		bRet = true;



	} while (0);



	delete k;



	return bRet;

}

/*

void DemoLayer::ccTouchesEnded(cocos2d::CCSet* pTouches, cocos2d::CCEvent* pEvent)

{

	CCTouch* touch = (CCTouch*)pTouches->anyObject();

	//获得触点坐标

	CCPoint location = touch->locationInView(touch->view());

	CCPoint convertedLocation = CCDirector::sharedDirector()->convertToGL(location);

}

*/

void DemoLayer::onQuit(CCObject* pSender)

{

	CCDirector::sharedDirector()->end();

}

 

OK,截图:

QQ截图20120520221444

你可能感兴趣的:(Delphi)