COCOS2D是移动端开发游戏的免费引擎,功能非常强大,由于在移动端没有标题栏不存在问题,在windows下会有默认的标题栏,如果做得游戏为了在windows下也有统一的游戏风格,修改标题栏就必不可少。

1.隐藏标题栏

CCEGLView类中有一个获取窗口句柄的接口CCEGLView::sharedOpenGLView()->getgetHWnd();所以实现去掉标题栏非常简单, LONG l_WinStyle = GetWindowLong(hWnd, GWL_STYLE); SetWindowLong(hWnd, GWL_STYLE, l_WinStyle & ~WS_CAPTION);,运行游戏会发现去掉的标题区域是黑色的没有渲染,这是由于客户区大小没有改变,可以通过如下函数修改:

void HideDefaultTitle(HWND hWnd, int nWidth, int nHeight)
{
LONG l_WinStyle = GetWindowLong(hWnd, GWL_STYLE);
SetWindowLong(hWnd, GWL_STYLE, l_WinStyle & ~WS_CAPTION);
RECT  rectProgram, rectClient;
GetWindowRect(hWnd, &rectProgram);   //获得程序窗口位于屏幕坐标
GetClientRect(hWnd, &rectClient);      //获得客户区坐标
//非客户区宽,高
int nClientWidth = rectProgram.right - rectProgram.left - (rectClient.right - rectClient.left);
int nClientHeiht = rectProgram.bottom - rectProgram.top - (rectClient.bottom - rectClient.top);
nClientWidth += nWidth;
nClientHeiht += nHeight;
rectProgram.right = nClientWidth;
rectProgram.bottom = nClientHeiht;
int showToScreenx = GetSystemMetrics(SM_CXSCREEN) / 2 - nClientWidth / 2;    //居中处理
int showToScreeny = GetSystemMetrics(SM_CYSCREEN) / 2 - nClientHeiht / 2;
MoveWindow(hWnd, showToScreenx, showToScreeny, nWidth, nHeight, false);
}

有了这个函数我们就可以:

int APIENTRY _tWinMain(HINSTANCE hInstance,
                       HINSTANCE hPrevInstance,
                       LPTSTR    lpCmdLine,
                       int       nCmdShow)
{
    UNREFERENCED_PARAMETER(hPrevInstance);
    UNREFERENCED_PARAMETER(lpCmdLine);

// create the application instance
    AppDelegate app;
//getFrameSize()获得实际屏幕的大小
CCDirector *pDirector = CCDirector::sharedDirector();
CCEGLView* pEGLView = CCEGLView::sharedOpenGLView();
pEGLView->setViewName("Fishing");
pEGLView->setFrameSize(800, 600); 
#ifdef _WIN32
HideDefaultTitle(pEGLView->getHWnd(), 800, 600);
#endif
    return CCApplication::sharedApplication()->run();
};

再次运行游戏发现游戏非常完美的去掉了标题栏。

2.增加移动

windows窗体在不是最大化的情况下可以根据鼠标移动,前提是由标题栏,由于标题栏被我们干掉了,所以该功能就失效了。windows实现这些功能是通过WM_NCHITTEST,这个消息来实现的,如果想要模拟,就有必要截获windows窗口回调函数,我们查看CCEGLView类:

class CC_DLL CCEGLView : public CCEGLViewProtocol
{
public:
    CCEGLView();
    virtual ~CCEGLView();

/* override functions */
    virtual bool isOpenGLReady();
    virtual void end();
    virtual void swapBuffers();
    virtual void setFrameSize(float width, float height);
virtual void setEditorFrameSize(float width, float height,HWND hWnd); 
    virtual void setIMEKeyboardState(bool bOpen);

void setMenuResource(LPCWSTR menu);
    void setWndProc(CUSTOM_WND_PROC proc);

protected:
    virtual bool Create();
public:
    bool initGL();
    void destroyGL();

virtual LRESULT WindowProc(UINT message, WPARAM wParam, LPARAM lParam);

void setHWnd(HWND hWnd);
    // win32 platform function
    HWND getHWnd();
    virtual void resize(int width, int height);

/* 
     * Set zoom factor for frame. This method is for debugging big resolution (e.g.new ipad) app on desktop.
     */
    void setFrameZoomFactor(float fZoomFactor);
float getFrameZoomFactor();
    virtual void centerWindow();

typedef void (*LPFN_ACCELEROMETER_KEYHOOK)( UINT message,WPARAM wParam, LPARAM lParam );
    void setAccelerometerKeyHook( LPFN_ACCELEROMETER_KEYHOOK lpfnAccelerometerKeyHook );

virtual void setViewPortInPoints(float x , float y , float w , float h);
    virtual void setScissorInPoints(float x , float y , float w , float h);
    
    // static function
    /**
    @brief    get the shared main open gl window
    */
    static CCEGLView* sharedOpenGLView();

protected:
static CCEGLView* s_pEglView;
    bool m_bCaptured;
    HWND m_hWnd;
    HDC  m_hDC;
    HGLRC m_hRC;
    LPFN_ACCELEROMETER_KEYHOOK m_lpfnAccelerometerKeyHook;
    bool m_bSupportTouch;

LPCWSTR m_menu;
    CUSTOM_WND_PROC m_wndproc;

float m_fFrameZoomFactor;
};

NS_CC_END

#endif    // end of __CC_EGLVIEW_WIN32_H__

里面有2个接口:   void setWndProc(CUSTOM_WND_PROC proc); , virtual LRESULT WindowProc(UINT message, WPARAM wParam, LPARAM lParam);

这个就是回调函数,说明有2种实现方式,第一种继承一个CCEGLView 类,在内部重载virtual LRESULT WindowProc(UINT message, WPARAM wParam, LPARAM lParam);

第二种:直接使用  void setWndProc(CUSTOM_WND_PROC proc); 来设置一个新的回调函数。

下面使用第二种方法来实现:

LRESULT winProc(UINT message, WPARAM wParam, LPARAM lParam, BOOL* pProcessed)
{
const int captionHeight = 10;
const int frameWidth = 10;
static POINTS cursor;
switch (message)
{
case WM_NCHITTEST:
{
RECT  rectClient;
GetClientRect(CCEGLView::sharedOpenGLView()->getHWnd(), &rectClient);      //获得客户区坐标
int w = rectClient.right - rectClient.left;
int h = rectClient.bottom - rectClient.top;
POINT point;
GetCursorPos(&point);
ScreenToClient(CCEGLView::sharedOpenGLView()->getHWnd(), &point);
rectClient = { frameWidth, captionHeight, w - frameWidth - frameWidth, h - captionHeight - frameWidth };
RECT rectTopLeft = { 0, 0, frameWidth, captionHeight };
RECT rectTop = { frameWidth, 0, w - frameWidth, captionHeight };
RECT rectTopRight = { w - frameWidth, 0, w, captionHeight };
RECT rectLeft = { 0, captionHeight, frameWidth, h - captionHeight - frameWidth };
RECT rectRight = { w - frameWidth, captionHeight, w, h - captionHeight - frameWidth };
RECT rectBottm = { frameWidth, h - frameWidth, w - frameWidth, h };
RECT rectBottmLeft = { 0, h - frameWidth, frameWidth, h};
RECT rectBottmRight = { w - frameWidth, h - frameWidth, w, h };

if (PtInRect(&rectClient, point))
{
OutputDebugString(L"CLicent\n");
return HTCLIENT;
}
else if (PtInRect(&rectTopLeft, point))
{
OutputDebugString(L"TopLeft\n");
return HTTOPLEFT;
}
else if (PtInRect(&rectTop, point))
{
OutputDebugString(L"Caption\n");
return HTCAPTION;
}
else if (PtInRect(&rectTopRight, point))
{
OutputDebugString(L"TopRight\n");
return HTTOPRIGHT;
}
else if (PtInRect(&rectLeft, point))
{
OutputDebugString(L"Left\n");
return HTLEFT;
}
else if (PtInRect(&rectRight, point))
{
OutputDebugString(L"Right\n");
return HTRIGHT;
}
else if (PtInRect(&rectBottm, point))
{
OutputDebugString(L"Bottom\n");
return HTBOTTOM;
}
else if (PtInRect(&rectBottmLeft, point))
{
OutputDebugString(L"BottomLeft\n");
return HTBOTTOMLEFT;
}
else if (PtInRect(&rectBottmRight, point))
{
OutputDebugString(L"BottomRight\n");
return  HTBOTTOMRIGHT;
}
}
break;
case WM_LBUTTONDOWN:   
{
OutputDebugString(L"WM_LBUTTONDOWN\n");
cursor = MAKEPOINTS(lParam);
}
break;
case WM_LBUTTONUP:
{
OutputDebugString(L"WM_LBUTTONUP\n");
POINTS pts = MAKEPOINTS(lParam);
int xDaly = pts.x - cursor.x;
int yDaly = pts.y - cursor.y;
RECT  rectClient;
GetWindowRect(CCEGLView::sharedOpenGLView()->getHWnd(), &rectClient);      //获得客户区坐标
int w = rectClient.right - rectClient.left;
int h = rectClient.bottom - rectClient.top;
MoveWindow(CCEGLView::sharedOpenGLView()->getHWnd(), rectClient.left + xDaly, rectClient.top + yDaly, w, h, true);
}
break;
default:
break;
}
return DefWindowProc(CCEGLView::sharedOpenGLView()->getHWnd(), message, wParam, lParam);
}

回调函数写好了,然后我们设置回调:

#ifdef _WIN32
HideDefaultTitle(pEGLView->getHWnd(), 800, 600);
pEGLView->setWndProc(winProc);
#endif

运行程序,已经能移动了。

cocos2D-x在windows下实现隐藏默认标题栏,并实现拖动相关推荐

  1. python 隐藏进程_python在windows下创建隐藏窗口子进程的方法

    python在windows下创建隐藏窗口子进程的方法 发布于 2015-11-08 20:56:53 | 213 次阅读 | 评论: 0 | 来源: 网友投递 Python编程语言Python 是一 ...

  2. Windows下 更改 pip默认缓存目录

    windows下,pip的默认缓存目录为:"C:\Users{username}\AppData\Local\pip\cache" 可以使用以下命令修改缓存目录 pip confi ...

  3. Windows下创建隐藏账户、影子账户

    方法一: 用户名后面加$符号 net user test$ password /add net localgroup administrators test$ /add 此时使用命令net user ...

  4. Windows下修改jupyter默认工作路径教程

    按照网上流传的三种修改方式一步一步做下来,都没有成功.反复试验了几次终于成功了.后来推测大概是安装过程和系统环境不同导致的. 我的环境: 我用的系统是 Win 10,Anaconda 是从官网直接下载 ...

  5. git安装,windows下git bash默认目录更改

    最早Git是在Linux上开发的,很长一段时间内,Git也只能在Linux和Unix系统上跑.不过,慢慢地有人把它移植到了Windows上.现在,Git可以在Linux.Unix.Mac和Window ...

  6. windows下快速 切换默认python系统

    1 空白处 右键-->属性 2 高级系统设置 3 点击环境变量 4 编辑path变量,把你想要使用的python版本的目录添加到环境变量path里面即可, 需要注意的是,新加的路径需要放到原先p ...

  7. Windows下修改Oracle默认的端口

    一.找到安装目录下 product\11.2.0\dbhome_1\NETWORK\ADMIN 下面的  listener.ora & tnsnames.ora 两个文件,记得先备份 二.修改 ...

  8. Windows下使用gvim格式化xml文件

    1. 下载xmllint.exe http://code.google.com/p/xmllint/downloads/list 下载后,将xmllint.exe配置到PATH中. 2. 配置_vim ...

  9. php 设置window计划任务,windows下设置计划任务自动执行PHP脚本

    背景: 环境部署在linux下或者windows中,可以使用windows的自动任务设置自动执行脚本执行一些日常运维任务 图形界面设置相对比较简单 准备工作: wamp(集成的PHP执行环境) 已经写 ...

最新文章

  1. git--分支管理:创建、合并、冲突解决
  2. Angr 初体验之探索口令
  3. Hadoop实战项目之网站数据点击流分析(转载分析)
  4. Java程序员情人节_盘点程序员情人节的表白,前端程序员最浪漫,后端不服来战...
  5. java 中 集合类相关问题
  6. cloudera-scm-agent 已死,但 pid 文件存在
  7. MATLAB 图像处理 简单人脸检测(详细,你上你也行)
  8. 公司计算机程序员英语怎么说,程序员英语怎么说
  9. 计算机系统机构中的八个伟大思想
  10. Windows 10 未安装任何音频输出设备 解决方案
  11. google翻译出错什么原因?翻译英文页面时中文闪了下就显示“翻译出错请重试”
  12. Microsoft SQL Server笔记整理
  13. CPU-Z查看内存条信息
  14. 年薪120W的架构师简历你见过吗?java程序员该如何达到?
  15. setex php,python redis setex可以设value为list或者其他数据结构吗?
  16. 每日新闻简报 每天三分钟,知晓天下事 一句话新闻早餐
  17. STM32学习之SPI协议(读写FLASH)
  18. 2021年中式烹调师(中级)及中式烹调师(中级)模拟试题
  19. 两成开发者月薪超1.7万,算法工程师最紧缺
  20. 分布式系统常见问题总结

热门文章

  1. round number
  2. cyq.data mysql_CYQ.Data4.5.5下载-CYQ.Data数据框架整套下载4.5.5 免费版【附源码】-东坡下载...
  3. 【论文解析】Cascade R-CNN: Delving into High Quality Object Detection
  4. java 图片合成 工具类_Java图片合成工具类
  5. html中的div标签的含义和应用
  6. Python web框架flask
  7. 辩论赛基础技巧培训PPT模板
  8. 厦大C语言上机 1397 数据排序
  9. 项目管理RMMM模型:80%的企业处于0级,没有标准,临时分配资源
  10. 关于使用电脑的打字技巧