如何解除屏蔽切换
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了如何解除屏蔽切换相关的知识,希望对你有一定的参考价值。
在很多软件设计的考试状态下,为防止考生作弊,答题窗体处于最大化状态且禁止任务切换,屏蔽了各种任务切换的热键(如Ctrl+Alt+Del、Alt+Tab、Win+D、Win+M)、禁用了任务栏等,想问下高手们桌面样才能解除这种屏蔽
关于屏蔽系统热键的问题,以前看过很多方法,最好的方法是替换 GINA,但用 vfp 无法实现。这篇文章中的方法可以很容易的修改为几乎所有语言的代码。原理很简单:系统热键(如:ctrl+alt+del, alt+tab, 系统任务栏等)都只会显示在 Windows 的缺省桌面中,所以如果想要使这些东西不出现,最简单的办法就是新建一个桌面(一个全新的桌面,除了背景图片外什么也没有),然后在其中运行它,这样即使你按下系统热键,它也不会在新桌面中显示(它显示在缺省桌面中)。新建和切换桌面只要几个 api 函数即可实现,但切换到新桌面后不能用 run / shellexec 等来启动 exe,因为这些函数只能在缺省桌面中创建新进程,所以需要用到 CreateProcess 这个 api 来创建并启动新进程,它其中的一个结构参数可指定要执行进程所在的桌面。Run 方法接收两个参数,第一个是要执行的完整文件路径及名称,第二个参数【可选】指定等待它运行多长时间后自动返回缺省桌面,缺省将一直等待到你关闭新桌面中的进程为止,下面是示例代码:1,2,m.oDesktop = NEWOBJECT( 'NewDesktop' )
3,IF ( 'O' == VARTYPE( m.oDesktop )) AND !ISNULL( m.oDesktop )
4, m.cFile = GETFILE( 'exe', '文件名(&N):', '运行(&R)', 0, '请选择要在新桌面中运行的程序' )
5, m.oDesktop.Run( m.cFile )
6,ENDIF
7,m.oDesktop = NULL 8,DEFINE CLASS NewDesktop AS Custom
9, HIDDEN hOldDesktop
10, hOldDesktop = 0
11, HIDDEN hOldInput
12, hOldInput = 0
13, HIDDEN hNewDesktop
14, hNewDesktop = 0
15, HIDDEN pcNewDesktop
16, pcNewDesktop = 0
17, HIDDEN NewDesktopName
18, NewDesktopName = ('desktop' +SYS(2015))
19, HIDDEN ErrMsg
20, ErrMsg = ''
21, Name = 'NewDesktop' 22, HIDDEN PROCEDURE api_decl
23, DECLARE Long GetThreadDesktop IN WIN32API Long dwThreadId
24, DECLARE Long OpenInputDesktop IN WIN32API ;
25, Long dwFlags, Long fInherit, Long dwDesiredAccess
26, DECLARE Long CreateDesktop IN WIN32API ;
27, String lpszDesktop, Long lpszDevice, Long pDevmode, ;
28, Long dwFlags, Long dwDesiredAccess, Long lpsa
29, DECLARE Long SetThreadDesktop IN WIN32API Long hDesktop
30, DECLARE Long SwitchDesktop IN WIN32API Long hDesktop
31, DECLARE Long CloseDesktop IN WIN32API Long hDesktop 32, DECLARE Long CreateProcess IN WIN32API ;
33, String pszAppName, String pszCmdLine, ;
34, Long lpProcessAttr, Long lpThreadAttr, ;
35, Long bInheritHandles, Long dwCreationFlags, ;
36, Long lpEnvironment, String pszCurDir, ;
37, String lpStartupInfo, String @ lpProcInfo
38, DECLARE Long CloseHandle IN WIN32API Long hObject
39, DECLARE Long WaitForSingleObject IN WIN32API ;
40, Long hHandle, Long dwMilliseconds 41, DECLARE Long GetProcessHeap IN WIN32API
42, DECLARE Long HeapAlloc IN WIN32API ;
43, Long hHeap, Long dwFlags, Long dwBytes
44, DECLARE Long HeapFree IN WIN32API ;
45, Long hHeap, Long dwFlags, Long lpMem
46, DECLARE Long GetLastError IN WIN32API 47, This.pcNewDesktop = HeapAlloc( GetProcessHeap(), 8, LEN(This.NewDesktopName)+1 )
48, IF ( 0 == This.pcNewDesktop )
49, MESSAGEBOX( '内存分配失败 !', 16, '错误' )
50, ELSE
SYS( 2600, This.pcNewDesktop, LEN(This.NewDesktopName), This.NewDesktopName )
ENDIF
ENDPROC PROCEDURE Run
*!* ------------------------------------------------------------------------
*!* 功能: 在新建桌面中运行指定的程序
*!* 入口: tcExeFile - 要执行的 exe 文件
*!* tiTimeout - 等待执行时间(单位 ms, 0 代表一直等待到它终止并退出)
*!* ------------------------------------------------------------------------
LPARAMETERS tcExeFile, tiTimeout IF ( 'C' != VARTYPE( m.tcExeFile )) OR EMPTY( m.tcExeFile )
RETURN .F.
ENDIF
IF ( PCOUNT() < 2 ) OR ( 'N' != VARTYPE( m.tiTimeout )) OR ( m.tiTimeout <= 0 )
m.tiTimeout = -1
ENDIF This.ErrMsg = ''
IF This.SwitchToNewDesktop()
This.StartProcess( m.tcExeFile, m.tiTimeout )
ENDIF IF !EMPTY( This.ErrMsg )
MESSAGEBOX( This.ErrMsg, 16, '错误' )
ENDIF
ENDPROC HIDDEN PROCEDURE SwitchToNewDesktop
#define DESKTOP_SWITCHDESKTOP 0x0100
#define GENERIC_ALL 0x10000000 *!* 保存当前线程所在的桌面句柄
This.hOldDesktop = GetThreadDesktop( _vfp.ThreadId )
*!* 保存当前用户输入线程的桌面句柄
This.hOldInput = OpenInputDesktop( 0, 0, DESKTOP_SWITCHDESKTOP )
*!* 创建新桌面
This.hNewDesktop = CreateDesktop( This.NewDesktopName, 0, 0, 0, GENERIC_ALL, 0 ) IF ( 0 == This.hNewDesktop )
This.ErrMsg = '创建桌面失败!错误代码: ' + TRANSFORM( GetLastError())
RETURN .F.
ENDIF *!* 切换当前线程到新建桌面中
SetThreadDesktop( This.hNewDesktop )
IF ( 0 == SwitchDesktop( This.hNewDesktop ))
This.ErrMsg = '切换桌面失败!错误代码: ' + TRANSFORM( GetLastError())
RETURN .F.
ENDIF
ENDPROC HIDDEN PROCEDURE StartProcess
LPARAMETERS tcExeFile, tiTimeout
*!* typedef struct _PROCESS_INFORMATION
*!* HANDLE hProcess;
*!* HANDLE hThread;
*!* DWORD dwProcessId;
*!* DWORD dwThreadId;
*!* PROCESS_INFORMATION *!* typedef struct _STARTUPINFO
*!* DWORD cb;
*!* LPTSTR lpReserved;
*!* LPTSTR lpDesktop;
*!* LPTSTR lpTitle;
*!* DWORD dwX;
*!* DWORD dwY;
*!* DWORD dwXSize;
*!* DWORD dwYSize;
*!* DWORD dwXCountChars;
*!* DWORD dwYCountChars;
*!* DWORD dwFillAttribute;
*!* DWORD dwFlags;
*!* WORD wShowWindow;
*!* WORD cbReserved2;
*!* LPBYTE lpReserved2;
*!* HANDLE hStdInput;
*!* HANDLE hStdOutput;
*!* HANDLE hStdError;
*!* STARTUPINFO LOCAL cSI, cPI, hProcess
IF ( m.tiTimeout <= 0 )
m.tiTimeout = -1
ENDIF
m.cSI = BINTOC( 0, 'rs' ) ;
+ BINTOC( This.pcNewDesktop, 'rs' ) + REPLICATE( CHR(0), 14*4 )
m.cSI = BINTOC( LEN( m.cSI )+4, 'rs' ) + m.cSI m.cPI = REPLICATE( CHR(0), 4*4 ) IF ( 0 == CreateProcess( ;
m.tcExeFile, '', 0, 0, 0, 0, 0, NULL, m.cSI, @ m.cPI ))
This.ErrMsg = '在新桌面中创建进程失败! 错误代码: ' + TRANSFORM( GetLastError())
ELSE
m.hProcess = CTOBIN( LEFT( m.cPI, 4 ), 'rs' )
*!* 等待此进程终止
WaitForSingleObject( m.hProcess, m.tiTimeout )
*!* CloseHandle( m.hProcess )
ENDIF
This.ClearUp()
ENDPROC HIDDEN PROCEDURE ClearUp
IF ( 0 != This.hOldInput )
SwitchDesktop( This.hOldInput ) && 切换回默认桌面
This.hOldInput = 0
ENDIF
IF ( 0 != This.hOldDesktop )
SetThreadDesktop( This.hOldDesktop ) && 回复原线程桌面
This.hOldDesktop = 0
ENDIF
IF ( 0 != This.hNewDesktop )
CloseDesktop( This.hNewDesktop ) && 关闭新建的桌面
This.hNewDesktop = 0
ENDIF
ENDPROC PROCEDURE Init
This.api_decl()
ENDPROC PROCEDURE Destroy
IF ( 0 != This.pcNewDesktop )
HeapFree( GetProcessHeap(), 0, This.pcNewDesktop )
This.pcNewDesktop = 0
ENDIF
ENDPROC
ENDDEFINE
进一步的,我们可以检查并限制我们的程序只能在新桌面中运行,这样可以最大程度的保护它的运行不受用户切换任务的干扰。
本文转载: http://blog.csdn.net/dkfdtf/archive/2008/08/05/2768317.aspx 参考技术A 待解决问题 收藏 如何解除屏蔽切换标签:解除 屏蔽,屏蔽,切换 在很多软件设计的考试状态下,为防止考生作弊,答题窗体处于最大化状态且禁止任务切换,屏蔽了各种任务切换的热键(如Ctrl+Alt+Del、Alt+Tab、Win+D、Win+M)、禁用了任务栏等,想问下高手们桌面样才能解除这种屏蔽 参考技术B 除非修改原程序,不然没办法。 参考技术C 可通过组策略进行恢复:在“运行”中键入“gpedit.msc”,启动“组策略”编辑器。在“本地策略”中依次展开“用户配置→管理模板→系统→Ctrl+Alt+Del选项”分支,在右侧窗口中双击“删除任务管理器”策略,在弹出的策略设置对话框中选择“未配置”选项,单击“确定”以后,按“Ctrl+Alt+Del”组合键就可以调出“任务栏管理器”了。 另外快捷键等等都是在组策略里面设置的 由于太多不细说了你可以找下PS:上述策略须在管理员帐户下操作
如何屏蔽Alt+F4
新建文本文档,输入:
[code=BatchFile]@echo off
title 屏蔽/允许 ALT-F4 组合键
cls
set rp=HKLM\\SYSTEM\\CurrentControlSet\\Control\\Keyboard Layout
set rv=Scancode Map
set /p ok=屏蔽或解除ALT-F4组合键 [Y-屏蔽 N-解除]:
if /i %ok%==Y (reg add "%rp%" /v "%rv%" /d 00000000000000000200000038e03e0000000000 /t reg_binary /f&&cls&&echo 屏蔽了ALT-F4组合键,重启计算机生效!)
if /i %ok%==N (reg delete "%rp%" /v "%rv%" /f&&cls&&echo 解除了ALT-F4组合键的屏蔽,重启计算机生效!)
echo.&&echo.&&pause
[/code]
将扩展名改为bat,以管理员方式打开,按照提示操作,重启即可。
--------------------------------------------------------------------------
补充:这是全局禁用,如果是你编的应用里要禁用的话请参考其他回答。
参考技术A 你好,建议你把F4这个键给抠掉应该就可以避免了。 参考技术B 在窗口中注册热键,然后在窗口中接收热键。vc++示例:
在cpp中增加(其中classname,baseclassname 为类名和基类名):
#define ID_WM_HOTKEY (0x1000)
BEGIN_MESSAGE_MAP(classname, baseclassname)
ON_MESSAGE(WM_HOTKEY,OnHotKey)
END_MESSAGE_MAP()
LRESULT classname::OnHotKey(WPARAM wParam,LPARAM lParam)
return 1;
中.h中定义
afx_msg LRESULT OnHotKey(WPARAM wParam,LPARAM lParam);
在create窗口后
RegisterHotKey(m_hWnd,ID_WM_HOTKEY,MOD_ALT,VK_F4);
在destroy窗口前
UnregisterHotKey(m_hWnd,ID_WM_HOTKEY);
搞定。 参考技术C 在HOOK中断定消息的WPARAM和LPARAM就可滤过ALT+F4 参考技术D 这个是屏不掉的,是系统自带的组合建
以上是关于如何解除屏蔽切换的主要内容,如果未能解决你的问题,请参考以下文章