I have a simple color clicker code.
~C::
Loop
{
PixelSearch, Px, Py, 300, 300, 300, 300, 0x91595c, 5, Fast
if errorlevel
{
sleep 20
return
}
else
{
Send, {LButton Down}
Sleep, 250
Send, {LButton Up}
Sleep, 500
}
}
return
When pressing a C, its find a right color and send a click.
But i tired to make it work ONLY when C is pressed and finish color search when C is not pressed.
What have you already tried?
I tried to make this work with:
while KeyIsDown := GetKeyState("c", "P")
or
if KeyIsDown := GetKeyState("c")
But it just come to infinite loop or doesnt work.
Can you have any ideas?
Find a solution:
$F2::
Loop
{
PixelSearch, Px, Py, 300, 300, 300, 300, 0x91595c, 5, Fast
if errorlevel
{
sleep 20
return
}
else
if GetKeyState("C","p")
{
Send, {LButton Down}
Sleep, 250
Send, {LButton Up}
Sleep, 500
}
}
return
Glad to see if you have a better solutions.
If I understand you right, you want to keep the looping going until you release C. If so, you shouldn't return inside the loop, for that will stop it.
$F2::
Loop
{
PixelSearch, Px, Py, 300, 300, 300, 300, 0x91595c, 5, Fast
if errorlevel
{
sleep 20
}
else
if GetKeyState("C","p")
{
Send, {LButton Down}
Sleep, 250
Send, {LButton Up}
Sleep, 500
}
else
break ; C was released: exit the loop, thus exit the thread
}
return
Also, you can keep ~C as the hotkey, and if you really only want to "click", there is no need for a complicated {LButton down} etc.
Suggested code (also more compact):
~c::
while(getKeyState("C","P)) {
PixelSearch, Px, Py, 300, 300, 300, 300, 0x91595c, 5, Fast
if( ! errorLevel ) {
click
sleep, 750
} else {
sleep 20
}
}
return
Related
Feeling stupid somehow as I'm now trying to get a simple interrupt for a thread working in groovy for some hours already.
Somehow following code won't set the 'interrupted' flag in the thread 'name'. Causing the loop to run 'til its end.
Found tons of other questions where usually the check for Thread.currentThread().isInterrupted() was missing. But this is not the case here:
def t = Thread.start('name') {
try {
for (int i = 0; i < 10 && !Thread.currentThread().isInterrupted(); ++i) {
println "$i"
sleep 1000
}
} catch (InterruptedException e) {
println "Catched exception"
Thread.currentThread().interrupt();
}
}
println "Interrupting thread in 1..."
sleep 1000
println "Interrupting thread..."
t.interrupt()
sleep 2000
I get following output
Interrupting thread in 1...
0
Interrupting thread...
1
2
3
4
5
6
7
8
9
Wonder what I miss here / am doing wrong?
Tried also using ExecutorService and calling cancel(true) on the returned Future. Didn't work either.
If you interrupt the thread while sleeping, the sleeping interrupted thread catches the InterruptedException thrown by Thread.sleep and the interrupted status is cleared. So your Thread.currentThread().isInterrupted() always returns false.
You can make your code work if you replace sleep 1000 with Thread.sleep(1000).
TL;DR: Do not use Thread interruption as abort criterion, but use some custom flag instead.
You are not using Thread.sleep() which would throw InterruptedException, but GDKs Object.sleep() which handles and ignores interruptions: http://docs.groovy-lang.org/docs/groovy-2.4.7/html/groovy-jdk/java/lang/Object.html#sleep(long)
Either use Thread.sleep() instead like: (interrupting in the catch block is useless in your case)
def t = Thread.start('name') {
try {
for (int i = 0; i < 10 && !Thread.interrupted(); ++i) {
println i
Thread.sleep 1000
}
} catch (InterruptedException e) {
println "Catched exception"
}
}
println "Interrupting thread in 1..."
sleep 1000
println "Interrupting thread..."
t.interrupt()
Or use the variant of Object.sleep() with a Closure and abort your loop in there, e. g. by throwing InterruptedException like:
def t
t = Thread.start('name') {
try {
for (int i = 0; i < 10 && !Thread.interrupted(); ++i) {
println i
sleep(1000) {
throw new InterruptedException()
}
}
} catch (InterruptedException e) {
println "Catched exception"
}
}
println "Interrupting thread in 1..."
sleep 1000
println "Interrupting thread..."
t.interrupt()
Having solved your confusion, now let me advice not to do what you are trying to do. Interrupting is any no way a good method for usage as abort condition. A sleep or blocking IO can always be interrupted due to various reasons. The much better approach is to make your run-loop check some boolean flag that you toggle to abort the work.
I'm trying to write an ncurses program which adds new windows in response to the user pressing keys. For example, consider the following C++ code:
#include <iostream>
#include "curses.h"
using namespace std;
int main()
{
WINDOW * win = initscr();
start_color();
noecho();
WINDOW * sub = subwin(win, 20, 20, 2, 2);
wborder(sub, 0, 0, 0, 0, 0, 0, 0, 0);
keypad(win, TRUE);
while (true)
{
int c = wgetch(win);
if (c == KEY_DOWN)
{
WINDOW* box = subwin(sub, 2, 2, (rand() % 20) + 2, (rand() % 20) + 2);
wborder(box, 0, 0, 0, 0, 0, 0, 0, 0);
}
else if (c == KEY_UP)
{
wrefresh(sub);
}
}
endwin();
return 0;
}
The user can press the down key to create new windows as many times as they want, but wrefresh will only draw them once. This appears to be related to the call to wgetch, a program that doesn't respond to keys works fine. Calling refresh also causes the problem.
The subwin man page says:
When using this routine, it is necessary to call touchwin or
touchline on orig before calling wrefresh on the subwindow.
Creating a sub-window does not actually change the parent window, so after the first refresh the parent window has not changed, touching the window marks it as changed.
So change:
wrefresh(sub);
to
touchwin(sub);
wrefresh(sub);
It might sound a little strange, but I can't correctly use the Draw_Pixel() and Draw_Line() functions of SDL_Draw.h
I've googled and people state: It's very simple to use, but unfortunately... not for me.
I've written a very simple piece of code but it doesn't show me the pixel, I tried also with a line, but nothing as well.
The simple code is:
#include <SDL.h>
#include "SDL_draw.h"
int main(int argc, char** argv)
{
SDL_Surface* surf;
if(SDL_Init(SDL_INIT_EVERYTHING) < 0) {
return -1;
}
if((surf = SDL_SetVideoMode(WIDTH, HEIGTH, BBP, FLAGS)) == NULL) {
return -1;
}
Uint32 myColor = SDL_MapRGB( surf->format, 255, 25, 23); //this is the red color
Draw_Pixel(surf, 45, 45, myColor);
Draw_Line(surf, 45, 20, 90, 100, myColor);
SDL_Quit();
return 1;
}
The x,y coordinates are just random. I'm trying to see the result with breakpoints in Visual Studio.
Can anyone tell me where I'm mistaking?
You have to update your surface by calling SDL_Flip( SDL_Surface * screen) ;
And add a delay before exiting the program, otherwise you wont see the window.
So I'm learning about sprite programming and we're using allegro. When I run one of the sample programs I get the message: rotatesprite.exe has triggered a breakpoint. This was in visual studio. I can't get allegro to work outside of visual studio
sample program:
#include <allegro.h>
#define WHITE makecol(255,255,255)
int main(void)
{
int x, y;
float angle = 0;
BITMAP *tank;
//initialize program
allegro_init();
install_keyboard();
set_color_depth(32);
set_gfx_mode(GFX_AUTODETECT_WINDOWED, 640, 480, 0, 0);
textout_ex(screen,font,"Rotate: LEFT / RIGHT arrow keys",
0,0,WHITE,0);
//load tank sprite
tank = load_bitmap("C:\Users\Jason\Desktop\module7\tank.bmp", NULL);
//calculate center of screen
//x = SCREEN_W/2 - tank->w/2;
//y = SCREEN_H/2 - tank->h/2;
x=SCREEN_W/2;
y=SCREEN_H/2;
//draw tank at starting location
rotate_sprite(screen, tank, x, y, 0);
//main loop
while(!key[KEY_ESC])
{
//wait for keypress
if (keypressed())
{
//left arrow rotates left
if (key[KEY_LEFT])
{
angle -= 0.1;
if (angle < 0) angle = 256;
rotate_sprite(screen, tank, x, y, itofix(angle));
}
//right arrow rotates right
if (key[KEY_RIGHT])
{
angle += 0.1;
if (angle > 256) angle = 0;
rotate_sprite(screen, tank, x, y, itofix(angle));
}
//display angle
textprintf_ex(screen, font, 0, 10, WHITE, 0,
"Angle = %f", angle);
}
}
allegro_exit();
return 0;
}
END_OF_MAIN()
the program triggering the breakpoint is: crt0msg.c off of the disk.
snippet of code:
#ifdef _DEBUG
/*
* Report error.
*
* If _CRT_ERROR has _CRTDBG_REPORT_WNDW on, and user chooses
* "Retry", call the debugger.
*
* Otherwise, continue execution.
*
*/
if (rterrnum!=_RT_CRNL&&rterrnum!=_RT_BANNER&&rterrnum!=_RT_CRT_NOTINIT)
{
if (1 == _CrtDbgReport(_CRT_ERROR, NULL, 0, NULL,rterrs[tblindx].rterrtxt))
_CrtDbgBreak();
}
#endif /* _DEBUG */
tank = load_bitmap("C:\Users\Jason\Desktop\module7\tank.bmp", NULL);
Your compiler should be warning you about that string since it contains invalid escaped characters. You should use double back slashes or single forward slashes:
tank = load_bitmap("C:\\Users\\Jason\\Desktop\\module7\\tank.bmp", NULL);
// or
tank = load_bitmap("C:/Users/Jason/Desktop/module7/tank.bmp", NULL);
The latter format is recommended because it is cross platform. (Minus the whole bit about hard coding an absolute path.)
Finally, you really need to check return codes:
if (!tank) {
// gracefully report error and exit
}
Otherwise the program will crash somewhere else and it will be harder to debug.
I just coded a child thread to create and update window but I am facing some problem. My window closes automatically after that thread execution is completed (naturally). But I don't want to close it so I tried putting a while loop in thread and in that loop I am calling InvalidateRect() function so that it can update window. Now window is not closing automatically but i can't move it or interact with it and cursor also showing some busy icon(means completely not responding). How I can solve that problem. below is code:
calling this from main()
bool CameraApp::OnInit()
{
hThread = (HANDLE)_beginthreadex( NULL, 0, &CameraFrame::StartCameraPreview,
NULL, 0, &threadID );
WaitForSingleObject( hThread, INFINITE );
CloseHandle( hThread );
return TRUE;
}
Thread function block
unsigned __stdcall CameraFrame::StartCameraPreview( void* pArgs )
{
cFrame.ShowCameraWindow();
while(1)
{
cFrame.StartCapture();
InvalidateRect(hwnd, NULL, false);
Sleep(5000);
}
_endthreadex( 0 );
return 0;
}
i can't use main() function to create window. So, i have to use thread and update that window with periodic image taken from web-camera.
Instead of your infinite loop you need to create message pump in secondary thread that processes windows messages.
unsigned __stdcall CameraFrame::StartCameraPreview( void* pArgs )
{
cFrame.ShowCameraWindow();
MSG msg;
while (GetMessage(&msg, NULL, 0, 0))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
_endthreadex( 0 );
return 0;
}