Windows C++控制台菜单库开发与源码展示
Windows C++控制台菜单库
- 声明:
- 演示视频:
- 一、前言
- 二、具体框架
- 三、源码展示
- console_screen_set.h
- frame
- console_screen_frame_base.h
- console_screen_frame_char.h
- console_screen_frame_wchar_t.h
- console_screen_frame.h
- menu
- console_screen_menu_base.h
- console_screen_menu_operate.h
- console_screen_menu.h
- text
- console_screen_text_base.h
- console_screen_text.h
- 四、代码参考
声明:
开发环境为 VS2022 C++,菜单库源码(2200行左右)为本人独立制作,转载使用请标明出处,谢谢!
演示视频:
C++菜单库例子展示
一、前言
做控制台菜单的时候总感觉太耗时了,因为坐标不对需要修改,还要一个一个检查,以及颜色的处理。
具体操作可看这篇博客C语言伪图形与键盘操作加扫雷实例(写的太挫了),所以我想制作一个控制台菜单库,便于在菜单方面的快速开发。
二、具体框架
因为制作的时候是走一步看一步,导致设计十分冗余,后续有时间可能会更新调整。这里我列举一些里面的功能:
- set 包含常用的函数,例如光标移动、隐藏等等。
- menu(模板) 包含选项、框架、内置键盘操作、内置鼠标操作、打印、清除等等。
- text(模板) 包含打印、清除等等。
在使用宽字符(wchar_t)对应的类,如:wmenu、wtext、应该加上这一句:
std::wcout.imbue(std::locale("zh_CN"));
详细可参考 C++基础(十八)区域设置、locale、中文乱码、中文不输出 ,这里不赘述。
三、源码展示
console_screen_set.h
#pragma once#include <CoreWindow.h>
#include <stdio.h>namespace my
{inline void SetPos(int x, int y){COORD pos = { x, y };SetConsoleCursorPosition(GetStdHandle(STD_OUTPUT_HANDLE), pos);}inline void HideCursor(){CONSOLE_CURSOR_INFO cursor_info = { 1, 0 };SetConsoleCursorInfo(GetStdHandle(STD_OUTPUT_HANDLE), &cursor_info);}inline void SetWordSize(int SizeX, int SizeY){CONSOLE_FONT_INFOEX font_infoex;COORD pos = { SizeX, SizeY };font_infoex.cbSize = sizeof(CONSOLE_FONT_INFOEX);font_infoex.dwFontSize = pos;SetCurrentConsoleFontEx(GetStdHandle(STD_OUTPUT_HANDLE), false, &font_infoex);}inline void FlushBuffer(){FlushConsoleInputBuffer(GetStdHandle(STD_INPUT_HANDLE));}inline void SetScreenSize(short consoleWide, short consoleHigh){char cmd[100];sprintf_s(cmd, "mode con cols=%d lines=%d", consoleWide, consoleHigh);system(cmd);}inline void GetMouseOperate(){if (!SetConsoleMode(GetStdHandle(STD_INPUT_HANDLE), ENABLE_EXTENDED_FLAGS | ENABLE_WINDOW_INPUT | ENABLE_MOUSE_INPUT)){fprintf(stderr, "%s\n", "SetConsoleMode");}}
}
frame
console_screen_frame_base.h
#pragma once#include <CoreWindow.h>
#include <cassert>namespace my
{template<class T>class console_screen_frame_base{template<class Type, class CH, class STRING>friend class console_screen_frame;template<class PFUNC, class MENU, class FRAME, class CHAR, class STRING>friend class console_screen_menu;template<class TEXTCHAR, class FRAME, class STRING, class CHAR>friend class console_screen_text;public:console_screen_frame_base(int x = 0, int y = 0, int high = 5, int wide = 10,T up = 0, T down = 0, T left = 0, T right = 0,T top_left = 0, T bottom_left = 0, T top_right = 0, T bottom_right = 0):_x(x), _y(y), _high(high), _wide(wide), _up(up), _down(down), _left(left), _right(right), _top_left(top_left), _bottom_left(bottom_left), _top_right(top_right), _bottom_right(bottom_right){assert(x >= 0 && y >= 0);assert(high >= 0 && wide >= 0);}void changePos(int x, int y){assert(x >= 0 && y >= 0);_x = x;_y = y;}void changeFrameSize(int high, int wide){assert(high >= 0 && wide >= 0);_high = high;_wide = wide;}void changeSide(T up = 0, T down = 0, T left = 0, T right = 0){_up = up == 0 ? _up : up;_down = down == 0 ? _down : down;_left = left == 0 ? _left : left;_right = right == 0 ? _right : right;}void changeCorner(T top_left = 0, T bottom_left = 0, T top_right = 0, T bottom_right = 0){_top_left = top_left == 0 ? _top_left : top_left;_bottom_left = bottom_left == 0 ? _bottom_left : bottom_left;_top_right = top_right == 0 ? _top_right : top_right;_bottom_right = bottom_right == 0 ? _bottom_right : bottom_right;}void changeUp(T up){_up = up;}void changeDown(T down){_down = down;}void changeLeft(T left){_left = left;}void changeRight(T right){_right = right;}void changeTopLeft(T top_left){_top_left = top_left;}void changeTopRight(T top_right){_top_right = top_right;}void changeBottomLeft(T bottom_left){_bottom_left = bottom_left;}void changeBottomRight(T bottom_right){_bottom_right = bottom_right;}protected:void printFrame(){if (_up != 0){printCharUp();}if (_down != 0){printCharDown();}if (_left != 0){printCharLeft();}if (_right != 0){printCharRight();}if (_top_left != 0 ||_top_right != 0 ||_bottom_left != 0 ||_bottom_right != 0){printCharCorner();}}virtual void printCharUp() = 0;virtual void printCharDown() = 0;virtual void printCharLeft() = 0;virtual void printCharRight() = 0;virtual void printCharCorner() = 0;void cleanFrame(){if (_up != 0){cleanCharUp();}if (_down != 0){cleanCharDown();}if (_left != 0){cleanCharLeft();}if (_right != 0){cleanCharRight();}if (_top_left != 0 ||_top_right != 0 ||_bottom_left != 0 ||_bottom_right != 0){cleanCharCorner();}}virtual void cleanCharUp() = 0;virtual void cleanCharDown() = 0;virtual void cleanCharLeft() = 0;virtual void cleanCharRight() = 0;virtual void cleanCharCorner() = 0;protected:short _x;short _y;short _high;short _wide;T _up;T _down;T _left;T _right;T _top_left = 0;T _bottom_left = 0;T _top_right = 0;T _bottom_right = 0;};
}
console_screen_frame_char.h
#pragma once#include "console_screen_frame_base.h"
#include "console_screen_set.h"
#include <iostream>namespace my
{extern void SetPos(int x, int y);class console_screen_frame_char : public console_screen_frame_base<signed char>{public:console_screen_frame_char(int x, int y, int high, int wide,signed char up = 0, signed char down = 0,signed char left = 0, signed char right = 0,signed char top_left = 0, signed char bottom_left = 0,signed char top_right = 0, signed char bottom_right = 0):console_screen_frame_base(x, y, high, wide, up, down, left, right,top_left, bottom_left, top_right, bottom_right){;}void show(){printFrame();}void clean(){cleanFrame();}protected:void printCharUp(){SetPos(_x + 1, _y);for (int wide = 1; wide <= _wide - 2; ++wide){std::cout << _up;}}void printCharDown(){SetPos(_x + 1, _y + _high - 1);for (int wide = 1; wide <= _wide - 2; ++wide){std::cout << _down;}}void printCharLeft(){for (int high = 1; high <= _high - 2; ++high){SetPos(_x, _y + high);std::cout << _left;}}void printCharRight(){for (int high = 1; high <= _high - 2; ++high){SetPos(_x + _wide - 1, _y + high);std::cout << _right;}}void printCharCorner(){SetPos(_x, _y);std::cout << _top_left;SetPos(_x + _wide - 1, _y);std::cout << _top_right;SetPos(_x, _y + _high - 1);std::cout << _bottom_left;SetPos(_x + _wide - 1, _y + _high - 1);std::cout << _bottom_right;}void cleanCharUp(){signed char temp = _up;_up = ' ';printCharUp();_up = temp;}void cleanCharDown(){signed char temp = _down;_down = ' ';printCharDown();_down = temp;}void cleanCharLeft(){signed char temp = _left;_left = ' ';printCharLeft();_left = temp;}void cleanCharRight(){signed char temp = _right;_right = ' ';printCharRight();_right = temp;}void cleanCharCorner(){signed char temp1 = _top_left;signed char temp2 = _bottom_left;signed char temp3 = _top_right;signed char temp4 = _bottom_right;changeCorner(' ', ' ', ' ', ' ');printCharCorner();changeCorner(temp1, temp2, temp3, temp4);}};
}
console_screen_frame_wchar_t.h
#pragma once#include "console_screen_frame_base.h"
#include "console_screen_set.h"
#include <iostream>namespace my
{class console_screen_frame_wchar_t : public console_screen_frame_base<wchar_t>{public:console_screen_frame_wchar_t(int x, int y, int high, int wide,wchar_t up = 0, wchar_t down = 0,wchar_t left = 0, wchar_t right = 0,wchar_t top_left = 0, wchar_t bottom_left = 0,wchar_t top_right = 0, wchar_t bottom_right = 0):console_screen_frame_base(x, y, high, wide, up, down, left, right,top_left, bottom_left, top_right, bottom_right){;}void show(){printFrame();}void clean(){cleanFrame();}protected:void printCharUp(){for (int wide = 0; wide <= _wide - 6; wide += 2){SetPos(_x + 2 + wide, _y);std::wcout << _up;}}void printCharDown(){for (int wide = 0; wide <= _wide - 6; wide += 2){SetPos(_x + 2 + wide, _y + _high - 1);std::wcout << _down;}}void printCharLeft(){for (int high = 1; high <= _high - 2; ++high){SetPos(_x, _y + high);std::wcout << _left;}}void printCharRight(){for (int high = 1; high <= _high - 2; ++high){SetPos(_x + _wide - 2, _y + high);std::wcout << _right;}}void printCharCorner(){SetPos(_x, _y);std::wcout << _top_left;SetPos(_x + _wide - 2, _y);std::wcout << _top_right;SetPos(_x, _y + _high - 1);std::wcout << _bottom_left;SetPos(_x + _wide - 2, _y + _high - 1);std::wcout << _bottom_right;}void cleanCharUp(){SetPos(_x + 2, _y);for (int wide = 0; wide <= _wide - 4; ++wide){std::cout << ' ';}}void cleanCharDown(){SetPos(_x + 2, _y + _high - 1);for (int wide = 0; wide <= _wide - 4; ++wide){std::cout << ' ';}}void cleanCharLeft(){for (int high = 1; high <= _high - 2; ++high){SetPos(_x, _y + high);std::cout << ' ' << ' ';}}void cleanCharRight(){for (int high = 1; high <= _high - 2; ++high){SetPos(_x + _wide - 2, _y + high);std::cout << ' ' << ' ';}}void cleanCharCorner(){SetPos(_x, _y);std::cout << ' ' << ' ';SetPos(_x + _wide - 2, _y);std::cout << ' ' << ' ';SetPos(_x, _y + _high - 1);std::cout << ' ' << ' ';SetPos(_x + _wide - 2, _y + _high - 1);std::cout << ' ' << ' ';}};
}
console_screen_frame.h
#pragma once#include "console_screen_frame_char.h"
#include "console_screen_frame_wchar_t.h"
#include <vector>
#include <utility>namespace my
{enum FRAME_DIRECTION{Up = 0,Down,Left,Right};template<class T, class CH, class STRING>class console_screen_frame{template<class PFUNC, class MENU, class FRAME, class CHAR, class STRING>friend class console_screen_menu;template<class TEXTCHAR, class FRAME, class STRING, class CHAR>friend class console_screen_text;public:console_screen_frame(int x, int y, int high, int wide,CH up = 0, CH down = 0, CH left = 0, CH right = 0,CH top_left = 0, CH bottom_left = 0, CH top_right = 0, CH bottom_right = 0):_the_char(x, y, high, wide, up, down, left, right, top_left, bottom_left, top_right, bottom_right){;}void setPos(int x, int y){_the_char.changePos(x, y);}void setFrameSize(int high, int wide){_the_char.changeFrameSize(high, wide);}void setSide(CH up = 0, CH down = 0, CH left = 0, CH right = 0){_the_char.changeSide(up, down, left, right);}void setCorner(CH top_left = 0, CH bottom_left = 0,CH top_right = 0, CH bottom_right = 0){_the_char.changeCorner(top_left, bottom_left, top_right, bottom_right);}void setUp(CH up){_the_char.changeUp(up);}void setDown(CH down){_the_char.changeDown(down);}void setLeft(CH left){_the_char.changeLeft(left);}void setRight(CH right){_the_char.changeRight(right);}void setTopLeft(CH top_left){_the_char.changeTopLeft(top_left);}void setTopRight(CH top_right){_the_char.changeTopRight(top_right);}void setBottomLeft(CH bottom_left){_the_char.changeBottomLeft(bottom_left);}void setBottomRight(CH bottom_right){_the_char.changeBottomRight(bottom_right);}void frameShow(){_the_char.show();if (sizeof(CH) == sizeof(signed char)){wordShow((void(*)(STRING))&getCout, (void(*)(CH))&getCoutC);}else{wordShow((void(*)(STRING))&getWcout, (void(*)(CH))&getWcoutC);}}void frameClean(){_the_char.clean();}void numWord(int number){_word.resize(number);_word_space.resize(number);}void setWord(int pos, STRING str1, signed char direction, short distance){assert(pos >= 0 && pos < _word.size());_word[pos] = str1;_word_space[pos] = { direction, distance };}void recallWord(int pos){assert(pos >= 0 && pos < _word.size());_word.erase(_word.begin() + pos);_word_space.erase(_word_space.begin() + pos);}protected:void wordShow(void(*outfuncString)(STRING), void(*outfuncChar)(CH)){for (int i = 0; i < _word.size(); ++i){if (_the_char._up != 0 && _word_space[i].first == Up){SetPos(_the_char._x + _word_space[i].second, _the_char._y);if (_word[i] == nullptr){continue;}outfuncString(_word[i]);}else if (_the_char._down != 0 && _word_space[i].first == Down){SetPos(_the_char._x + _word_space[i].second, _the_char._y + _the_char._high - 1);if (_word[i] == nullptr){continue;}outfuncString(_word[i]);}else if (_the_char._left != 0 && _word_space[i].first == Left){int len = clen(_word[i]);for (int j = 0; j < len; ++j){SetPos(_the_char._x, _the_char._y + _word_space[i].second + j);if (_word[i] == nullptr){continue;}outfuncChar(_word[i][j]);}}else if (_the_char._right != 0 && _word_space[i].first == Right){int len = clen(_word[i]);for (int j = 0; j < len; ++j){SetPos(_the_char._x + _the_char._wide - sizeof(CH), _the_char._y + _word_space[i].second + j);if (_word[i] == nullptr){continue;}outfuncChar(_word[i][j]);}}}}static void getWcout(STRING str1){std::wcout << str1;}static void getCout(STRING str1){std::cout << str1;}static void getWcoutC(CH ch){std::wcout << ch;}static void getCoutC(CH ch){std::cout << ch;}protected:std::vector<STRING> _word; // 嵌入词std::vector<std::pair<signed char, short>> _word_space; // 嵌入词位置T _the_char;typedef size_t(*p_T_char)(STRING);p_T_char clen = sizeof(CH) == sizeof(signed char) ? (p_T_char)&strlen : (p_T_char)&wcslen;};typedef console_screen_frame<console_screen_frame_char, signed char, const char*> frame;typedef console_screen_frame<console_screen_frame_wchar_t, wchar_t, const wchar_t*> wframe;}
menu
console_screen_menu_base.h
#pragma once#include "console_screen_set.h"
#include <iostream>
#include <string>
#include <vector>
#include <cassert>
#include <Windows.h>
#include <utility>namespace my
{template<class T>static T Max(T a, T b){return a > b ? a : b;}typedef enum CONSOLE_SCREEN_COLOR{CBlack = 0,CBlue,CGreen,CLight_blue,CRed,CPurple,CYellow,CWhite,BBlack = 0,BBlue = 0x10,BGreen = 0x20,BLight_blue = 0x30,BRed = 0x40,BPurple = 0x50,BYellow = 0x60,BWhite = 0x70} the_color;class console_screen_menu_base{public:console_screen_menu_base(int x, int y, int rowNum = 1, int colNum = 1, int high = 1, int wide = 1):_x(x), _y(y), _high(high), _wide(wide), _rowNum(rowNum), _colNum(colNum), _option(rowNum, std::vector<std::string>(colNum, std::string("nullptr"))), _char_space(rowNum, std::vector<std::pair<short, short>>(colNum, { 1, 1 })), _char_color(rowNum, std::vector<std::pair<short, bool>>(colNum, { CWhite, 0 })), _background_space(rowNum, std::vector<std::pair<short, short>>(colNum, { 0, 0 })), _background_color(rowNum, std::vector<std::pair<short, bool>>(colNum, { BBlack, 0 })){assert(rowNum >= 1 && colNum >= 1);assert(x >= 0 && y >= 0);assert(high >= 0 && wide >= 0);}const std::string& getOption(int rowPos, int colPos){assert(rowPos >= 1 && colPos >= 1);return _option[rowPos - 1][colPos - 1];}void setOption(int rowPos, int colPos, const std::string& str1,short front = 1, short back = 1){assert(rowPos >= 1 && colPos >= 1);assert(front >= 0 && back >= 0);assert(rowPos <= _rowNum && colPos <= _colNum);_option[rowPos - 1][colPos - 1] = str1;_char_space[rowPos - 1][colPos - 1] = { front, back };}void setColor(int rowPos, int colPos, int charColor, bool charStrength, int backgroundColor = 0, bool backgroundStrength = false){char_color(rowPos, colPos, charColor, charStrength);background_color(rowPos, colPos, backgroundColor, backgroundStrength);}void setCharColor(int rowPos, int colPos, int colorNum, bool strength = false){char_color(rowPos, colPos, colorNum, strength);}void setBackgroundColor(int rowPos, int colPos, int colorNum, bool strength = false){background_color(rowPos, colPos, colorNum, strength);}void setCharSpace(int rowPos, int colPos, int front, int back){assert(rowPos >= 1 && colPos >= 1);_char_space[rowPos - 1][colPos - 1] = { front, back };}void setBackgroundSpace(int rowPos, int colPos, int front, int back){assert(rowPos >= 1 && colPos >= 1);_background_space[rowPos - 1][colPos - 1] = { front, back };}void setRowSpace(int row){assert(row >= 0);_row_space = row;}void setPos(int x, int y){assert(x >= 0 && y >= 0);_x = x;_y = y;}void show(){show_or_clean_ready(true);}void clean(){show_or_clean_ready(false);}protected:void char_color(int rowPos, int colPos, int colorNum, bool strength){assert(CBlack <= colorNum && colorNum <= CWhite);_char_color[rowPos - 1][colPos - 1] = { colorNum, strength };}void background_color(int rowPos, int colPos, int colorNum, bool strength){assert(BBlack <= colorNum && colorNum <= BWhite);_background_color[rowPos - 1][colPos - 1] = { colorNum, strength };}void clean_ready(int i, int j, int x, int y){int len1 = _option[i][j].size();if (_background_space[i][j].first > 0){len1 += _background_space[i][j].first;}if (_background_space[i][j].second > 0){len1 += _background_space[i][j].second;}// 补丁:正序打印会影响宽字体,逆向可解决for (int i = len1 - 1; i >= 0; --i){SetPos(x + i, y);std::cout << ' ';}}void show_ready(int i, int j){int charStrength = 0;int backgroundStrength = 0;if (_background_color[i][j].second == true){backgroundStrength = BACKGROUND_INTENSITY;}if (_char_color[i][j].second == true){charStrength = FOREGROUND_INTENSITY;}if (_background_space[i][j].first > 0){SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), _background_color[i][j].first | backgroundStrength);std::cout << std::string(_background_space[i][j].first, ' ');}SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), _char_color[i][j].first | charStrength | _background_color[i][j].first | backgroundStrength);std::cout << _option[i][j];if (_background_space[i][j].second > 0){SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), _background_color[i][j].first | backgroundStrength);std::cout << std::string(_background_space[i][j].second, ' ');}SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), CWhite | BBlack);}void show_or_clean_ready(bool option){int countPosY = 0;for (int i = 0; i < _rowNum; ++i){if (i != 0){countPosY += _row_space;}int countPosX = 0;for (int j = 0; j < _colNum; ++j){int front = _char_space[i][j].first;if (j != 0){countPosX += _option[i][j - 1].size();countPosX += _char_space[i][j - 1].first + _background_space[i][j - 1].first;countPosX += _background_space[i][j - 1].second + _char_space[i][j - 1].second;}SetPos(_x + front + countPosX, _y + i + countPosY);if (option == true){show_ready(i, j);}else{clean_ready(i, j, _x + front + countPosX, _y + i + countPosY);}}}}protected:std::vector<std::vector<std::string>> _option; // 选项//std::vector<std::vector<const char*>> _option;std::vector<std::vector<std::pair<short, short>>> _char_space; // 字符间距std::vector<std::vector<std::pair<short, bool>>> _char_color; // 字符 颜色 与 颜色加强std::vector<std::vector<std::pair<short, short>>> _background_space; // 背景间距std::vector<std::vector<std::pair<short, bool>>> _background_color; // 背景 颜色 与 颜色加强short _x;short _y;short _high;short _wide;//short _rowNum = 1;//short _colNum = 1;int _rowNum = 1;int _colNum = 1;signed char _row_space = 0; // 行距};
}
console_screen_menu_operate.h
#pragma once#include "console_screen_set.h"
#include <iostream>
#include <string>
#include <vector>
#include <cassert>
#include <Windows.h>
#include <utility>namespace my
{template<class T>static T Max(T a, T b){return a > b ? a : b;}typedef enum CONSOLE_SCREEN_COLOR{CBlack = 0,CBlue,CGreen,CLight_blue,CRed,CPurple,CYellow,CWhite,BBlack = 0,BBlue = 0x10,BGreen = 0x20,BLight_blue = 0x30,BRed = 0x40,BPurple = 0x50,BYellow = 0x60,BWhite = 0x70} the_color;class console_screen_menu_base{public:console_screen_menu_base(int x, int y, int rowNum = 1, int colNum = 1, int high = 1, int wide = 1):_x(x), _y(y), _high(high), _wide(wide), _rowNum(rowNum), _colNum(colNum), _option(rowNum, std::vector<std::string>(colNum, std::string("nullptr"))), _char_space(rowNum, std::vector<std::pair<short, short>>(colNum, { 1, 1 })), _char_color(rowNum, std::vector<std::pair<short, bool>>(colNum, { CWhite, 0 })), _background_space(rowNum, std::vector<std::pair<short, short>>(colNum, { 0, 0 })), _background_color(rowNum, std::vector<std::pair<short, bool>>(colNum, { BBlack, 0 })){assert(rowNum >= 1 && colNum >= 1);assert(x >= 0 && y >= 0);assert(high >= 0 && wide >= 0);}const std::string& getOption(int rowPos, int colPos){assert(rowPos >= 1 && colPos >= 1);return _option[rowPos - 1][colPos - 1];}void setOption(int rowPos, int colPos, const std::string& str1,short front = 1, short back = 1){assert(rowPos >= 1 && colPos >= 1);assert(front >= 0 && back >= 0);assert(rowPos <= _rowNum && colPos <= _colNum);_option[rowPos - 1][colPos - 1] = str1;_char_space[rowPos - 1][colPos - 1] = { front, back };}void setColor(int rowPos, int colPos, int charColor, bool charStrength, int backgroundColor = 0, bool backgroundStrength = false){char_color(rowPos, colPos, charColor, charStrength);background_color(rowPos, colPos, backgroundColor, backgroundStrength);}void setCharColor(int rowPos, int colPos, int colorNum, bool strength = false){char_color(rowPos, colPos, colorNum, strength);}void setBackgroundColor(int rowPos, int colPos, int colorNum, bool strength = false){background_color(rowPos, colPos, colorNum, strength);}void setCharSpace(int rowPos, int colPos, int front, int back){assert(rowPos >= 1 && colPos >= 1);_char_space[rowPos - 1][colPos - 1] = { front, back };}void setBackgroundSpace(int rowPos, int colPos, int front, int back){assert(rowPos >= 1 && colPos >= 1);_background_space[rowPos - 1][colPos - 1] = { front, back };}void setRowSpace(int row){assert(row >= 0);_row_space = row;}void setPos(int x, int y){assert(x >= 0 && y >= 0);_x = x;_y = y;}void show(){show_or_clean_ready(true);}void clean(){show_or_clean_ready(false);}protected:void char_color(int rowPos, int colPos, int colorNum, bool strength){assert(CBlack <= colorNum && colorNum <= CWhite);_char_color[rowPos - 1][colPos - 1] = { colorNum, strength };}void background_color(int rowPos, int colPos, int colorNum, bool strength){assert(BBlack <= colorNum && colorNum <= BWhite);_background_color[rowPos - 1][colPos - 1] = { colorNum, strength };}void clean_ready(int i, int j, int x, int y){int len1 = _option[i][j].size();if (_background_space[i][j].first > 0){len1 += _background_space[i][j].first;}if (_background_space[i][j].second > 0){len1 += _background_space[i][j].second;}// 补丁:正序打印会影响宽字体,逆向可解决for (int i = len1 - 1; i >= 0; --i){SetPos(x + i, y);std::cout << ' ';}}void show_ready(int i, int j){int charStrength = 0;int backgroundStrength = 0;if (_background_color[i][j].second == true){backgroundStrength = BACKGROUND_INTENSITY;}if (_char_color[i][j].second == true){charStrength = FOREGROUND_INTENSITY;}if (_background_space[i][j].first > 0){SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), _background_color[i][j].first | backgroundStrength);std::cout << std::string(_background_space[i][j].first, ' ');}SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), _char_color[i][j].first | charStrength | _background_color[i][j].first | backgroundStrength);std::cout << _option[i][j];if (_background_space[i][j].second > 0){SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), _background_color[i][j].first | backgroundStrength);std::cout << std::string(_background_space[i][j].second, ' ');}SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), CWhite | BBlack);}void show_or_clean_ready(bool option){int countPosY = 0;for (int i = 0; i < _rowNum; ++i){if (i != 0){countPosY += _row_space;}int countPosX = 0;for (int j = 0; j < _colNum; ++j){int front = _char_space[i][j].first;if (j != 0){countPosX += _option[i][j - 1].size();countPosX += _char_space[i][j - 1].first + _background_space[i][j - 1].first;countPosX += _background_space[i][j - 1].second + _char_space[i][j - 1].second;}SetPos(_x + front + countPosX, _y + i + countPosY);if (option == true){show_ready(i, j);}else{clean_ready(i, j, _x + front + countPosX, _y + i + countPosY);}}}}protected:std::vector<std::vector<std::string>> _option; // 选项//std::vector<std::vector<const char*>> _option;std::vector<std::vector<std::pair<short, short>>> _char_space; // 字符间距std::vector<std::vector<std::pair<short, bool>>> _char_color; // 字符 颜色 与 颜色加强std::vector<std::vector<std::pair<short, short>>> _background_space; // 背景间距std::vector<std::vector<std::pair<short, bool>>> _background_color; // 背景 颜色 与 颜色加强short _x;short _y;short _high;short _wide;//short _rowNum = 1;//short _colNum = 1;int _rowNum = 1;int _colNum = 1;signed char _row_space = 0; // 行距};
}
console_screen_menu.h
#pragma once#include "console_screen_frame.h"
#include "console_screen_menu_operate.h"namespace my
{typedef enum console_screen_menu_operate_way{keyboard = 1,mouse,} way;template<class PFUNC = int(*)(),class MENU = console_screen_menu_operate<PFUNC>, class FRAME = frame, class CHAR = signed char, class STRING = const char*>class console_screen_menu{public:console_screen_menu(int x = 0, int y = 0, int high = 10, int wide = 20, int rowNum = 1, int colNum = 1, bool operate_switch = false):_frame(x, y, high, wide),_menu(x, y, operate_switch, rowNum, colNum, high, wide){;}public: // 自定义操作准备template<class T1, class T2, class T3, class T4>int operateCustom(int (*customize)(T1&, T2&, T3&, T4&), T2& fun1, T3& fun2, T4& fun3){return customize(*this, fun1, fun2, fun3);}template<class T1, class T2, class T3>int operateCustom(int (*customize)(T1&, T2&, T3&), T2& fun1, T3& fun2){return customize(*this, fun1, fun2);}template<class T1, class T2>int operateCustom(int (*customize)(T1&, T2&), T2& fun1){return customize(*this, fun1);}template<class T>int operateCustom(int (*customize)(T&)){return customize(*this);}void customSetMenuCharColor(int rowPos, int colPos, int colorNum, bool strength = false){_menu.setCharColor(rowPos, colPos, colorNum, strength);}const std::string& customGetMenuOption(int rowPos, int colPos){return _menu.getOption(rowPos, colPos);}void customSetMenuOption(int rowPos, int colPos, const std::string& str1, short front = 0, short back = 0){setMenuOption(rowPos, colPos, str1, front, back);}void customMouseAndOptionAc(int posX, int posY){_menu.mouseAndOptionAc(posX, posY);}THE_POS customGetMouseCheckAlgorithm(int mouseX, int mouseY){return _menu.mouseAndOptionDockingAlgorithm(mouseX, mouseY);}void customGetMouseOperate(){_menu.getMouseOperate();}void customOperateClean(){_menu.operateClean();}int customGetSleepTime(){return _menu._sleep_time;}PFUNC customGetOptionButton(int cursorX, int cursorY){assert(cursorX >= 0 && cursorX < _menu._colNum);assert(cursorY >= 0 && cursorY < _menu._rowNum);return _menu._the_way[cursorY][cursorX];}int customGetCursorColNum(){return _menu._colNum;}int customGetCursorX(){return _menu._cursorPosX;}void customSetCursorX(int cursorX){_menu.cursorXReset(cursorX);}int customGetCursorRowNum(){return _menu._rowNum;}int customGetCursorY(){return _menu._cursorPosY;}//short customGetOptionRowNum()//{// return _menu._rowNum;//}//short customGetOptionY()//{// return _menu._cursorPosY;//}void customSetCursorY(int cursorY){_menu.cursorYReset(cursorY);}void customSetCursorPos(int cursorX, int cursorY){_menu.cursorReset(cursorX, cursorY);}void customOperateShow(){_menu.operateShow();}bool customMenuCheckOperate(){return _menu._open_operate;}public: // 静态准备void staticInit(bool yes = true){_staticInit = yes;}bool alreadyStaticInit(){return _staticInit;}public: // 有关菜单与框架void setPosCompare(short x, short y){assert(x >= 0);assert(y >= 0);_compare_x = x;_compare_y = y;_menu.setPos(_menu._x + x, _menu._y + y);}void setAndCheckPos(int x, int y){_frame.setPos(x, y);_menu.setPos(x, y);checkPosFrameWithMenu();}void show(){_menu.show();_frame.frameShow();}void clean(){_menu.clean();_frame.frameClean();}public: // 只关于菜单的void setMaxSpaceOper(){_menu.setMaxSpaceOper();}void setSameSpaceOperWithBack(){_menu.setSameSpaceOperWithBack();}void setMenuButton(int rowPos, int colPos, PFUNC customize){_menu.setWay(rowPos, colPos, customize);}void setOperateSpace(int rowPos, int colPos, int front, int back){_menu.setOperateSapce(rowPos, colPos, front, back);}void setOperateColor(int rowPos, int colPos, int colorNum, bool strength = false){_menu.setOperateColor(rowPos, colPos, colorNum, strength);}void operateMode(bool Yes = false){_menu.operateMode(Yes);}int operateWay(int way, int optionX = 1, int optionY = 1){int info = 0;if (way == keyboard){info = _menu.operateKeyboardStart(optionX, optionY);}else if (way == mouse){info = _menu.operateMouseStart();}return info;}//void operateMouseStart()//{// _menu.operateMouseStart();//}//void operateKeyboardStart(int posX = 0, int posY = 0)//{// _menu.operateKeyboardStart(posX, posY);//}void setMenuRowSpace(int row){_menu.setRowSpace(row);}void setMenuBackgroundSpace(int rowPos, int colPos, int front, int back){_menu.setBackgroundSpace(rowPos, colPos, front, back);}void setMenuCharSpace(int rowPos, int colPos, int front, int back){_menu.setCharSpace(rowPos, colPos, front, back);}void setMenuBackgroundColor(int rowPos, int colPos, int colorNum, int strength = false){_menu.setBackgroundColor(rowPos, colPos, colorNum, strength);}void setMenuCharColor(int rowPos, int colPos, int colorNum, int strength = false){_menu.setCharColor(rowPos, colPos, colorNum, strength);}void setMenuColor(int rowPos, int colPos, int charColor, bool charStrength, int backgroundColor = 0, bool backgroundStrength = false){_menu.setColor(rowPos, colPos, charColor, charStrength, backgroundColor, backgroundStrength);}void setMenuOption(int rowPos, int colPos, const std::string& str1, short front = 1, short back = 1){_menu.setOption(rowPos, colPos, str1, front, back);}public: // 只关于框架的void setFrameSide(CHAR up, CHAR down, CHAR left , CHAR right){_frame.setSide(up, down, left, right);checkPosFrameWithMenu();}void setFrameCorner(CHAR top_left, CHAR bottom_left, CHAR top_right, CHAR bottom_right){_frame.setCorner(top_left, bottom_left, top_right, bottom_right);checkPosFrameWithMenu();}void setFrameNumWord(int number){_frame.numWord(number);}void setFrameWord(int pos, STRING str1, signed char direction, short distance){_frame.setWord(pos, str1, direction, distance);}void setFrameRecallWord(int pos){_frame.recallWord(pos);}protected:void checkPosFrameWithMenu(){if (_frame._the_char._x != _menu._x && _frame._the_char._y != _menu._y){return;}short up = 0;short down = 0;short left = 0;short right = 0;if (_frame._the_char._up != 0){up = 1;}if (_frame._the_char._left != 0){left = sizeof(CHAR);}if (_frame._the_char._down != 0){down = 1;}if (_frame._the_char._right != 0){right = 1;}_menu.setPos(_frame._the_char._x + left + _compare_x, _frame._the_char._y + up + _compare_y);}protected:FRAME _frame;MENU _menu;short _compare_x = 0;short _compare_y = 0;bool _staticInit = false;};typedef console_screen_menu<int(*)(), console_screen_menu_operate<int(*)()>, frame, signed char, const char*> menu;typedef console_screen_menu<int(*)(), console_screen_menu_operate<int(*)()>, wframe, wchar_t, const wchar_t*> wmenu;
}
text
console_screen_text_base.h
#pragma once#include <vector>
#include <utility>
#include <cassert>
#include <iostream>namespace my
{template<class STRING, class CH>class console_screen_text_base{template<class TEXTCHAR, class FRAME, class STRING, class CHAR>friend class console_screen_text;public:console_screen_text_base(short x, short y, short high = 10, short wide = 10, int textNum = 1):_text_num(textNum, std::pair<STRING, short>(nullptr, 0)),_x(x),_y(y),_high(high),_wide(wide){assert(textNum > 0);assert(high > 0 && wide > 0);assert(x >= 0 && y >= 0);}void setText(int theTextRank, STRING theText, short frontDistance){assert(theTextRank > 0);assert(theText != nullptr && frontDistance >= 0);_text_num[theTextRank - 1] = { theText, frontDistance };}void setRowSpace(int row){assert(row >= 0);_row_space = row;}void setHideAndWide(int high, int wide){assert(high > 0 && wide > 0);_high = high;_wide = wide;}void showNoCheck(){if (sizeof(CH) == sizeof(signed char)){textShowClean((void(*)(STRING))&getCout, true);}else{textShowClean((void(*)(STRING)) & getWcout, true);}}void cleanNoCheck(){if (sizeof(CH) == sizeof(signed char)){textShowClean((void(*)(STRING)) & getCout, false);}else{textShowClean((void(*)(STRING)) & getWcout, false);}}void cleanAndCheck(){if (sizeof(CH) == sizeof(signed char)){textShowCleanAndCheck((void(*)(CH)) & getCoutC, false);}else{textShowCleanAndCheck((void(*)(CH)) & getWcoutC, false);}}void showAndCheck(){if (sizeof(CH) == sizeof(signed char)){textShowCleanAndCheck((void(*)(CH)) & getCoutC, true);}else{textShowCleanAndCheck((void(*)(CH)) & getWcoutC, true);}}void setPos(short x, short y){assert(x >= 0 && y >= 0);_x = x;_y = y;}protected://文本长度受宽度限制,过长会换行void textShowCleanAndCheck(void(*outfuncString)(CH), bool isShow){int countPosY = 0;int wideLine = _wide;if (sizeof(CH) == 2){wideLine /= 2;}for (int i = 0; i < _text_num.size(); ++i){if (i != 0){countPosY += _row_space;}if (_text_num[i].first == nullptr){return;}int len = theStrlen(_text_num[i].first);int j = 0;int printIndex = 0;if (sizeof(CH) == 1){printIndex = _text_num[i].second;}else{printIndex = _text_num[i].second % 2;printIndex = _text_num[i].second / 2;}SetPos(_x + _text_num[i].second, _y + i + countPosY);while (j < wideLine - printIndex){if (isShow == true){outfuncString(_text_num[i].first[j]);}else{CH blank = 0;if (sizeof(CH) == 2){blank = L' ';outfuncString(blank);outfuncString(blank);}else{blank = ' ';outfuncString(blank);}}++j;}++countPosY;while (printIndex < len){SetPos(_x, _y + i + countPosY);printIndex = j;int maxSize = wideLine + printIndex;if (maxSize > len){maxSize = len;}while (j < maxSize){if (isShow == true){outfuncString(_text_num[i].first[j]);}else{CH blank = 0;if (sizeof(CH) == 2){blank = L' ';outfuncString(blank);outfuncString(blank);}else{blank = ' ';outfuncString(blank);}}++j;}if (j < len){++countPosY;}}}}void textShowClean(void(*outfuncString)(STRING), bool isShow){int countPosY = 0;for (int i = 0; i < _text_num.size(); ++i){if (i != 0){countPosY += _row_space;}SetPos(_x + _text_num[i].second, _y + i + countPosY);if (_text_num[i].first == nullptr){return;}if (isShow == true){outfuncString(_text_num[i].first);}else{int len = theStrlen(_text_num[i].first);if (sizeof(CH) == 1){std::cout << std::string(len, ' ');}else{std::wcout << std::wstring(len * 2, L' ');}}}}static void getWcout(STRING str1){std::wcout << str1;}static void getCout(STRING str1){std::cout << str1;}static void getWcoutC(CH ch){std::wcout << ch;}static void getCoutC(CH ch){std::cout << ch;}protected:std::vector<std::pair<STRING, short>> _text_num; // 文本存储short _row_space = 0; // 行距short _x;short _y;short _high;short _wide; typedef size_t(*p_T_char)(STRING);p_T_char theStrlen = sizeof(CH) == sizeof(signed char) ? (p_T_char)&strlen : (p_T_char)&wcslen;};typedef console_screen_text_base<const char*, signed char> text_base;typedef console_screen_text_base<const wchar_t*, wchar_t> wtext_base;}
console_screen_text.h
#pragma once#include "console_screen_frame.h"
#include "console_screen_text_base.h"namespace my
{template<class TEXTCHAR, class FRAME, class STRING, class CHAR>class console_screen_text{public:console_screen_text(short x, short y, short high = 10, short wide = 20, int textNum = 1):_text(x, y, high, wide, textNum), _frame(x, y, high, wide){;}public: // 静态准备void staticInit(bool yes = true){_staticInit = yes;}bool alreadyStaticInit(){return _staticInit;}public: // 有关文本与框架void setPosCompare(short x, short y){assert(x >= 0);assert(y >= 0);_compare_x = x;_compare_y = y;setTextPos(_text._x + x, _text._y + y);}void checkPosFrameWithText(){if (_frame._the_char._x != _text._x && _frame._the_char._y != _text._y){return;}short up = 0;short down = 0;short left = 0;short right = 0;if (_frame._the_char._up != 0){up = 1;}if (_frame._the_char._left != 0){left = sizeof(CHAR);}if (_frame._the_char._down != 0){down = 1;}if (_frame._the_char._right != 0){right = 1;}setTextPos(_frame._the_char._x + left + _compare_x, _frame._the_char._y + up + _compare_y);_text._high = _frame._the_char._high - up * 2;_text._wide = _frame._the_char._wide - left * 2;}void setAndCheckPos(int x, int y){_frame.setPos(x, y);_text.setPos(x, y);checkPosFrameWithText();}void show(){_frame.frameShow();_text.showNoCheck();}void showAndCheck(){_frame.frameShow();_text.showAndCheck();}void clean(){_frame.frameClean();_text.cleanNoCheck();}void cleanAndCheck(){_frame.frameClean();_text.cleanAndCheck();}public: // 只关于文本的void setTextPos(short x, short y){_text.setPos(x, y);}//void showAndCheck()//{// _text.showAndCheck();//}//void showButNoCheck()//{// _text.showButNoCheck();//}void setHideAndWide(int high, int wide){_text.setRowSpace(high, wide);}void setRowSpace(int row){_text.setRowSpace(row);}void setText(int theTextRank, STRING text, short frontDistance){_text.setText(theTextRank, text, frontDistance);}public: // 只关于框架的void setFrameSide(CHAR up, CHAR down, CHAR left, CHAR right){_frame.setSide(up, down, left, right);checkPosFrameWithText();}void setFrameCorner(CHAR top_left, CHAR bottom_left, CHAR top_right, CHAR bottom_right){_frame.setCorner(top_left, bottom_left, top_right, bottom_right);checkPosFrameWithText();}void setFrameNumWord(int number){_frame.numWord(number);}void setFrameWord(int pos, STRING str1, signed char direction, short distance){_frame.setWord(pos, str1, direction, distance);}void setFrameRecallWord(int pos){_frame.recallWord(pos);}protected:TEXTCHAR _text;FRAME _frame;short _compare_x = 0;short _compare_y = 0;bool _staticInit = false;};typedef console_screen_text<text_base, frame, const char*, signed char> text;typedef console_screen_text<wtext_base, wframe, const wchar_t*, wchar_t> wtext;}
四、代码参考
后续可能会出一份使用菜单库的博客,这里只给一个菜单供大家参考。
#include "console_screen_menu.h"
#include <iostream>int isQuit()
{return 1;
}int main()
{std::wcout.imbue(std::locale("zh_CN"));my::HideCursor();static my::wmenu isATest(2, 1, 5, 10, 2, 1, true);if (isATest.alreadyStaticInit() == false){isATest.setMenuOption(1, 1, "开始", 0, 0);isATest.setMenuOption(2, 1, "结束", 0, 0);isATest.setFrameSide(L'□', L'■', L'○', L'●');isATest.setFrameCorner(L'△', L'▲', L'▽', L'▼');isATest.setMenuBackgroundSpace(1, 1, 0, 2);isATest.setMenuBackgroundSpace(2, 1, 0, 2);isATest.setOperateSpace(1, 1, 2, 0);isATest.setOperateSpace(2, 1, 2, 0);isATest.setMenuButton(2, 1, isQuit);isATest.staticInit(true);}int operWay = 1;isATest.show();if (operWay == 1){isATest.operateWay(my::keyboard);}else{isATest.operateWay(my::mouse);}return 0;
}
相关文章:

Windows C++控制台菜单库开发与源码展示
Windows C控制台菜单库 声明:演示视频:一、前言二、具体框架三、源码展示console_screen_set.hframeconsole_screen_frame_base.hconsole_screen_frame_char.hconsole_screen_frame_wchar_t.hconsole_screen_frame.h menuconsole_screen_menu_base.hcons…...

ARM——驱动——Linux启动流程和Linux启动
一、flash存储器 lash存储器,全称为Flash EEPROM Memory,又名闪存,是一种长寿命的非易失性存储器。它能够在断电情况下保持所存储的数据信息,因此非常适合用于存储需要持久保存的数据。Flash存储器的数据删除不是以单个的字节为单…...

Docker和虚拟机的区别详细讲解
Docker 和虚拟机(VM)是现代 IT 基础设施中常见的技术,它们都用于在单一硬件上运行多个操作环境,但它们的工作原理、性能、资源利用和使用场景存在显著差异。以下是对 Docker 和虚拟机区别的详细讲解。 一、基础概念 1. Docker …...

leetcode_68. 文本左右对齐
68. 文本左右对齐 题目描述:给定一个单词数组 words 和一个长度 maxWidth ,重新排版单词,使其成为每行恰好有 maxWidth 个字符,且左右两端对齐的文本。 你应该使用 “贪心算法” 来放置给定的单词;也就是说,…...

python探索分形和混沌
简单产生复杂,混沌孕育秩序 0. 引言 a. 分形 fractal 【也叫碎形】 分形是一种具有自相似性和复杂结构的几何图形。在分形结构中,无论放大多少次,局部的结构特征都与整体结构相似。这种特性在自然界中广泛存在,比如树木枝干、山…...

LeetCode77 组合
前言 题目: 77. 组合 文档: 代码随想录——组合 编程语言: C 解题状态: 没尝试出来 思路 经典的组合问题,可以考虑使用回溯法。使用回溯法时可以根据回溯法的模板来考虑如何解决。 代码 回溯法 class Solution { p…...

C#:Bitmap类使用方法—第1讲
首先看一下Bitmap定义:封装 GDI 位图,此位图由图形图像及其属性的像素数据组成。 Bitmap 是用于处理由像素数据定义的图像的对象。 下面介绍一下使用的例子: Bitmap image1; private void Button1_Click(System.Object sender, System.Eve…...

PaddleNLP 3.0 支持大语言模型开发
huggingface不支持模型并行。张量并行,不满足大规模预训练的需求。 1、组网部分 2、数据流 3、训练器 4、异步高效的模型存储...

32次8.21(学习playbook-roles,脚本创建数据库和表,mycat读写分离)
1.roles目录介绍 files:⽤来存放由copy模块或script模块调⽤的⽂件。 tasks:⾄少有⼀个main.yml⽂件,定义各tasks。 handlers:有⼀个main.yml⽂件,定义各handlers。 templates:⽤来存放jinjia2模板。 vars:…...

I2C通信协议(软件I2C和硬件I2C)
相比于之前学的异步全双工且需要两条通信线的串口通信,I2C则为同步半双工,仅需要一条通信线,全双工与半双工区别如下: 全双工(Full Duplex)半双工(Half Duplex)数据传输方式同时双向…...

Linux入门——08 进程间通讯——管道
1.进程间通讯 1.1什么是通讯 进程具有独立性(每个进程都有自己的PCB,独立地址空间,页表)但是要进行进程的通信,通信的成本一定不低,打破了独立性 进程间通信目的 数据传输:一个进程需要将它的数据发送给…...

深入探讨SD NAND的SD模式与SPI模式初始化
在嵌入式系统和存储解决方案中,SD NAND的广泛应用是显而易见的。CS创世推出的SD NAND支持SD模式和SPI模式,这两种模式在功能和实现上各有优劣。在本文中,我们将深入探讨这两种模式的初始化过程,并比较它们在不同应用场景下的优劣&…...

【jvm】栈和堆的区别
目录 1. 用途2. 线程共享性3. 内存分配和回收4. 生命周期5. 性能特点 1. 用途 1.堆:主要用于存储对象实例和数组。在Java中,所有通过new关键字创建的对象都会被分配到堆上。堆是一个大的内存池,用于存储所有的Java对象,包括实例变…...

智能的意义是降低世界的不确定性
世界充满着不确定性,而智能天生就追求一定的确定性,因为不确定性会危及智能的生存。智能本身是一种有序、相对确定的结构产生的,虽然也有一定的不确定性,而且这些不确定性有利于智能的进化,但是,相对而言&a…...

python实现指数平滑法进行时间序列预测
python实现指数平滑法进行时间序列预测 一、指数平滑法定义 1、指数平滑法是一种常用的时间序列预测算法,有一次、二次和三次平滑,通过加权系数来调整历史数据权重; 2、主要思想是:预测值是以前观测值的加权和,且对不同的数据给予不同的权数,新数据给予较大的权数,旧数…...

linux文件——用户缓冲区——概念深度探索、IO模拟实现
前言:本篇文章主要讲解文件缓冲区。 讲解的方式是通过抛出问题, 然后通过分析问题, 将缓冲区的概念与原理一步一步地讲解。同时, 本节内容在最后一部分还会带友友们模拟实现一下c语言的printf, fprintf接口,…...

Hive3:常用查询语句整理
一、数据准备 建库 CREATE DATABASE itheima; USE itheima;订单表元数据 1 1000000 100058 6 -1 509.52 0.00 28155.40 499.33 0 0 lisi shanghai 157 2019-06-22 17:28:15 2019-06-22 17:28:15 1 2 5000000 100061 72 -1 503.86 0.00 38548.00 503.86 1 0 zhangsan shangha…...

Ubuntu下载安装教程|Ubuntu最新长期支持(LTS)版本24.04 LTS下载安装
安装Ubuntu Ubuntu最新长期支持(LTS)版本24.04 LTS Ubuntu 24.04 LTS | 概览 Ubuntu长期支持(LTS)版本,LTS意为“长期支持”,一般为5年。LTS版本将提供免费安全和维护更新至 2029年4月。 Ubuntu 24.04 LTS(代号“Noble Numbat”,…...

通知:《自然语言及语音处理设计开发工程师》即将开课!
自然语言及语音处理设计开发工程师:未来职业的黄金选择 下面我们来看看证书颁发的背景: 为进一步贯彻落实中共中央印发《关于深化人才发展体制机制改革的意见》和国务院印发《关于“十四五”数字经济发展规划》等有关工作的部署要求,深入实…...

Vim youcompleteme Windows 安装保姆级教程
不说废话。 准备 检查 Vim 的 Python 配置 安装好 vim 和 python 后(python 必须 ≥ \ge ≥ 3.6),在 cmd 下运行 vim --version会弹出以下窗口。 如果发现 python/dyn 和 python3/dyn 都是 - (我不知道只有前者是 能不能运行…...

港迪技术IPO提交注册,拟募资6.56亿元
武汉港迪技术股份有限公司(下称“港迪技术”)拟在创业板IPO上市,并于近期在深交所提交招股书(注册稿),进入提交注册阶段。 港迪技术IPO招股书(注册稿)显示,公司是一家专…...

retinaface在ubuntu20.04(wsl2)下使用tensorrt(c++)部署
1. 参考博客: 1. Retinaface Tensorrt Python/C部署:https://blog.csdn.net/weixin_45747759/article/details/124534079 2. B站视频教程:https://www.bilibili.com/video/BV1Nv4y1K727/ 3. Retinaface_…...

vue打包设置 自定义的NODE_ENV
默认NODE_ENV 自定义process.env.NODE_ENV的值_process.node.env的值-CSDN博客 NODE_ENV开发环境下:NODE_ENVdevelopment(默认) 生产环境下:NODE_ENVproduction(默认) NODE_ENV 除了默认的 development 和 production 以外,确实可以自定义…...

python爬虫521
爬虫521 记录 记录 最近想学爬虫,尝试爬取自己账号下的文章标题做个词云 csdn有反爬机制 原理我就不说啦 大家都写了 看到大家结果是加cookie 但是我加了还是521报错 尝试再加了referer 就成功了(╹▽╹) import matplotlib import requests from wordcloud impor…...

CSS中flex:1是什么属性
flex: 1 是 CSS 中的一个简写属性,用于设置 Flex 项目的灵活伸缩比例(flex-grow)、收缩比例(flex-shrink)以及基础大小(flex-basis)。具体来说,flex: 1 实际上是以下三个属性的简写&…...

网络硬件升级指南:提升性能的策略与实践
随着企业对网络依赖程度的增加,网络性能的提升已成为信息技术部门的首要任务。本文将探讨如何通过升级网络硬件来提高网络性能,包括选择正确的硬件、实施升级策略和考虑未来网络的可扩展性。 一、网络性能的重要性 在数字化时代,网络是企业…...

XSS-过滤特殊符号的正则绕过
目录 靶场练习地址:https://xss.pwnfunction.com/ 题目源码: 代码分析: 方法一:匿名函数 方法二:使用eval函数绕过限制 示例: 方法三:利用hash绕过 靶场练习地址:https://xs…...

CocosCreator3.8 IOS 构建插屏无法去除的解决方案
CocosCreator3.8 IOS 构建插屏无法去除的解决方案 在实际项目开发过程中,我们通常无需CocosCreator 自带的插屏,一般采用自定义加载页面。 然后在构建IOS 项目时,启用(禁用)插屏无法操作,如下图所示&#…...

Linux软件编程---数据库
目录 一、数据库 1.1.概念 1.2.类型 1.关系型数据库 2.非关系型数据库 1.3.SQL语言 1.4.如何在Linux安装sqlite数据库 1.确保虚拟机可以上网 2.配置apt-get工具集合 3.安装sqlite数据库 1.5.sqlite3 1.创建数据库 2.查看数据表 3.退出数据库 4.SQL语句 二、数…...

Spring 源码解读专栏:从零到一深度掌握 Spring 框架
前言 Spring 是 Java 世界中无可争议的王者框架,它以其灵活、轻量、强大而著称,成为企业级开发的首选工具。然而,很多开发者在使用 Spring 时,往往只停留在会用的层面,对于其内部实现和设计原理知之甚少。本专栏旨在通…...