winapi GetAsyncKeyState() does not work as described? - c++

According to microsoft's documentation, GetAsyncKeyState() supposedly
Determines whether a key is up or down at the time the function is called
I've been building a UI automation library and the issue boils down to this
#include <Windows.h>
#include <iostream>
#include <chrono>
#include <thread>
using namespace std;
bool IsKeydownAsync(int key) {
return GetAsyncKeyState(key) & 0x8000;
}
int main(){
while (1) {
if (IsKeydownAsync('A')) {
cout << "triggered" << endl;
}
this_thread::sleep_for(chrono::milliseconds(10));
}
}
So my understanding is that it should not matter if my application is in focus or not, the GetAsyncKeyState() should always return whether the physical keys are up or down at the time of being called.
I have tested this over various applications and for most time it behaves as it is described. However, in some games this behavior breaks and it no longer reports whether the key is up or down. cout << "triggered" << endl doesn't get called when the key is held.
Is there something I overlooked?

It has been a while since I worked with native input in Windows, but from experience the Windows API functions only report key-states that are also reported using the synchronzied Windows API functionality, which is to say the normal application message/event input.
Some older games use previous versions of DirectX and alternative ways to capture input, e.g. using a library called the XInput(2) that has been deprecated since Windows 8.1 / 10. While both polling and events/msgs were supported, the input was caught using the DirectX thread and handled entirely differently compared to the Windows API. The main reason for this is that the OS tries to cater to all manufacturers, where the DirectX API did not specificcally address that issue for input.

Related

Syntax for BluetoothLEDevice::RequestPreferredConnectionParameters()

Using C++/WinRT, Win10, VS2019, SDK 10.0.22621.0, NuGet CppWinRT 2.0.220608.4
I'm trying to get the RequestPreferredConnectionParameters to work. At this point I am wondering if maybe I have the syntax wrong or maybe something else about it that I am not aware of. The MS docs for the function are here and the link to the various parameters are here.
The command line, as I have it, with pubDevice being the BLE device object, is:
BluetoothLEPreferredConnectionParametersRequest rcoConnect = pubDevice.RequestPreferredConnectionParameters(BluetoothLEPreferredConnectionParameters::ThroughputOptimized());
Just to mention, I am able to run
auto statusTest = co_await pubDevice.RequestAccessAsync();
before the RequestPreferredConnectionParameters without problems so, obviously, the device object is good and can be connected to.
What is happening is this. I have a function, OpenDevice(), that opens the device based on the address. If, after getting the device object, I issue the command above while still in the OpenDevice function, the code will not crash but it will immediately jump to the end of the OpenDevice() function bypassing all other lines of code below it and there will be no connection at all after that.
If I run the RequestPreferredConnectionParameters outside of the OpenDevice() function it errors out with a
An unhandled exception was encountered during a user callback and the line referenced is in base.h line 4942 if (result == impl::error_changed_state)
I had assumed that the callback refered to was the Rx Characteristic ValueChanged Callback that is set in OpenDevice(). So I tested by first revoking that callback with
pubRxCharacteristic.ValueChanged(etValueChangeToken);
and then running the RequestPreferredConnectionParameters but I still got the An unhandled exception error.
The only other callback that I have is the BluetoothLEAdvertisementWatcher advert received callback but that was stopped after the device was found.
Can anyone verify that my syntax seems correct and/or have any clue as to what is causing my problems?
EDIT to show more code in a console app------------
#IInspectable
Again for the record:
Using C++/WinRT, Win10, VS2019 - Console App, SDK 10.0.22621.0, NuGet CppWinRT 2.0.220608.4
Pertinent includes in the pch.h file:
// 2022/9/10 -- for WHCAR and apparently GUID
#include <Windows.h>
#include <tchar.h>
#include <winrt\Windows.Foundation.h>
#include <winrt\Windows.Storage.Streams.h>
#include <winrt\Windows.Devices.Bluetooth.h>
#include <winrt\Windows.Devices.Bluetooth.Advertisement.h>
#include <winrt\Windows.Devices.Bluetooth.GenericAttributeProfile.h>
// 2022/9/10
#include <winrt\Windows.Devices.Enumeration.h>
#include <winrt/Windows.Foundation.Collections.h>
Pertinent name spaces at top of Main.cpp:
using namespace winrt;
using namespace Windows::Foundation;
using namespace winrt::Windows::Foundation;
using namespace Windows::Storage::Streams;
using namespace Windows::Devices::Bluetooth;
using namespace Windows::Foundation::Collections;
using namespace Windows::Devices::Bluetooth::Advertisement;
using namespace Windows::Devices::Bluetooth::GenericAttributeProfile;
// 2022/9/10 for RequestConnectionAsync
using namespace Windows::Devices::Enumeration;
I assume that the code to watch for and find the device is not pertinent here. Needless to say the device is found and the address is passed to OpenDevice to create the device object.
Here is the top portion of OpenDevice:
IAsyncAction OpenDevice(unsigned long long deviceAddress)
{
auto device = co_await BluetoothLEDevice::FromBluetoothAddressAsync(deviceAddress);
// 2022/9/10 test code
auto statusTest = co_await device.RequestAccessAsync();
// Allowed, DeniedBySystem, Unspecified
if (statusTest != DeviceAccessStatus::Allowed) {
std::cout << "Access to device is not allowed...." << std::endl;
}
else {
std::cout << "Access to device is allowed...." << std::endl;
}
// Next line ends without error but immediately goes to the end of OpenDevice()
std::cout << "Asking for ThroughputOptimized...." << std::endl;
auto statusConnection = device.RequestPreferredConnectionParameters(BluetoothLEPreferredConnectionParameters::ThroughputOptimized());
std::cout << "Line after Request ThroughputOptimized...." << std::endl;
Beep(500, 500);<br/> // function never gets to this cout or Beep<br/>
// More code follows to get Rx and TxCharacteristics etc.<br/>
} // end OpenDevice
Here is the console output:
Notice the last cout is the line Asking for ThroughputOptimized.
No cout for Line after Request ThroughputOptimized and no Beep.
Trying to locate the TENS device: Waiting for device:
AdvertisementReceived:
LocalName: []
AdvertisementType: [ConnectableUndirected]
BluetoothAddress: [0x300000e59630]
RawSignalStrengthInDBm: [-60] ServiceUUID: [0000fff0-0000-1000-8000-00805f9b34fb] Found TENS Device Main
Service.... TENS device found. Access to device is
allowed.... Asking for ThroughputOptimized....
WinRTBle.exe (process 15576) exited with code -1073740791. Press
any key to close this window .
Barring a problem in syntax or a missing header. the only other thing that I can think of is that it needs Win11. The docs for RequestPreferredConnectionParameters Method say
Windows requirements Device family Windows 11 (introduced in
10.0.22000.0)
Does that mean that regardless of the SDK it needs Win11?
#IInspectable As much as I was dreading this, apparently the answer is that it needs Win11. The console app code mentioned above in the edit to the original question was compiled into an exe. I have Win11 on a VM VirtualBox and I ran that exe on that Win11 and the code continued past the ThroughputOptimized() line in question and finished the rest of the app as expected. So that's ashamed. I don't have Win11 on a real box yet (call me paranoid) but I guess I could bracket the code for the Win11 OS and only run it when a user happens to be running Win11
Always something.......
EDIT 2 ...............................
And the "Always something" comes up immediately. As far as I can tell from what I have been able to find, there is no way to tell if the OS is Win10 or Win11. It was recommended to use RtlGetVersion but that returned 10 for both Win10 and Win11. Another poster suggested to use the File version of the System32 kernal32.dll file but they also both reported major number 10 and minor number 0. The MS docs for adding a version manifest had the UUIDs for both OSs as the same.
This is ridiculous that MS would come up with a function that only runs in Win11 and then not have to ability to tell you which OS you are running in....Jeeeeeeze.....
EDIT 3.........................
Spoke too soon. I was messing around with the console app and forgot that in my MFC app I use the WMI IWbemClassObject Caption property to get the OS.
For Windows 10 I get
Microsoft Windows 10 Pro
and for Win11 I get
Microsoft Windows 11 Home
So apparently that is really the only way to do it.

How do I graph data in c++?

I am trying to make a graph using graphics.h in c++. I was following a tutorial on youtube. It seems that either due to the age of the video (perhaps the syntax has changed slightly?) or a problem on my end; I cannot even get a separate window for my graph to open. I am in completely uncharted waters for me as the limit of my coding knowledge is what you would expect to learn from a first-semester coding class. I am using DEV C++ and am compiling using "TDM-GCC 4.9.2 32-bit Release" (because the 64 bit release gives me an error in "Makefile.win" that scares me) and my program exits with a return value of 3221225477. What am i doing wrong?
#include"graphics.h"
#include<math.h>
#include<conio.h>
#include<iostream>
using namespace std;
int main() {
initwindow(800,600);
int x,y;
line(0,300,getmaxx(),300);
line(400,0,400,getmaxy());
float pi=3.14159;
for(int i=-360;i<=360;i++){
x=(int)400+i;
y=(int)300-sin(i*pi/100)*25;
putpixel(x,y,WHITE);
}
getch();
closegraph();
return 0;
}
According to your issue and exit-code, the return value in hex is 0xC0000005 or STATUS_ACCESS_VIOLATION. But most developers didn't even bother to learn out-dated legacy API and I can not help you to find the exact line (use debugger, it shows you the exact line, still not the reason).
But to answer your question in the title, well, according to what free framework one uses (Qt or XWidget), the method differs, for Qt (which I would recommend) simply override paint-event and use QPainter renderer to show your QPath data.
Don't reinvent the wheel (or render-system in this case), your course and/or book may soon introduce you to one of the mentioned frameworks.

PfCreateInterface returns error 120 (not implemented)

I need to create a simple IP filtering program for Windows; however, I am having problems getting the relevant API call to work. Below is a small example demonstrating how PfCreateInterface fails. It is returning 120 which is the system error code ERROR_CALL_NOT_IMPLEMENTED. I am running the program on Windows 10.
#include <windows.h>
#include <Iphlpapi.h>
#include <Fltdefs.h>
#include <iostream>
#pragma comment(lib, "Iphlpapi.lib")
int main()
{
INTERFACE_HANDLE hInterface;
PFFORWARD_ACTION action = PF_ACTION_FORWARD;
DWORD errorCode = PfCreateInterface(0,
action,
action,
FALSE,
TRUE,
&hInterface);
std::cout << "errorCode = " << errorCode << std::endl;
}
Can somebody explain why it is failing? If I can't use it on Windows 10, do you know what is the alternative API?
Microsoft's documentation is pretty clear:
PfCreateInterface is available for use in the operating systems listed
in the Requirements section.
The Windows versions "listed in the Requirements section" are Windows Server 2003 or Windows 2000 Server.
So this API call is essentially obsolete. The documentation recommends using the Windows Filtering Platform management functions instead.

Sleep() function windows 8 c++

I'm attempting to get the Sleep() function working on a Windows 8 operating system, with c++. So far I haven't found any examples specific to this.
Following from http://msdn.microsoft.com/en-us/library/windows/desktop/ms686298%28v=vs.85%29.aspx i've included the header <Synchapi.h>, though i get "Identifier "Sleep" is undefined". I am able to find the functions SleepConditionVariableCS() and SleepConditionVariableSRW() from Synchapi.h, but not Sleep().
Has anyone managed to use Sleep() on a Windows 8 operating system or know why I am unable to find the function?
You shouldn't be including Synchapi.h directly. Include Windows.h instead.
#include <Windows.h>
int main()
{
Sleep(1000);
return 0;
}
Are you using C++11? If you are you can use:
#include <thread>
template< class Rep, class Period >
void sleep_for( const std::chrono::duration<Rep,Period>& sleep_duration );
Update
The Sleep() function is only available for Desktop Apps. Are you building a formerly known as Metro app? Or an App Store app?
See this article for some work arounds:
http://blogs.msdn.com/b/win8devsupport/archive/2012/11/28/introduce-multi-thread-programming-in-windows-store-apps-part-ii.aspx

How to set progress bar for parallel_invoke?

What I want is how to get the progress data. I can implement the bar whatever I like. And I'm using Visual C++ 2010, so I can use MFC.
Now, I'm writting multithreaded program. And Microsoft already provides PPL lib since VC++ 2010. The Parallel Patterns Library (PPL) provides algorithms that concurrently perform work on collections of data. It's convenient to implement multithreaded app, but I encounter progress bar problem.
How can I set progress bar for parallel_invoke?
The demo code is as follows:
// parallel-invoke-structure.cpp
// compile with: /EHsc
#include <ppl.h>
#include <string>
#include <iostream>
using namespace concurrency;
using namespace std;
// Returns the result of adding a value to itself.
template <typename T>
T twice(const T& t) {
return t + t;
}
int wmain()
{
// Define several values.
int n = 54;
double d = 5.6;
wstring s = L"Hello";
// Call the twice function on each value concurrently.
parallel_invoke(
[&n] { n = twice(n); },
[&d] { d = twice(d); },
[&s] { s = twice(s); }
);
// Print the values to the console.
wcout << n << L' ' << d << L' ' << s << endl;
}
Maybe this is off topic, but I would recommend checking out Cilk instead of PPL.
Here is a course at MIT (from one of the main creators of Cilk) that outlines its pros, cons and specific usage. It's very easy to use and claims to be much more performant than PPL (in case you're concerned about that).
As for your specific question about progress bars, coming up with a percentage is the first task. If you use timers to map which work costs you what (in terms of wall time), you can use that (via a callback from each worker to register work done) to drive the percentage. Once you have your percentage down, hooking it up to a bar (in the shell) or a GUI progress bar is trivial.
Depending on how much work your worker processes do (how granular they are), you may want to consider different methods of instrumentation. If you look at this wikipedia page, it'll outline many types of profiling (statistical, event based, etc.).
One last note: I find that progress bars are difficult to get right. Anyone can make a bar move. But having it accurately represent a true indication of how much time it will take involves a great understanding of what factors are affecting your performance. As is the case with any computer program, your performance can change based on which system your run it on (cpu architecture, IO bandwidth, network bandwidth). So even if you get it predictable on your box, your clients' boxes may be drastically different--so much so that your progress bar doesn't yield good indications anymore.
Hope that helps...