TeamTalk初学笔记4---关于win-client【第二篇:入口文件teamtalk.cpp】

#include "stdafx.h"

#include "teamtalk.h"

#include "UI/MainDialog.h"

#include "GlobalConfig.h"

#include "versioninfo.h"

#include "google/protobuf/stubs/common.h"

#include "utility/utilCommonAPI.h"

#include "utility/Multilingual.h"

#include "utility/utilStrCodingAPI.h"

#include "Modules/IHttpPoolModule.h"

#include "Modules/ILoginModule.h"

#include "Modules/IMiscModule.h"        //一些比较杂的公用的接口函数

#include "Modules/ISysConfigModule.h"

#include "Modules/ITcpClientModule.h"

#include "Modules/UIEventManager.h"

#include "network/OperationManager.h"

#include "network/ImCore.h"             //IM核心类:线程、TcpSockets的操作之类的

/*

*  指定重启管理器的风格

*  重启管理器可以支持多种风格,例如,有的风格(AFX_RESTART_MANAGER_SUPPORT_RESTART)只是将崩溃的应用程序重新启动,

*  而有的风格(AFX_RESTART_MANAGER_SUPPORT_ALL_ASPECTS)不仅将应用程序重新启动,还可以打开原来自动保存的文档,恢复应用程序到崩溃前的状态。

*  我们可以在应用程序类的构造函数中,通过指定CWinAppEx的dwRestartManagerSupportFlags成员变量来指定重启管理器的风格。

*/

CteamtalkApp::CteamtalkApp()

:m_pMainDialog(0)

{

m_dwRestartManagerSupportFlags = AFX_RESTART_MANAGER_SUPPORT_RESTART;

}

CteamtalkApp theApp;    //MFC类实例

/*

*  应用程序入口

*/

BOOL CteamtalkApp::InitInstance()

{

INITCOMMONCONTROLSEX InitCtrls;

InitCtrls.dwSize = sizeof(InitCtrls);

InitCtrls.dwICC = ICC_WIN95_CLASSES;  //用来注册InitCommonControls函数所注册的所有类。

InitCommonControlsEx(&InitCtrls);

//如果一个运行在 Windows XP 上的应用程序清单指定要使用 ComCtl32.dll 版本 6 或更高版本来启用可视化方式,则需要 InitCommonControlsEx();否则,将无法创建窗口。

//YAOLOG 初始化

_InitLog();

//验证GOOGLE_PROTOBUF版本兼容性

// Verify that the version of the library that we linked against is

// compatible with the version of the headers we compiled against.

GOOGLE_PROTOBUF_VERIFY_VERSION;

//输出一行日志

LOG__(APP, _T("===================VersionNO:%d======BulidTime:%s--%s==========================")

, TEAMTALK_VERSION, util::utf8ToCString(__DATE__), util::utf8ToCString(__TIME__));

if (!__super::InitInstance())  //__super关键字:本类的基类CWinApp

{

LOG__(ERR, _T("__super::InitInstance failed."));

return FALSE;

}

//调用在应用程序对象的 InitInstance 函数中对此函数启用 OLE 控件包容的支持。

AfxEnableControlContainer();

//应用程序是否已经启动

if (_IsHaveInstance())

{

LOG__(ERR, _T("Had one instance,this will exit"));

HWND hwndMain = FindWindow(_T("TeamTalkMainDialog"), NULL); //寻找标题为TeamTalkMainDialog的进程

if (hwndMain)

{

::SendMessage(hwndMain, WM_START_MOGUTALKINSTANCE, NULL, NULL);

//该函数将指定的消息发送到一个或多个窗口。此函数为指定的窗口调用窗口程序,直到窗口程序处理完消息再返回。

//而和函数PostMessage不同,PostMessage是将一个消息寄送到一个线程的消息队列后就立即返回。

}

return FALSE;

}

//启动蓝狐大神写的IM核心类(线程启动,互斥锁。。。有兴趣可以深入去了解ImCore)

//start imcore lib

if (!imcore::IMLibCoreRunEvent())

{

LOG__(ERR, _T("start imcore lib failed!"));

}

LOG__(APP, _T("start imcore lib done"));

//start ui event

if (module::getEventManager()->startup() != imcore::IMCORE_OK)

{

LOG__(ERR, _T("start ui event failed"));

}

LOG__(APP, _T("start ui event done"));

//create user folders

_CreateUsersFolder();

//duilib初始化

CPaintManagerUI::SetInstance(AfxGetInstanceHandle()); //将程序实例与皮肤绘制管理器挂钩

//获取可执行程序的所在路径,指的是.exe文件路径

CPaintManagerUI::SetResourcePath(CPaintManagerUI::GetInstancePath() + _T("..\\gui\\"));//track这个设置了路径,会导致base里设置的无效。

//COM在OLE32.DLL和 OLE32.LIB定义了一些常用的函数。在使用这些函数前要先调用CoInitialize来初始化COM库

::CoInitialize(NULL);

//OleInitialize是初始化Ole的运行环境,Ole是在Com的基础上作的扩展,是ActiveX运行的基础,OleInitialize肯定会调用CoInitialize。

::OleInitialize(NULL);

//无需配置server(这里是初始化)

module::TTConfig* pCfg = module::getSysConfigModule()->getSystemConfig();

if (pCfg && pCfg->loginServIP.IsEmpty())

{

if (!module::getSysConfigModule()->showServerConfigDialog(NULL))

{

LOG__(APP, _T("server config canceled"));

return FALSE;

}

}

//创建登陆窗口,并启动它

if (!module::getLoginModule()->showLoginDialog())

{

LOG__(ERR, _T("login canceled"));

return FALSE;

}

LOG__(APP,_T("login success"));

//创建主窗口,只是初始化,这里不会ShowModal显示处理

if (!_CreateMainDialog())

{

LOG__(ERR, _T("Create MianDialog failed"));

return FALSE;

}

LOG__(APP, _T("Create MianDialog done"));

CPaintManagerUI::MessageLoop(); //DuiLib之消息循环。

CPaintManagerUI::Term();        //关闭压缩包

return TRUE;

}

//销毁主窗口

BOOL CteamtalkApp::_DestroyMainDialog()

{

delete m_pMainDialog;

m_pMainDialog = 0;

return TRUE;

}

//创建主窗口

BOOL CteamtalkApp::_CreateMainDialog()

{

m_pMainDialog = new MainDialog();   //新建主窗体类对象

PTR_FALSE(m_pMainDialog);           //assert 该值为FALSE时中断当前操作

CString csTitle = util::getMultilingual()->getStringById(_T("STRID_GLOBAL_CAPTION_NAME"));  //从bin\teamtalk\chinese.ini 配置文件中获取窗体标题

//创建主窗口(600宽,800高)

if (!m_pMainDialog->Create(NULL, csTitle

, UI_CLASSSTYLE_DIALOG, WS_EX_STATICEDGE /*| WS_EX_APPWINDOW*/ | WS_EX_TOOLWINDOW, 0, 0, 600, 800))

return FALSE;

m_pMainDialog->BringToTop(); //主窗体置于所有窗体上面

return TRUE;

}

//退出应用程序

BOOL CteamtalkApp::ExitInstance()

{

LOG__(APP, _T("Exit Instance"));

//close httppool

module::getHttpPoolModule()->shutdown();

LOG__(APP, _T("close http pool done"));

//close network socket io

module::getTcpClientModule()->shutdown();

LOG__(APP, _T("close tcpclient socket done"));

//stop imcore lib

imcore::IMLibCoreStopEvent();

LOG__(APP, _T("stop imcore lib done"));

//stop ui event

module::getEventManager()->shutdown();

LOG__(APP, _T("stop ui event done"));

//销毁主窗口

_DestroyMainDialog();

LOG__(APP,_T("MainDialog Destory done"));

//终止Winsock 2 DLL (Ws2_32.dll) 的使用.

WSACleanup();

// Optional:  Delete all global objects allocated by libprotobuf.

google::protobuf::ShutdownProtobufLibrary();

LOG__(APP, _T("Exit OK"));

YAOLOG_EXIT;

return __super::ExitInstance();  ///__super关键字:本类的基类CWinApp

}

//创建用户目录

BOOL CteamtalkApp::_CreateUsersFolder()

{

module::IMiscModule* pModule = module::getMiscModule(); //定义一些比较杂的公用的接口函数的类实例

//users目录

if (!util::createAllDirectories(pModule->getUsersDir()))

{

LOG__(ERR, _T("_CreateUsersFolder users direcotry failed!"));

return FALSE;

}

//下载目录

if (!util::createAllDirectories(pModule->getDownloadDir()))

{

LOG__(ERR, _T("_CreateUsersFolder download direcotry failed!"));

return FALSE;

}

return TRUE;

}

//应用程序的HANDLE标识号

#ifdef _DEBUG

#define  AppSingletonMutex _T("{7A666640-EDB3-44CC-954B-0C43F35A2E17}")

#else

#define  AppSingletonMutex _T("{5676532A-6F70-460D-A1F0-81D6E68F046A}")

#endif

BOOL CteamtalkApp::_IsHaveInstance()

{

// 单实例运行

HANDLE hMutex = ::CreateMutex(NULL, TRUE, AppSingletonMutex);

if (hMutex != NULL && GetLastError() == ERROR_ALREADY_EXISTS)

{

MessageBox(0, _T("上次程序运行还没完全退出,请稍后再启动!"), _T("TeamTalk"), MB_OK);

return TRUE;

}

return FALSE;

}

//初始化YAOLOG日志

void CteamtalkApp::_InitLog()

{

std::string logConfig = util::cStringToString(util::getAppPath()) + "\\ttlogconfig.ini";

YAOLOG_INIT;

YAOLOG_CREATE(APP, true, YaoUtil::LOG_TYPE_TEXT);

YAOLOG_CREATE(NET, true, YaoUtil::LOG_TYPE_TEXT);

YAOLOG_CREATE(DEBG, true, YaoUtil::LOG_TYPE_TEXT);

YAOLOG_CREATE(ERR, true, YaoUtil::LOG_TYPE_TEXT);

YAOLOG_CREATE(SOCK, true, YaoUtil::LOG_TYPE_FORMATTED_BIN);

YAOLOG_SET_ATTR_FROM_CONFIG_FILE(APP, logConfig.c_str());

YAOLOG_SET_ATTR_FROM_CONFIG_FILE(NET, logConfig.c_str());

YAOLOG_SET_ATTR_FROM_CONFIG_FILE(DEBG, logConfig.c_str());

YAOLOG_SET_ATTR_FROM_CONFIG_FILE(ERR, logConfig.c_str());

YAOLOG_SET_ATTR_FROM_CONFIG_FILE(SOCK, logConfig.c_str());

}

时间: 2024-10-25 08:23:02

TeamTalk初学笔记4---关于win-client【第二篇:入口文件teamtalk.cpp】的相关文章

TeamTalk初学笔记3---关于win-client【第二篇:入口文件_头文件】

研究一个应用程序的源码,我们常常会从它的第一个窗口:登陆界面开始研究.至少我个人就比较喜欢从程序启动的瞬间,第一时间执行的那个函数开始着手. 选中解决方案,右键->属性->启动项目,可以看到当前选中的是单启动项目:teamtalk.C++的英文名字就是cplusplus,简写:cpp.这下可以知道入口文件必然是同名文件:teamtalk.cpp了,寻找一番,就可以找到,如下图位置: 文件的物理路径:\win-client\src\teamtalk\文件夹下面. 既然入口已经找到,接下来这篇博客

TeamTalk初学笔记2---关于win-client【第一篇】

        为了直观的修改TT客户端页面,我花了很多时间在网上寻找UIDesigner设计工具.最后实在是找不到了,就找了同事帮忙,他climb over the wall(这个词都成敏感词汇了?博客里居然不准用)之后终于帮我下载到了. 以下是Duilib的一些网址,很多都需要climb over the wall后才能访问. 官网: www.duilib.com 论坛: bbs.duilib.com qq群: 153787916(1群),79145400(2群),1507570(3群) g

TeamTalk初学笔记

1.图像处理:采用CxImage图像操作类库,它可以快捷地存取.显示.转换各种图像:(暂时没找到在哪使用了) 一.win-client: 1.解析参数:采用jsoncpp: 示例:登陆msg_server服务时候从config.dat中取配置信息; 2.界面:从XML中获取控件等UI界面是用的Duilib界面库画出来的: 示例:登陆界面的tipText框,提示内容取自:chinese.ini 3.日志:yaolog记录日志:格式:LOG__(szLogID, szFormat, ...); 示例

建立apk定时自动打包系统第二篇——自动上传文件

在<建立apk定时自动打包系统第一篇——Ant多渠道打包并指定打包目录和打包日期>这篇文章中介绍多渠道打包的流程.很多时候我们需要将打包好的apk上传到ftp中,这时候我可以修改custom_rules.xml这个文件就可以实现这个需求了. 1.下载 common-net-3.3.jar 并将其放在ant安装目录下的lib文件夹中. 2.修改ant.properties文件 key.store=./test.keystore key.alias=test.keystore key.store.

dsp6657的helloworld例程测试-第二篇-CFG文件

1. 上一篇疑问,int StackTest()这个函数是怎么运行的,后来在.cfg文件找到了答案,.cfg包含丰富的信息,对于用惯C语言的,确实不太习惯 1 var Memory = xdc.useModule('xdc.runtime.Memory'); 2 //使用的模块,XDCTools配置工具, 3 var BIOS = xdc.useModule('ti.sysbios.BIOS'); 4 5 var Task = xdc.useModule('ti.sysbios.knl.Task

TensorFlow官方文档MNIST初学笔记[二]

TensorFlow官方文档MNIST初学笔记[二] MNIST是一个简单的计算机视觉数据集, 它还包括每个图像的标签, 每个图像是28像素乘以28像素, 我们可以把这个数组变成一个28×28 = 784个数字的向量.MNIST只是一个784维向量空间中的一个点.mnist.train.images具有形状的张量(n维阵列)[55000, 784] 第一维度是图像列表中的索引,第二维度是每个图像中每个像素的索引.对于特定图像中的特定像素,张量中的每个条目是0和1之间的像素强度. MNIST中的每

Lua初学笔记

Lua初学笔记 lua动态类型语言,支持过程式编程.面向对象编程.函数式编程与数据驱动编程. lua -la -lb:命令首先在一个Chunk内先运行脚本文件a,然后运行脚本文件b.(-l参数会调用require,将会在指定的目录下搜索文件). lua -i -la -lb:参数-i要求lua运行指定Chunk后进入交互模式. 运行Chunk的另外一个方式是在交互模式下使用dofile 全局变量:全局变量不需要声明,给一个变量赋值后即创建了这个全局变量,访问一个没有初始化的全局变量也不会出错,只

《javascript权威指南》读书笔记——第二篇

<javascript权威指南>读书笔记--第二篇 金刚 javascript js javascript权威指南 今天是今年的196天,分享今天的读书笔记. 第2章 词法结构 2.1 字符集 JavaScript程序是用Unicode字符集编写. Unicode是ASCII和Latin-1的超集,支持几乎所有语言. ES3 要求支持Unicode 2.1及后续版本 ES5 要求支持Unicode 3及后续版本 2.1.1 区分大小写 JavaScript是区分大小写的. HTML 并不区分大

初学笔记(C#事件)

1.声明事件      EventHandler是一个预定义的委托,它定义了一个无返回值的方法.在 .Net Fromwork中,他的格式: public  delegate  void EventHandler (Object  sender, EvenArgs  e) 其中sender的类型为Object,表示时间发布者本身,e用来传递事件的相关信息,数据类型为EvenArgs及其派生类. 标准的EvenArgs并不包含任何事件数据, 因此EventHandler专用于表示不生成数据的事件的