📄 uiwnd.c
字号:
/*********************************************************************/
// 文 件 名: uiWnd.cpp
// 程序说明: 窗口
// 程序设计: 张学平
// 2001.10.23 设计完成 说明文档:R004-S229-0001
// 2002.05.29 修改输入对话框,增加键盘选择参数
// 程序审查: 宋军霞
// 2002.01.28 审查完成 说明文档:R004-S229-0001
// 项目编号: R004-S229
// 版 本: V1.0
// 版 权: Reality Plus Technology (ShenZhen) Co.,Ltd.
/*********************************************************************/
#include <pr2k.h>
#include <uiWnd.h>
#include <uiTextEdit.h>
#include <uiIcon_Img.h>
#include <uiHandWrite.h>
#include <uikey_hdr.h>
extern struct thread *CurrentThread;
extern int gLanguage;
TGuiWindow *gpWindowsList=NULL; // 窗口链表,指向最后建立的窗口
TGuiWindow *gpTopWindow=NULL; // 顶层窗口
TGuiWindow *gpBackWindow=NULL; // 背景窗口,used by dialog
WORD gBackWindowStyle=0; // 背景窗口风格
/*************************************************************************/
// 建立窗口
// 参数:
// hParentWnd: 父窗口
// caption: 窗口名
// szHelp: 帮助信息字符串指针
// TMenuItemInfo:菜单信息指针
// style: 窗口风格
// 返回值:
// 成功: 窗口的handle值
// 失败: NULL
/*************************************************************************/
DLL_EXP(HNDL) guiWindow_Create(HNDL hParentWnd, const char *caption, const char *szHelp,
TMenuItemInfo *pMenuItemInfo, WORD style)
{
TGuiMessageQueue *pMessageQueue;
TGuiWindow *pParentWnd, *pWnd;
HNDL hMenu,hClose,hRet;
STATUS result;
short closeTop;
short titleHeight,closeHeight,closeWidth,menuWidth,menuLeft;
int i;
guiEnterWCS();
pParentWnd = (TGuiWindow *)hParentWnd;
if( hParentWnd )
{
if( pParentWnd->checkFlag!=GUI_WIN_CHECK_FLAG || pParentWnd->parent )
{
guiExitWCS();
return NULL; // 建立子窗口或对话框时父窗口无效或父窗口本身为一子窗口
}
}
pWnd = (TGuiWindow *)kernelMalloc( sizeof(TGuiWindow) );
if( !pWnd )
{
guiExitWCS();
return NULL; // 分配存储空间失败
}
if( style&GUIWIN_TITLE_NONE ) // 在没有标题条时也不能有关闭按钮和系统菜单
{
style|=GUIWIN_CLOSE_NONE;
style|=GUIWIN_MENU_NONE;
}
// 数据初始化
pWnd->handle = (HNDL)pWnd; // 句柄
pWnd->type = CONTROL_WINDOW; // 控件类型
pWnd->left = GUIWIN_LEFT; // 座标
pWnd->top = GUIWIN_TOP;
pWnd->right = GUIWIN_RIGHT;
pWnd->bottom = GUIWIN_BOTTOM;
pWnd->checkFlag = GUI_WIN_CHECK_FLAG; // 1112
pWnd->style = style;
pWnd->font = GUI_DEFAULT_FONT;
pWnd->status = GUIWIN_NOT_ACTIVE; // 窗口创建时为不活动状态
// by zhangxp 2003/06/11
pWnd->BackWindowStyle = 0;
pWnd->pBackWindow = NULL;
initDLinkList(&(pWnd->controlList)); // 初始化控件列表
pWnd->parent = (TGuiWindow *)hParentWnd;// 父窗口
if( !hParentWnd || style&GUIWIN_DIALOG )
{ // 主窗口、对话框:分配消息队列
pMessageQueue = guiAllocateMessageQueue();
if( !pMessageQueue )
{
kernelFree(pWnd); // 消息队列分配失败时,应释放窗口的存储空间
guiExitWCS();
return NULL;
}
pWnd->messageQueue=pMessageQueue;
}
else
{
pWnd->messageQueue = pParentWnd->messageQueue; // 子窗口:与父窗口共享消息队列
}
if(caption) // 标题
{
strncpy(pWnd->caption, caption, GUI_WIN_CAPTION_SIZE);
pWnd->caption[GUI_WIN_CAPTION_SIZE] = 0;
}
else
pWnd->caption[0] = 0;
pWnd->backColor = GUI_WHITE; // 缺省背景为白色
pWnd->screenBuffer = NULL; // 创建时不会有被保存的屏幕
if( style&GUIWIN_HELP) // 帮助信息
pWnd->tWinSysCtr.szHelp = (char *)szHelp;
else
pWnd->tWinSysCtr.szHelp = NULL;
guiPushFont(pWnd->font);
titleHeight = guiGetStringHeight() + TITLE_HEIGHT_ADD; // 计算标题条高度
// by zhangxp 2003/06/25
//menuWidth=guiGetStringWidth(caption)+guiGetStringWidth(RES_STR_MENUFLAG[gLanguage]);
guiPopFont();
closeWidth=0;
pWnd->tWinSysCtr.hClose=NULL;
if( !(style&GUIWIN_CLOSE_NONE) )
{
closeHeight=guiGetImageHeight(icon_Gui_Wnd_Close_Up); // 获取关闭按钮高度
closeWidth=guiGetImageWidth(icon_Gui_Wnd_Close_Up); // 获取关闭按钮宽度
closeTop = (titleHeight-closeHeight)>>1; // 计算关闭按钮的Y座标
hClose = guiBitmap_Create(1, closeTop, closeWidth, closeTop+closeHeight-1, icon_Gui_Wnd_Close_Up, 0);
if( !hClose ) // 创建Bitmap失败时,释放已分配的空间
{
if( !hParentWnd || (style&GUIWIN_DIALOG) )
kernelFree(pWnd->messageQueue);
kernelFree(pWnd);
guiExitWCS();
return NULL;
}
guiBitmap_SetDouble(hClose, icon_Gui_Wnd_Close_Down); // 设置笔点下时,关闭按钮的显示图形
guiControl_SetStyle(hClose, BMP_WINCLOSE|BMP_DIMAGE); // 设置Bitmap风格
result = guiControl_Add((HNDL)pWnd, hClose);
if(result != STATUS_OK) // 将Bitmap加入窗口失败时,删除bitmap并释放已分配的空间
{
guiControl_Delete(hClose);
if( !hParentWnd || (style&GUIWIN_DIALOG) )
kernelFree(pWnd->messageQueue);
kernelFree(pWnd);
guiExitWCS();
return NULL;
}
pWnd->tWinSysCtr.hClose = hClose;
}
pWnd->tWinSysCtr.hMenu = NULL;
if( style&GUIWIN_MENU ) // 有菜单
{
// by zhangxp 2003/06/25
menuWidth=guiGetStringWidth(caption)+guiGetStringWidth(RES_STR_MENUFLAG[gLanguage]);
menuLeft=closeWidth+2;
if( style&GUIWIN_CAPTION_CENTER )
menuLeft=(GUI_SCREEN_WIDTH-menuWidth)>>1;
if(menuLeft<closeWidth+2)
menuLeft=closeWidth+2;
hMenu=guiMenu_Create(menuLeft,0,menuLeft+menuWidth-1,titleHeight-1,caption,MENU_SYSTEM);
if( !hMenu ) // 创建菜单失败时,释放空间
{
if( !(style&GUIWIN_CLOSE_NONE) )
guiControl_Delete(hClose);
if( !hParentWnd || (style&GUIWIN_DIALOG) )
kernelFree(pWnd->messageQueue);
kernelFree(pWnd);
guiExitWCS();
return NULL;
}
result=guiControl_Add((HNDL)pWnd, hMenu);
if(result != STATUS_OK) // 将Menu加入窗口失败时,删除Menu并释放已分配的空间
{
guiControl_Delete(hMenu);
if( !(style&GUIWIN_CLOSE_NONE) )
guiControl_Delete(hClose);
if( (hParentWnd==NULL) || (style&GUIWIN_DIALOG) )
kernelFree(pWnd->messageQueue);
kernelFree(pWnd);
guiExitWCS();
return NULL;
}
pWnd->tWinSysCtr.hMenu = hMenu;
i=0;
while(pMenuItemInfo[i].command) // 加入菜单项
{
guiMenu_AppendItem(hMenu, (char *)pMenuItemInfo[i].caption, pMenuItemInfo[i].command);
i++;
}
}
pWnd->ownerThreadID = CurrentThread->tid;
if( gpWindowsList!=NULL ) // 将所有窗口链接起来
gpWindowsList->prev = pWnd;
pWnd->back = gpWindowsList;
gpWindowsList = pWnd;
pWnd->prev = NULL;
guiExitWCS();
return (HNDL)pWnd;
}
/*************************************************************************/
// 绘出窗口框架(包括清除窗口显示区域、画出边框、标题条、关闭按钮、标题)
// 参数:
// hWnd: 窗口句柄
// 返回值: 无
/*************************************************************************/
void _guiWindow_PaintFrame(HNDL hWnd)
{
short left, top, right, bottom;
TGuiWindow *pWnd;
short titleHeight;
WORD style;
pWnd = (TGuiWindow *)hWnd;
style = pWnd->style;
left = pWnd->left;
top = pWnd->top;
right = pWnd->right;
bottom = pWnd->bottom;
guiClearBlock(0,left, top, right, bottom, pWnd->backColor, 0); // 用背景色清除窗口
if( pWnd->style&GUIWIN_BORDER )
guiDrawRect(0,left,top,right,bottom,GUI_BLACK,0); // 画边框
if( pWnd->style&GUIWIN_TITLE_NONE )
return; // 没有标题条
// 有标题条时,才可能具有关闭按钮和标题
guiPushFont(pWnd->font);
titleHeight = guiGetStringHeight() + TITLE_HEIGHT_ADD;
guiPopFont();
guiClearBlock(0,left, top, right, top+titleHeight-1, GUI_BLACK, 0); // 画标题条
if( pWnd->tWinSysCtr.hClose )
guiControl_Show(pWnd->tWinSysCtr.hClose); // 显示关闭按钮
_guiWindow_PaintCaption(hWnd); // 显示标题
}
/*************************************************************************/
// 绘出窗口标题
// 参数:
// hWnd 窗口句柄
// 返回值: 无
/*************************************************************************/
void _guiWindow_PaintCaption(HNDL hWnd)
{
TGuiWindow *pWnd;
short captionWidth,captionLeft,left,titleHeight;
char caption[GUI_WIN_CAPTION_SIZE+3];
WORD style;
pWnd=(TGuiWindow *)hWnd;
style=pWnd->style;
if( style&GUIWIN_TITLE_NONE )
return; // 没有标题条
strcpy(caption,pWnd->caption);
if( style&GUIWIN_MENU )
strcat(caption,RES_STR_MENUFLAG[gLanguage]);
guiPushFont(pWnd->font);
captionWidth=guiGetStringWidth(caption); // 显示宽度
guiPopFont();
if(!captionWidth) // 没有caption时,返回
return;
if( style&GUIWIN_CLOSE_NONE ) // 没有close button
left=2;
else // 有close button
left=guiGetImageWidth(icon_Gui_Wnd_Close_Up)+2;
if( style&GUIWIN_CAPTION_CENTER )
{
captionLeft= (pWnd->right-pWnd->left+1-captionWidth)>>1;
if(captionLeft<left)
captionLeft=left;
}
else
captionLeft= left;
guiPushFont(pWnd->font);
guiShowString(hWnd,caption,captionLeft,TITLE_HEIGHT_ADD>>1,GUI_WHITE,0);
guiPopFont;
}
/*************************************************************************/
// 获取顶层窗口句柄
// 参数: 无
// 返回值: 顶层窗口句柄
/*************************************************************************/
DLL_EXP(HNDL) guiWindow_QueryTop(void)
{
return (HNDL)gpTopWindow;
}
/*************************************************************************/
// 重画窗口及其中的所有控件
// 参数: hWnd 窗口句柄
// 返回值:
// STATUS_OK: 成功
// STATUS_ERR: 失败
/*************************************************************************/
DLL_EXP(STATUS) guiWindow_Repaint(HNDL hWnd)
{
struct dLinkList *pControlList;
TGuiWindow *pWnd;
guiEnterWCS();
if( hWnd!=(HNDL)gpTopWindow ) // 所指窗口不是顶层窗口时,不进行重绘
{
guiExitWCS();
return STATUS_ERR;
}
pWnd = (TGuiWindow *)hWnd;
if( pWnd->checkFlag!=GUI_WIN_CHECK_FLAG ) // 窗口无效时,不进行重绘
{
guiExitWCS();
return STATUS_ERR;
}
if( pWnd->status==GUIWIN_NOT_ACTIVE ) // 窗口不活动时,不进行重绘
{
guiExitWCS();
return STATUS_ERR;
}
_guiWindow_PaintFrame(hWnd); // 画窗口框架
pControlList = &(pWnd->controlList); // 窗口中的控件链表
while(1) // 重画控件
{
pControlList = pControlList->back;
if( !pControlList )
break; // 已到链表尾
guiControl_Show( (HNDL)pControlList->elementPointer );
}
if( pWnd->screenBuffer )
kernelFree( pWnd->screenBuffer );
guiExitWCS();
return STATUS_OK;
}
/*************************************************************************/
// 显示窗口及其中的所有控件
// 参数:
// hWnd 窗口句柄
// 返回值:
// STATUS_OK: 成功
// STATUS_ERR: 失败
/*************************************************************************/
DLL_EXP(STATUS) guiWindow_Show(HNDL hWnd )
{
TGuiWindow *pWnd;
TGuiMessage message;
WORD style;
BYTE *backBitmap;
short left,top,right,bottom;
guiEnterWCS();
pWnd = (TGuiWindow *)hWnd;
if(pWnd->checkFlag!=GUI_WIN_CHECK_FLAG) // 1112
{
guiExitWCS();
return STATUS_ERR; // 窗口无效
}
if(gpTopWindow) // 处理前一个顶层窗口
{
style=gpTopWindow->style;
// by zhangxp 2003/06/11
/*
if(style & GUIWIN_DIALOG)
{
guiExitWCS();
return STATUS_ERR; // 顶层窗口为对话框时,不能再显示窗口
}
*/
guiCaret_Disable(); // 禁止光标
guiMenu_Shrink(); // 收回已展开的菜单
guiListbox_Shrink(); // 收回已展开的PopList
guiHWR_End(); // 停止手写识别线程
if( style&GUIWIN_IMAGE_SAVE ) // 保存窗口背景
{
left=gpTopWindow->left;
top=gpTopWindow->top;
right=gpTopWindow->right;
bottom=gpTopWindow->bottom;
backBitmap = (BYTE *)kernelMalloc(guiGetImageSize(left,top,right,bottom));// 分配背景存储空间
if( !backBitmap )
{
guiExitWCS();
return STATUS_ERR;
}
if( gpTopWindow->screenBuffer )
kernelFree(gpTopWindow->screenBuffer); // 释放前一次所分配的背景存储空间
guiGetImage(0,left,top,right,bottom,backBitmap); // 保存背景
gpTopWindow->screenBuffer=backBitmap;
}
gpTopWindow->status = GUIWIN_NOT_ACTIVE; // 将窗口设置为不活动
}
style = pWnd->style;
pWnd->status = GUIWIN_ACTIVE; // 激活新窗口
gpTopWindow = pWnd; // 新窗口为顶层窗口
if( (style&GUIWIN_IMAGE_SAVE) && (pWnd->screenBuffer) )
{
guiPutImage(0, pWnd->left, pWnd->top, pWnd->right, pWnd->bottom, pWnd->screenBuffer); // 恢复被保存的屏幕
kernelFree(pWnd->screenBuffer);
pWnd->screenBuffer=NULL;
guiSwKbd_Reset(hWnd);
guiCaret_Enable();
}
else
guiWindow_Repaint(hWnd); // 重绘窗口
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -