(C#)SKYPE API项目总结(一)讲了如何使用微软在线翻译服务和skype.dll中的一些常用属性和方法,接下来我们将以下各种功能的具体实现,使用的方法请参考项目总结一。
一、语言栏的绑定:
语言栏的绑定用skype工具类的 public DataTable GetToLanguage(string code) 方法,DataTable的两个列的值都是通过Web Service实现在线翻译,可能因为网速和其他原因导致这个函数运行会导致延迟,影响整个form的加载,所以语言栏的绑定用到了异步方法,代码如下。
public delegate DataTable ComboBoxGetLanguages(string code); //用于执行绑定下拉菜单函数的委托
/// <summary>
/// 构建语言列表
/// </summary>
private void BindComboBox()
{
MyCode = ConstStrings.DEFAULT_LANGUAGE_CODE; //默认的语言,设置为"zh-CHS"
this.cbLanguage.DataSource = null;
ComboBoxGetLanguages comboxGetLanguages = new ComboBoxGetLanguages(this.Skype.GetToLanguage);//异步线程委托
comboxGetLanguages.BeginInvoke(MyCode, new AsyncCallback(result =>
{
if (result.IsCompleted)
{
var dataTable = comboxGetLanguages.EndInvoke(result);
list = dataTable.Copy ();
DataTable FromdataTable = dataTable.Copy();
DelegateTool.BindDataToComboBox(cbLanguage, list, Display", Value);
DelegateTool.SetControlSelectedValue(cbLanguage,MyCode );
cbLanguage.SelectionChangeCommitted += new EventHandler((sender, e) =>
{
this.MyCode = cbLanguage.SelectedValue.ToString();
});
}
}), null);
}
在异步线程中,不能对控件进行操作,必须通过Invoke()函数代理来操作,上述BindDataToCombox()和SetControlSelectValue()的代码如下:
// 向ComboBox绑定数据的委托
public delegate void BindDataToComboBoxDelegate(ComboBox cbb, object data, string displayMember, string valueMember);
public static void BindDataToComboBox(ComboBox cbb, object data, string displayMember, string valueMember)
{
if (cbb.InvokeRequired)
{
cbb.Invoke(new BindDataToComboBoxDelegate((c, d, i, v) =>
{
c.DataSource = d;
c.DisplayMember = i;
c.ValueMember = v;
}), new object[] { cbb, data, displayMember, valueMember });
}
else
{
cbb.DataSource = data;
cbb.DisplayMember = displayMember;
cbb.ValueMember = valueMember;
}
}
// 设置某个ComboBox控件的选中项
public delegate void SetControlSelectedValueDelegate(ComboBox control, string value);
public static void SetControlSelectedValue(ComboBox control, string value)
{
if (control.InvokeRequired)
{
control.Invoke(new SetControlSelectedValueDelegate ((ct, v) => { ct.SelectedValue = v; }), new object[] { control, value });
}
else
{
control.SelectedValue = value;
}
}
这样语言绑定的功能就实现了
二、好友列表的绑定:
好友列表用的是ListView控件,listview控件中ListViewItem的三个属性 :Text,Tag,ImageIndex分别表示 显示的值,项的值,和图片的索引,这个ImageIndex和ImageList的值是关联的,所以列表绑定代码如下:
/// <summary>
/// 加载好友列表
/// </summary>
private void IniteFriendsList()
{
list_friends.Visible = true;
string[,] list = this.Skype.GetFriends();
for (int i = 0; i <=list.GetUpperBound(0); i++)
{
ListViewItem lt = new ListViewItem();
lt.Text = list[i, 0];
lt.Tag = list[i, 1];
lt.ImageIndex = Convert.ToInt32(list[i, 2]);
if (lt.Text!= "")
{
list_friends.Items.Add(lt);
}
}
}
接下来实现双击好友列表,弹出聊天对话框窗体,且窗体不重复,代码如下:
private void list_friends_MouseDoubleClick(object sender, MouseEventArgs e)
{
int frmFlag=0;
foreach (Form t in System.Windows.Forms.Application.OpenForms)//从所有已打开的窗体中判断
{
if (t.Tag != null)
{
if (list_friends.SelectedItems.Count != 0)//判断双击到了项而不是空白
{
if (t.Tag.ToString().Substring(0, (t.Tag.ToString().IndexOf('('))) == list_friends.SelectedItems[0].Text)
{
frmFlag++;
}
}
}
}
//如果已存在与改用户的聊天窗体则不再增加窗体
if (frmFlag == 0)
{
if (list_friends.SelectedItems.Count != 0)
{
FrmChat frmchat = new FrmChat();
frmchat.MyCode = this.MyCode;
ListViewItem item = list_friends.SelectedItems[0];
frmchat.Tag = item.Text + "(" + item.Tag.ToString() + ")";
frmchat.Show();
}
}
}
三、聊天的翻译功能:
发送消息的时候将信息翻译后再发送过去,代码如下
/// <summary>
/// 翻译对话
/// </summary>
/// <param name="pMessage">聊天内容</param>
/// <param name="Status">信息状态</param>
public void Skype_MessageStatus(ChatMessage pMessage, TChatMessageStatus Status)
{
string fullname = pMessage.Chat.FriendlyName.Substring(0, pMessage.Chat.FriendlyName.IndexOf('|')).TrimEnd();//获得对方的用户名
switch (Status)
{
case TChatMessageStatus.cmsSending:
//发送信息
if (this.Tag.ToString() == fullname + "(" + pMessage.Chat.DialogPartner + ")")
{
string PaternerLanguage=(cb_toLanguage.Text == "" ? this.Skype.GetUserLanguageCode (pMessage.Chat .DialogPartner):cb_toLanguage.SelectedValue .ToString () );
pMessage.Body = "原文为:" + pMessage.Body + "\r\n"
+ "译文为:" + this.Skype.translate.GetTranslateResult(pMessage.Body, null,PaternerLanguage) + "\r\n";
//添加到聊天列表
string message = this.Skype.CurrentUser.FullName + "(" + DateTime.Now.ToShortTimeString() + "): " + pMessage.Body + "\r\n";
this.rtb_Record.AppendText(message);
this.rtb_Record.ScrollToCaret();
}
break;
case TChatMessageStatus.cmsReceived:
//接受信息
if (this.Tag.ToString() == fullname + "(" + pMessage.Chat.DialogPartner + ")")
{
string senderMessage = fullname + "(" + DateTime.Now.ToShortTimeString() + "): 原文为:" + pMessage.Body + "\r\n"
+ "译文为:" + this.Skype.translate.GetTranslateResult(pMessage.Body, null, this.cb_fromLanguage.Text == "" ? this.MyCode : this.cb_fromLanguage.SelectedValue.ToString()) + "\r\n";
this.rtb_Record.AppendText(senderMessage);
this.rtb_Record.ScrollToCaret();
}
break;
default:
break;
}
}
这里要注意的是:
private void FrmChat_Load(object sender, EventArgs e)
{
this.Skype.MessageStatus += new _ISkypeEvents_MessageStatusEventHandler(Skype_MessageStatus);
}
注册时间后,关闭窗体时应该去除,否则调用该事件都会执行上面的方法
private void FrmChat_FormClosed(object sender, FormClosedEventArgs e)
{
//关闭窗体时,释放翻译方法
this.Skype.MessageStatus -= new _ISkypeEvents_MessageStatusEventHandler(Skype_MessageStatus);
}
这个插件用到的方法就总结这些,由于软件的skype.dll需要注册才能使用,我们新的需求就是制作一个安装部署,在安装的时候自动检测和安装.netFramWork,自动注册组件,这个放到下节。