专栏首页魔法师的世界c++ | lwketh | day04

c++ | lwketh | day04

note

 已知 api 功能:
 - create_window
    - window_callback  系统会在窗口事件发生后调用的函数
        - 给窗口绑定事件  在 windows 中,事件被称之为消息
            - 窗口发生不同事件(案件/鼠标移动等)的时候本函数会自动调用
                - PostQuitMessage
                - buttonAction
                - keyboardAction

 - window_main
    - container
        - element :
            - Edit (输入框) 
            - BUTTON (什么垃圾东西,按钮全大写,输入框第一个字母大写,这设计,mmp)
                 
- element
    - buttonAction 
        - 样式设定
        - x, y, w, h
        - 按钮的父窗口,也就是放在哪个窗口里
        - 按钮的 tag,自行指定

- runloop
    -  如果窗口没有接收到退出消息的话,就一直循环
        - 检查消息队列,如果消息存在的话,执行消息处理 如果没有任何消息,GetMessage 就会等在这里

homework

不太清楚, 有些可以复用的函数 用不了

#include <windows.h>
#include <tchar.h>
#include <string>
#include <sstream>
#include <atlstr.h>


// 这样写了之后就可以用 string 替代原本的 std::string 写法
using std::string;
using std::stringstream;


// 下面两个分别是按钮和输入框的 tag,随便是什么不同的数字就可以了
const int kbcLoginButtonTag = 233;
const int kbcUsernameInputTag = 1233;
const int kbcUsernameInputTag02 = 1234;

bool
validate_login(CString &s1, CStirng &s2) {
    if (s1 =="leiketang" && s2 == "kbc") {
        return true;
    }
    return false;
}

CString
content_by_input_tag(HWND windowId, int inputTag) {
    // 获得输入框的 “句柄”
    auto inputId = GetDlgItem(windowId, inputTag);
     
    // 获得输入框中的内容
    const int length = 128;

    TCHAR text[length];
    GetWindowText(inputId, text, length);
    CString content(text);

    return content;
}


// 这个自定义的函数是我们用来响应按钮点击事件的
// 这个函数在 windowCallback 中被我们调用
void
keyboardAction(unsigned char key) {
    // 用 stringstream 格式化字符串
    // 用 CString 转成 MessageBox 所需参数的格式
    stringstream s;
    s << string("按键 [") << (int)key << string("] 被按下");

    CString content(s.str().c_str());
    // 需要注意的是,如果你开了输入法啊,key 将会一直是 229
    MessageBox(NULL, content, _T("按键事件"), MB_OK);
}

// 这个自定义的函数是我们用来响应按钮点击事件的
// 这个函数在 windowCallback 中被我们调用
void
buttonAction(int buttonTag, HWND windowId) {
    if (buttonTag == kbcLoginButtonTag) {
        // 获得输入框的 “句柄”
        auto inputId = GetDlgItem(windowId, kbcUsernameInputTag);
        //HWND receiveEditorHwnd = GetDlgItem(windowId, EDIT_ID2);
        auto inputId02 = GetDlgItem(windowId, kbcUsernameInputTag02);
        //CString content = content_by_input_tag(windowId, kbcUsernameInputTag);
        //CString content02 = content_by_input_tag(windowId, kbcUsernameInputTag02);
        // 获得输入框中的内容
         const int length = 128;

         TCHAR text[length];
         GetWindowText(inputId, text, length);
         CString content(text);

         TCHAR text02[length];
         GetWindowText(inputId02, text02, length);
         CString content02(text02);
      
        CString c1 = "leiketang";
        CString c2 = "kbc";
        if (content == c1 && content02 == c2) {
            // 需要注意的是,如果你开了输入法啊,key 将会一直是 229
            MessageBox(NULL, content + content02, _T("登录成功"), MB_OK);
        }  else {
            MessageBox(NULL, content + content02, _T("登录失败"), MB_OK);
        }
    }
}

// win32 窗口的回调函数
// 函数的定义是固定好的
LRESULT CALLBACK 
windowCallback(HWND windowId, UINT msg, WPARAM wp, LPARAM lp) {
    // 窗口发生不同事件(案件/鼠标移动等)的时候本函数会自动调用
    // msg 代表了事件的类型,WM_DESTROY 表示窗口关闭
    // 在 windows 中,事件被称之为消息
    if (msg == WM_DESTROY) {
        PostQuitMessage(0);
        return 0;
    } else if (msg == WM_COMMAND) {
        // msg 是 WM_COMMAND 的时候,表明是按钮点击事件
        // 这时候 wp 中存的就是按钮的 tag,这个 tag 是我们自己在创建按钮的时候设定的
        int tag = (int)wp;
        buttonAction(tag, windowId);
    } else if (msg == WM_KEYDOWN) {
        unsigned char key = (unsigned char)wp;
        keyboardAction(key);
    }
    // 系统的默认窗口处理函数,这是套路
    return DefWindowProc(windowId, msg, wp, lp);
}

int
runLoop() {
    MSG msg;
    ZeroMemory(&msg, sizeof(msg));
    // 窗口进入消息循环
    // 如果窗口没有接收到退出消息的话,就一直循环
    while(msg.message != WM_QUIT) {
        // 检查消息队列,如果消息存在的话,执行消息处理
        // 如果没有任何消息,GetMessage 就会等在这里
        if(GetMessage(&msg, NULL, 0, 0)) {
            // 下面两行是规定,现在不必理解为什么
            // 这两行执行完后,系统就会自动调用 WndProc 函数
            TranslateMessage(&msg);
            DispatchMessage(&msg);
        }
    }
    return (int)msg.wParam;
}

HWND
kbcCreateWindow(HINSTANCE hInstance) {
    // _T 包起来的字符串才能在里面使用中文
    auto className = _T("kbcWinClass");
    // 设置窗口属性并初始化
    WNDCLASSEX window = { 0 };
    window.hInstance = hInstance;           // 这个是 WinMain 函数的第一个参数
    window.lpfnWndProc = windowCallback;    // 系统会在窗口事件发生后调用的函数
    window.lpszClassName = className;       // 这个要和下面 CreateWindow 第一个参数一样
    // 下面的属性,不必具体了解,当做规定即可
    // 实际上如果这个 API 设计得稍微用点点点点心,下面很多属性都应该有默认值而不是让人手动去设置
    window.cbSize = sizeof(WNDCLASSEX);
    window.cbClsExtra = 0;
    window.cbWndExtra = 0;
    window.style = CS_CLASSDC;
    window.hIcon = LoadIcon(NULL, IDI_APPLICATION);
    window.hCursor = LoadCursor(NULL, IDC_ARROW);
    window.hbrBackground = (HBRUSH)(COLOR_WINDOW + 1);
    window.lpszMenuName = NULL;
    window.hIconSm = LoadIcon(NULL, IDI_APPLICATION);
    RegisterClassEx(&window);

    // 创建窗口
    HWND windowId = CreateWindow(
        className,                  // 这个要和上面的 wcex 的 lpszClassName 属性一样
        _T("快编程雷课堂窗口范例 4"), // 窗口标题
        WS_OVERLAPPEDWINDOW,        // 窗口样式
        // 下面 4 个参数分别是窗口左上角的 x y 坐标以及窗口的 w h
        100, 100, 800, 600,
        // 下面 4 个现在应当做规定
        NULL,
        NULL,
        hInstance,
        NULL
    );

    // 显示,更新窗口,当做规定
    ShowWindow(windowId, SW_SHOW);
    UpdateWindow(windowId);

    return windowId;
}

/*
- 里面有 2 个输入框和 1 个按钮   done
- 点击按钮后,获取 2 个输入框的值并分别用 MessageBox 输出  done
- 实现一个判断,当输入框 1 的内容是 “leiketang” 并且输入框 2 的内容是 
“kbc” 的时候,弹窗输出 “登录成功”done
*/

int WINAPI
WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, PSTR lpCmdLine, int nCmdShow) {
    HWND windowId = kbcCreateWindow(hInstance);

    // +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
    // 输入框, 如果你对这个函数有兴趣,文档链接如下
    // https://docs.microsoft.com/en-us/previous-versions/aa931018(v=msdn.10)
    CreateWindow(
        _T("Edit"),                        // 输入框名称,这里一定不能错
        _T("快编程  kuaiBianCheng.com"),   // 这里是输入框的默认内容
        // 样式设定,分别是,子窗口,窗口可见,带纵向滚动条,带横向滚动条,多行编辑框,
        WS_CHILD | WS_VISIBLE | WS_VSCROLL | WS_HSCROLL | ES_MULTILINE,
        20, 80, 500, 200,
        windowId,
        (HMENU)kbcUsernameInputTag,
        hInstance,
        NULL
    );
    CreateWindow(
        _T("Edit"),                        // 输入框名称,这里一定不能错
        _T("快编程  kuaiBianCheng.com davizi 02"),   // 这里是输入框的默认内容
        // 样式设定,分别是,子窗口,窗口可见,带纵向滚动条,带横向滚动条,多行编辑框,
        WS_CHILD | WS_VISIBLE | WS_VSCROLL | WS_HSCROLL | ES_MULTILINE,
        20, 280, 500, 200,
        windowId,
        (HMENU)kbcUsernameInputTag02,
        hInstance,
        NULL
    );
    // +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
    
    // 创建按钮
    CreateWindow(
        _T("BUTTON"),     // 按钮类名称,必须是 BUTTON
        _T("登录"),       // 按钮的标题名,可以随便改
        // 样式,分别是,创建一个子窗口,创建的窗口可见,按键(类型)
        WS_CHILD | WS_VISIBLE | BS_PUSHBUTTON,
        0, 0, 400, 50,              // 按钮的左上角坐标以及宽高
        windowId,                   // 按钮的父窗口,也就是放在哪个窗口里
        (HMENU)kbcLoginButtonTag,   // 按钮的 tag,自行指定
        // 下面 2 个现在当做规定
        hInstance,
        NULL
    );

    return runLoop();
}

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

我来说两句

0 条评论
登录 后参与评论

相关文章

  • c++ | lwketh | day01

    李朝
  • c++ | lwketh | day02

    李朝
  • c++ | lwketh | day_04

    李朝
  • c++ | lwketh | day03

    李朝
  • day04

      一个只包含一个元素的元祖,必须在这个元素的后面加上逗号,如:(1,)。否则他就是(1),而(1)和1并无区别。

    py3study
  • 从零学Python(案例源码)

    https://gitee.com/itcode-itcode/Python.git

    程序源代码
  • 从零搭建Spring Boot脚手架(5):整合 Mybatis Plus

    在上一文中我根据Mybatis中Mapper的生命周期手动实现了一个简单的通用Mapper功能,但是遗憾的是它缺乏实际生产的检验。因此我选择更加成熟的一个Myb...

    码农小胖哥
  • 爬虫系列(18)Python-Spider。

    小Gy
  • django学习-day04

    #模板结构优化 #dl1项目中muban app有演示 1.模板引入 include 标签 方法使用起来很简单,就是分别吧不同的模板存在tmplates中...

    kirin
  • Java基础-day04-代码题

    Java基础-day04-代码题 1.键盘录入班级人数,并用随机数产生成绩 案例描述 第一题:分析以下需求,并用代码实现 1.键盘录入班级人数 2.根据录入的...

    Java帮帮
  • Java基础-day04-基础题

    Java基础-day04-基础题 1.遍历数组 案例描述 依次输出数组中的每一个元素 获取数值长度:数值名.length eclipse展示 ? 具体实现代码 ...

    Java帮帮
  • 《剑指offer》专题—算法训练 day04

    https://www.nowcoder.com/practice/75e878df47f24fdc9dc3e400ec6058ca?

    RAIN7
  • Java SE | 基础语法day04

    剑走天涯
  • 【LeetCode】重建二叉树day04

    4.从中序便利中我们可以判断出根节点是哪一个,那就是前序遍历的preorder[0].

    居士
  • Java SE | 每日作业卷day04

    定义一个长度为3的一维数组,给每个元素赋值. (要求数组中每个元素的值是0-9的随机数),遍历数组打印每个元素的值。

    剑走天涯
  • 每天一道面试题 | day04

    (2)通过实现Runnable接口(推荐使用,因为Java中是单继承,一个类只有一个父类,若继承了Thread类,就无法在继承其它类,显然实现Runnable接...

    剑走天涯
  • JavaWeb05- 就这几步轻松操作MySQL数据库!

    mysql-1 一.数据库 1. 数据库介绍 数据库就是存储数据的仓库,其本质是一个文件系统,数据按照特定的格式将数据存储起来,用户可以通过sql语句对数据库中...

    Java帮帮
  • 微服务[学成在线] day04:页面静态化

    常用的 java 模板引擎还有哪些? Jsp、Freemarker、Thymeleaf、Velocity 等

    LCyee
  • JDK1.9-Collection集合

    版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明...

    cwl_java

扫码关注云+社区

领取腾讯云代金券