上一篇写的是关于控制台屏幕缓冲区滚动机制的剖析,费了我老鼻子劲。平时觉得非常简单的知识点,等落笔成文时,才发现非常不容易。找遍全文,都是挂一漏万,没有系统讲解的。微软的MSDN。。。呵呵,大家懂的都懂。新手看不懂,老手不需要看,就是个工具书。
最后虽然写成了,但是非常不满意,本来这个windows控制台的主题,本意是想写的好玩、轻松、有趣。因为主要是面向c和c++的初学者,能让平时枯燥无比的控制台,也能玩出很多花样,没想到写到第六期,竟然越来越复杂,越来越面目可憎。
今天一定要重新开始,写点简单又有意思的小技巧,这样学起来也不累。
前面也陆陆续续的介绍了窗口操作的一些技巧,但是最重要的却遗漏了。就是每次控制台程序启动时,窗口在屏幕上的位置好像都出现过,但是就是没有居中过。特别是对一些强迫症,或者完美主义者来说,是无法接收的。。。
让窗口居中有很多办法。我们先来看看如何移动窗口的。下面是一段把控制台从屏幕上一个位置移动到另一个位置的代码:
#include <windows.h>
#include <stdio.h>
#include <stdlib.h>
int main(){
HWND hwnd=GetConsoleWindow();
RECT rect;
GetWindowRect(hwnd,&rect);
int newX,newY,width,height;
width=rect.right - rect.left + 1;
height=rect.bottom - rect.top + 1;
newX=300,newY=300;
getchar();
MoveWindow(hwnd,newX,newY,width,height,FALSE);
getchar();
return 0;
}
下面是程序运行后效果截图:
图1
然后再点击回车键,窗口被改变位置:
图2
程序比较简单,用到了这样几个函数:
HWND GetConsoleWindow(void);
见名知意,得到当前控制台程序的窗口句柄,返回值是控制台所使用的窗口句柄。
HWND,是Handle Window的缩写,H是handle,句柄的缩写,句柄的概念我们已经介绍多次,初学者就理解为类似指针,用以唯一表示一个对象的标识符即可。WND是window的缩写,表示“窗口对象”,windows程序,就是由一个个“窗口”组成的程序。
实际上HWND就是HANDLE,用HWND表示,就是强调这是一个窗口对象句柄。看看定义便可以知道:
typedef HANDLE HWND;
BOOL GetWindowRect(HWND hWnd,LPRECT lpRect);
见名知意,得到窗口对象的矩形值,返回值为TRUE,表示获取成功。HWND是一个输入参数,绑定一个窗口对象。
第二个参数是一个输出型参数,LPRECT类型中的LP,表示指针,RECT表示一个结构体类型,组合起来LPRECT就是一个指向RECT结构体类型的指针。
RECT结构体和之前文章中讲解的SMALL_RECT类型类似,区别在于成员变量是LONG类型。RECT结构体定义如下:
typedef struct tagRECT {
LONG left;
LONG top;
LONG right;
LONG bottom;
} RECT;
通过这个函数可以获取当前控制台窗口的左上角和右下角坐标,这个坐标不是之前文章中说的坐标是相对于屏幕缓冲区的相对位置的坐标,此处是相对于显示器屏幕左上角(0,0)的相对位置的坐标(假定不是子窗口),这样就可以计算出当前窗口的矩形面积的宽width和高height,移动窗体时需要用到。
移动窗体windows提供了一个MoveWindow函数,函数原型如下:
BOOL MoveWindow(HWND hWnd, int X,int Y, int nWidth, int nHeight, BOOL bRepaint);
返回值为TRUE则执行成功,传入一个窗体句柄(HWND类型,尽量不要传入HANDEL类型),X和Y表示要移动到的新位置的左上角的坐标。(之前已经说过X是横坐标,Y是纵坐标,计算机系统以左上角为坐标原点)。
如果在移动窗体的过程中,保持窗体大小不变,那么就要用GetWindowRect函数获取窗体的顶点坐标,并计算出宽和高,然后传入到对应的参数。如果需要改变窗体的大小,可以直接填入新的宽和高。
最后一个参数一般都默认为FALSE,因为还没学到窗体重绘,暂时不展开讲解。
总结一下,首先通过GetConsoleWindow()函数获得当前控制台窗口的HWND窗体句柄值, 通过GetWindowRect函数,获得控制台窗口在屏幕上所占据的矩形面积的宽和高,然后通过MoveWindow函数移动窗体到新的位置。
下面的例子演示了窗体在移动过程中同事调整尺寸的效果:
#include <windows.h>
#include <stdio.h>
#include <stdlib.h>
int main(){
HWND hwnd=GetConsoleWindow();
RECT rect;
int newX,newY,width,height;
newX=300,newY=300;
width=500;
height=350;
MoveWindow(hwnd,newX,newY,width,height,FALSE);
getchar();
return 0;
}
程序运行的效果如图:
图3
控制台程序运行时,自动调整好窗口的尺寸和位置。
有了前面移动窗口的基础知识,再让窗口居中就非常简单了。
基本思路:窗口的宽度和高度的中心点,一定也是屏幕的宽度和高度的中心点。所以只需要知道屏幕的宽度和高度,然后求出他们的1/2的值,其实就是窗口的宽高的中心点。
实现代码如下:
#include <windows.h>
#include <stdio.h>
#include <stdlib.h>
int main(){
HWND hwnd=GetConsoleWindow();
RECT rect;
GetWindowRect(hwnd,&rect);
int newX,newY,width,height;
width=rect.right - rect.left + 1;
height=rect.bottom - rect.top + 1;
int screen_width=GetSystemMetrics(SM_CXSCREEN);
int screen_height=GetSystemMetrics(SM_CYSCREEN);
newX=(screen_width - width)/2;
newY=(screen_height - height) /2;
MoveWindow(hwnd,newX,newY,width,height,FALSE);
getchar();
return 0;
}
程序运行的效果如下:
图4
这个程序中,用到了一个很重要的GetSystemMetrics函数。Metrics,指标、配置,System Metrics,即系统相关的指标,配置等参数。函数原型如下:
int GetSystemMetrics( [in] int nIndex);
传入的参数代表不同功能的枚举常量,大部分枚举常量都是与某个图形对象的宽度、高度、粗细有关。下面列举了部分枚举常量,全部的详细信息从MSDN都可以查阅到。
SM_CMONITORS 80
桌面上的显示器数量。
SM_CMOUSEBUTTONS43
鼠标上的按钮数,如果未安装鼠标,则为零。
SM_CXFULLSCREEN 16
主显示器上全屏窗口的工作区宽度(以像素为单位)。
SM_CXSCREEN 0
主显示器的屏幕宽度(以像素为单位)。
SM_CYFULLSCREEN 17
主显示器上全屏窗口的工作区高度(以像素为单位)。
SM_CYSCREEN 1
主显示器的屏幕高度(以像素为单位)。
SM_SWAPBUTTON 23
如果鼠标左键和右键的含义互换,则为非零;否则为 0。
下面这个程序是对这个函数的部分枚举常量编写的演示代码:
#include <windows.h>
#include <stdio.h>
#include <stdlib.h>
int main(){
int cnt_monitor=GetSystemMetrics(SM_CMONITORS);
printf("显示器有 %d 台。\n",cnt_monitor);
int cnt_mouse=GetSystemMetrics(SM_CMOUSEBUTTONS);
printf("鼠标有 %d 个按钮。\n",cnt_mouse);
int height_screen_contain_taskbar=GetSystemMetrics(SM_CYSCREEN);
printf("包含任务栏的屏幕高度:%d\n",height_screen_contain_taskbar);
int height_screen_above_taskbar=GetSystemMetrics(SM_CYFULLSCREEN);
printf("任务栏上面屏幕高度:%d\n",height_screen_above_taskbar);
int width_full_screen=GetSystemMetrics(SM_CXFULLSCREEN);
printf("屏幕宽度full mode:%d\n",width_full_screen);
int width_screen=GetSystemMetrics(SM_CXSCREEN);
printf("屏幕宽度:%d\n",width_screen);
int swap_mouse_btn=GetSystemMetrics(SM_SWAPBUTTON);
if(swap_mouse_btn)
printf("鼠标按钮功能被互换。\n");
else{
printf("鼠标按钮功能正常。\n");
}
getchar();
return 0;
}
程序运行截图如下:
图5
注意,运行结果中说有2台显示期,不是指打开的2台显示器,而是必须如下图所示,设置为“扩展”模式的显示器。如果选择“复制“模式,则多台显示器也计为1台。
图6
之所以有8个鼠标按钮,是因为无线鼠标、触控板、ThinkPad上的红点加起来一共有8个按钮。
SM_CYSCREEN,表示显示器整个屏幕的垂直高度,CYFULLSCREEN,表示屏幕中未遮挡区域的垂直高度,如果底部有任务栏,那么任务栏就属于遮挡屏幕的区域,它的高度要被扣除,在我的屏幕上,底部任务栏高度=960 - 897 (像素)。
SM_CXFULLSCREEN 和 SM_CXSCREEN ,都是获取屏幕的宽度,区别在于,当任务栏在左侧或右侧显示时,SM_CXFULLSCREEN的屏幕宽度,是不包含任务栏区域的屏幕宽度,而SM_CXSCREEN是整个显示器屏幕区域的大小。如果任务栏在屏幕底部,那么这两个的值是相同的,在我的显示器上都是1707像素。
通过GetSystemMetrics函数获取到了屏幕的高度和宽度后,需要计算出当前矩形窗口居中时,左上角的坐标值,然后通过MoveWindow函数,移动到对应的区域,即可实现“窗体居中”的效果。
有时候,我们需要控制台程序保持运行,但又不显示在屏幕上,就需要用到“窗口隐藏”。通过ShowWindow函数,就可以灵活的控制窗口的隐藏和各种显示方式。函数原型如下:
BOOL ShowWindow(HWND hWnd,int nCmdShow);
第二个参数通过各种枚举常量来设置窗口的显示状态。部分功能的枚举常量如下:
1.使窗口处于激活状态的显示方式:
SW_HIDE 0
隐藏窗口。
SW_NORMAL 1
激活并显示窗口。如果窗口被最小化、最大化或排列,系统会将其恢复到其原始大小和位置。
SW_SHOWMINIMIZED 2
激活窗口并将其显示为最小化窗口。
SW_SHOWMAXIMIZED
SW_MAXIMIZE 3
激活窗口并将其显示为最大化窗口。
SW_SHOW 5
激活窗口并按其当前大小和位置显示窗口。
SW_RESTORE 9
激活并显示窗口。如果窗口被最小化、最大化或排列,系统会将其恢复到其原始大小和位置。
2.显示但不激活窗口的方式:
SW_SHOWNOACTIVATE 4
以最近的大小和位置显示窗口。此值与 SW_SHOWNORMAL 值类似,只是窗口未激活。
SW_MINIMIZE 6
最小化指定的窗口,并按 Z 顺序激活下一个顶级窗口。
SW_SHOWMINNOACTIVE 7
将窗口显示为最小化窗口。此值与 SW_SHOWMINIMIZED 类似,只是窗口未激活。
SW_SHOWNA 8
以窗口的当前大小和位置显示窗口。此值与 SW_SHOW 值类似,只是窗口未激活。
下面是部分显示方式的示例代码:
#include <windows.h>
#include <stdio.h>
#include <stdlib.h>
int main(){
HWND hwnd=GetConsoleWindow();
RECT rect;
GetWindowRect(hwnd,&rect);
int newX,newY,width,height;
width=rect.right - rect.left + 1;
height=rect.bottom - rect.top + 1;
int screen_width=GetSystemMetrics(SM_CXSCREEN);
int screen_height=GetSystemMetrics(SM_CYSCREEN);
newX=(screen_width - width)/2;
newY=(screen_height - height) /2;
MoveWindow(hwnd,newX,newY,width,height,FALSE);
Sleep(500);
ShowWindow(hwnd,SW_HIDE);
Sleep(500);
ShowWindow(hwnd,SW_NORMAL);
Sleep(500);
ShowWindow(hwnd,SW_SHOWMINIMIZED);
Sleep(500);
ShowWindow(hwnd,SW_MAXIMIZE);
Sleep(500);
ShowWindow(hwnd,SW_MINIMIZE);
Sleep(500);
ShowWindow(hwnd,SW_SHOWNOACTIVATE);
Sleep(500);
return 0;
}
因程序界面动态变化,就不截图了。
下面这段代码,演示了控制台程序窗口闪烁的特效:
#include <windows.h>
#include <stdio.h>
#include <stdlib.h>
int main(){
HWND hwnd=GetConsoleWindow();
RECT rect;
GetWindowRect(hwnd,&rect);
int newX,newY,width,height;
width=rect.right - rect.left + 1;
height=rect.bottom - rect.top + 1;
int screen_width=GetSystemMetrics(SM_CXSCREEN);
int screen_height=GetSystemMetrics(SM_CYSCREEN);
newX=(screen_width - width)/2;
newY=(screen_height - height) /2;
MoveWindow(hwnd,newX,newY,width,height,FALSE);
int flag=1;
while(1){
if(flag){
ShowWindow(hwnd,SW_HIDE);
flag=0;
}else{
ShowWindow(hwnd,SW_SHOW);
flag=1;
}
Sleep(200);
}
return 0;
}
窗口闪烁效果如下:
<script src="https://lf3-cdn-tos.bytescm.com/obj/cdn-static-resource/tt_player/tt.player.js?v=20160723"></script>
Sleep函数,是让当前程序执行到此处,暂停规定的毫秒数之后再继续执行下一条指令。参数就是一个具体的数值,代表暂停的毫秒数。建议编译前,一定要把Sleep的毫秒数调大,不然闪烁太快,不容易关闭程序[憨笑][呲牙]
没有什么可总结的,今天的几个用法,非常简单,实验一下即可,如果感兴趣,也可以在MSDN上看更扩展的关联函数功能。
段誉,2024年2月17日,写于合肥。
要让你的Excel表格看起来既专业又整洁?
只需一分钟,就能学会如何让数据在单元格中完美居中。快来掌握这个小技巧,让你的报告和数据展示焕然一新!
在Excel中,居中摆列通常指的是将单元格内容在水平和垂直方向上都居中显示。以下是快速学会如何设置Excel单元格内容居中的步骤:
水平居中
垂直居中
- 如果你想要同时实现水平和垂直居中,可以同时点击“水平居中”和“垂直居中”按钮,或者在“对齐”组中找到一个带有十字标志的按钮,这个按钮代表了同时水平和垂直居中。
水平居中+垂直居中
通过以上步骤,你可以在一分钟内学会如何在Excel中设置单元格内容的居中摆列。
这些操作适用于大多数Excel版本哦
Word文档编辑中,居中对齐是一种常用的排版方式,它可以使文本内容在页面上更加整齐、美观。本文将详细介绍Word居中对齐的快捷键、操作方法以及相关技巧,帮助大家轻松实现高效排版。
一、Word居中对齐快捷键
在Word中,居中对齐的快捷键是“Ctrl + E”。选中需要居中对齐的文本内容,然后按下“Ctrl + E”组合键,即可将文本内容居中对齐。这个快捷键可以大大提高我们的排版效率,特别是在处理大量文本内容时。具体word教程,可以在下图点击打开看。
二、Word中如何快速居中对齐
除了使用快捷键外,我们还可以通过以下步骤快速实现Word中的居中对齐:
这种方法虽然比快捷键稍慢一些,但它更加直观,适合初学者使用。
三、Word文档居中对齐的快捷方式
除了上述两种方法外,我们还可以通过设置段落格式来实现Word文档的居中对齐。具体操作步骤如下:
这种方法虽然相对繁琐一些,但它可以对整个段落进行更加精细的格式设置,满足不同的排版需求。
四、Word居中对齐的键盘快捷键是什么
前面已经提到,Word居中对齐的键盘快捷键是“Ctrl + E”。这个快捷键可以帮助我们快速实现文本内容的居中对齐,提高排版效率。需要注意的是,在使用快捷键之前,我们需要先选中需要居中对齐的文本内容。
五、Word如何实现文本一键居中对齐
除了使用快捷键和菜单选项外,我们还可以通过自定义工具栏来实现Word中文本的一键居中对齐。具体操作步骤如下:
完成上述设置后,我们就可以在工具栏中直接点击“居中对齐”按钮来实现文本内容的一键居中对齐了。这种方法可以根据个人习惯进行自定义设置,提高操作效率。
六、Word居中对齐操作技巧
在使用Word进行居中对齐时,我们可以掌握一些操作技巧来提高排版效率:
七、Word文本居中对齐的快捷键教程总结
本文详细介绍了Word居中对齐的快捷键、操作方法以及相关技巧。通过掌握这些知识和技巧,我们可以轻松实现Word文档的高效排版。无论是初学者还是有一定经验的用户,都可以从本文中获得实用的帮助和指导。希望大家在阅读本文后能够更加熟练地运用Word进行文档编辑和排版工作。
按ctrl+e键
通过上面的方法都可以对齐
*请认真填写需求信息,我们会在24小时内与您取得联系。