Kibor |
Отправлено: 26 Февраля, 2015 - 10:21:35
|
Эксперт
Просматривает форум
Сообщений всего: 8217
Дата рег-ции: Март 2013
Откуда: Одесса
Репутация: 357
|
Появились функции с помощью которых можно обмениваться данными между собранными запущенными EXE и копиями Кибор. Можно как передавать и получать информацию, так и управлять работой другой программы.
Для этого в Кибор и собранных EXE присутствует специальный буфер размером в 1024 байта (переменная char имеет 1 байт). С помощью записи и чтения этого буфера можно обмениваться любыми данными. Как информационными так и управляющими.
Запись и чтение возможны как в свой буфер так и в буфер другой программы.
writebuffer - производит запись в свой буфер либо в буфер указанной программы.
readbuffer - производит чтение с своего буфера либо буфера указанной программы.
синтаксис
пишем в свой буфер
Цитата: char ch[100];
ch[0]='f'; ch[1]='u'; // тд
writebuffer(#ch[0], 100);//пишем в свой буфер
первый параметр - указатель на массив char, данные с которого будем писать в буфер.
второй - количество записываемых байт.
пишем в буфер другой программы
Цитата: win w=window ("Skript");
char ch[100];
ch[0]='f'; ch[1]='u'; // тд
writebuffer(#ch[0], 100, w);//пишем в буфер программы на которую указывает указатель w
первый параметр - указатель на массив char, данные с которого будем писать в буфер.
второй - количество записываемых байт.
третий - указатель на программу в буфер которой пишем
Читаем с своего буфера
Цитата: char ch[100];
readbuffer(#ch[0], 100);//Читаем с своего буфера
первый параметр - указатель на массив char, в который запишутся считываемы е данные с буфера
второй - количество считываемых байт.
Читаем с буфера другой программы
Цитата: win w=window ("Skript");
char ch[100];
readbuffer(#ch[0], 100, w);//Читаем с своего буфера программы на которую указывает указатель w
первый параметр - указатель на массив char, в который запишутся считываемы е данные с буфера
второй - количество считываемых байт.
третий - указатель на программу с буфера которой читаем
Функции возвращают 1 при удачной работе. или меньше 1 при ошибке.
Цитата: char Command[1]={'A'};
writebuffer (#Command[0], 1);//Записываем в внутренний буффер программы символ 'A'
char b[1];
readbuffer(#b[0], 1);//Считываем с буффера первый один символ
if(b[0] == 'A')
{
messagebox (b[0]);
}
Данные функции работаю асинхронно (не отанавливают и не тормозят процессы)
Связь возможна с помощью двух вариантов
1)положить в свой буфер и заниматься своими делами. когда другой программе понадобится она прочитает.
2)положить в буфер другой программы и заниматься своими делами. когда другая программа проверит свой буфер она прочитает с него.
=========================================================
Простой пример управления другой программой путем записи в ее буфер одного знака.
код управляющей программы. при нажатие на кнопки 0-9 она записывает свой символ в буфер программы p2
CODE:char s='n';
win w=window ("p2");
lop:;
if (w==0)w=window ("p2");
if (getkeystate(49)==1){s='1';if (writebuffer(#s, 1, w)<1) goto er;}
if (getkeystate(50)==1){s='2';if (writebuffer(#s, 1, w)<1) goto er;}
if (getkeystate(51)==1){s='3';if (writebuffer(#s, 1, w)<1) goto er;}
if (getkeystate(52)==1){s='4';if (writebuffer(#s, 1, w)<1) goto er;}
if (getkeystate(53)==1){s='5';if (writebuffer(#s, 1, w)<1) goto er;}
if (getkeystate(54)==1){s='6';if (writebuffer(#s, 1, w)<1) goto er;}
if (getkeystate(55)==1){s='7';if (writebuffer(#s, 1, w)<1) goto er;}
if (getkeystate(56)==1){s='8';if (writebuffer(#s, 1, w)<1) goto er;}
if (getkeystate(57)==1){s='9';if (writebuffer(#s, 1, w)<1) goto er;}
if (getkeystate(48)==1){s='0';if (writebuffer(#s, 1, w)<1) goto er;}
sleep(10);
goto lop;
er:;
код управляемой программы. (собрать в exe и назвать p2 (на английском)).
при чтение своего буфера в зависимостьи от символа печатает его и воспроизводит звук
CODE:char s;
lop:;
if (readbuffer(#s, 1)<1) goto er;
if (s=='1')beep(100, 200);
if (s=='2')beep(200, 200);
if (s=='3')beep(300, 200);
if (s=='4')beep(400, 200);
if (s=='5')beep(500, 200);
if (s=='6')beep(600, 200);
if (s=='7')beep(700, 200);
if (s=='8')beep(800, 200);
if (s=='9')beep(900, 200);
if (s=='0')beep(1000, 200);
textout(0, 100, 50, format(#s), 1);
sleep(10);
goto lop;
er:;
=========================================================
Простой пример управления другой программой путем записи в свой буфер одного знака.
код управляющей программы. при нажатие на кнопки 0-9 она записывает свой символ в свой буфер, с которого уже управляющая почитает сама. (собрать эту в exe и назвать p1 (на английском))
CODE:char s='n';
lop:;
if (getkeystate(49)==1){s='1';if (writebuffer(#s, 1)<1) goto er;}
if (getkeystate(50)==1){s='2';if (writebuffer(#s, 1)<1) goto er;}
if (getkeystate(51)==1){s='3';if (writebuffer(#s, 1)<1) goto er;}
if (getkeystate(52)==1){s='4';if (writebuffer(#s, 1)<1) goto er;}
if (getkeystate(53)==1){s='5';if (writebuffer(#s, 1)<1) goto er;}
if (getkeystate(54)==1){s='6';if (writebuffer(#s, 1)<1) goto er;}
if (getkeystate(55)==1){s='7';if (writebuffer(#s, 1)<1) goto er;}
if (getkeystate(56)==1){s='8';if (writebuffer(#s, 1)<1) goto er;}
if (getkeystate(57)==1){s='9';if (writebuffer(#s, 1)<1) goto er;}
if (getkeystate(48)==1){s='0';if (writebuffer(#s, 1)<1) goto er;}
sleep(10);
goto lop;
er:;
код управляемой программы. при чтение буфера программы p1 в зависимостьи от символа печатает его и воспроизводит звук
CODE:char s;
win w=window ("p1");
lop:;
if (w==0)w=window ("p1");
if (readbuffer(#s, 1, w)<1) goto er;
if (s=='1')beep(100, 200);
if (s=='2')beep(200, 200);
if (s=='3')beep(300, 200);
if (s=='4')beep(400, 200);
if (s=='5')beep(500, 200);
if (s=='6')beep(600, 200);
if (s=='7')beep(700, 200);
if (s=='8')beep(800, 200);
if (s=='9')beep(900, 200);
if (s=='0')beep(1000, 200);
textout(0, 100, 50, format(#s), 1);
sleep(10);
goto lop;
er:;
============================================
с помощью функций форматирования можно преобразовать данные массива char в любой тип
Преобразование одного типа данных к другому
format- Привод целго число int или дробного double к string
formatsn- Преобразование строк в которых записаны числа в натуральное число int или double
formatci- Возвращает int char'а значения в параметре
formatic- Возвращает char чисового значения в параметре
strcpy- Копирование string в массив char
codhex- Переводит целые или дробные числа (до 4 байт) в HEX (справа на лево)
codhexi- Переводит шестнадцатеричный HEX код в целое число int (справа на лево).
======================================
Данный скрипт позволяет запускать всего один EXE бота нужное количество раз (сколько окон игры) и каждая копия привяжется автоматически к своему окну игры.
Не зависим от названий окон игры.
Код (Отобразить)CODE:win w_bot[10];
int k_bot=window (#w_bot[0], "bots");//Получаем указатели на все боты которые имеют имена bots
win w_game[10];
int k_game=window (#w_game[0], -1, "Notepad", -1);//Получаем указатели на все окна игр (Блокнотов)
char ch[100];
string S;
win W;//Указатель в который запишется указатель на привязанное окно
for (int n1=0; n1<k_game; n1++)//Перебираем все окна игр
{
S=format(formatwi(w_game[n1]));//Приводим HWND игры к string
for (int n=0; n<k_bot; n++)//Перебираем все окна ботов
{
if (gethwnd()!=formatwi(w_bot[n]))// если это указатель не на этот бот
{
readbuffer(#ch[0], 100, w_bot[n]);//Читаем с буфера программы на которую указывает указатель w_bot[n]
if (format(#ch[0])==S) goto aa;//Если в буфере какого то бота записан этот указатель на эту игру, переходим к следующему указателю на следующую игру
}
}
W=w_game[n1];//Если ни у одного бота не записан указатель на эту игру - присваеваем его в W
setwindowparam(W);//Обновляем структуру указателя W
strcpy(#ch[0], S);
writebuffer(#ch[0], size(S));//Запишем в свой буфер указатель на эту игру что бы другие боты знали что этот бот привязан у этой игре
rename(format(formatwi(W))+"-"+W.name);//Меняем заголовок бота
aa:;
}
loop()//Основной цикл бота
{
sleep(100);
}
CREATE_INTERFACE
{
DIALOG "bots" 337 180 //РазмерX РазмерY
BUTTONSCRIPT "Запустить" 225 121 100 25 //ПозицияX ПозицияY РазмерX РазмерY
//Добавление контролов управления ......
}
EXE бота надо переименовать в "bots.exe"
1 - Запустим 3 окна игры (в данном случае блокнота)
2 - Запустим 3 копии bots.exe
3 - Нажмем в каждой - Запустить
4 - Через пару секунд нажмем конрл шифт Z и остановим боты.
5 - Увидим что названия ботов поменялись и приняли заголовки окон блокнотов к которым привязаны. |
|
|
yo1 |
Отправлено: 23 Марта, 2015 - 19:02:47
|
Участник
Покинул форум
Сообщений всего: 110
Дата рег-ции: Окт. 2014
Репутация: 0
|
Возник вопрос: буфер перезаписывается? Т.е. если 2й скрипт не успеет\не сможет (ну допустим) по каким либо причинам выполнить команду пришедшую в его буфер, а на буфер уже пришла следующая, то он выполнит эту следующую, пропустив ту, которую не успел? Или очередность какая?
Заметил, что когда окна линейки "неактивны" так сказать, то скрипт выполняется медленнее, что ли. Делаю окно активным, прекрасно работает, неактивным - снова какие то замедления в скрипте (не знаю как объяснить эти долгие паузы). Команды sendkey и аналоги. В чем может быть причина?
Кстати, есть кликер написанный на коленке на с+ (не мной), он нормально работает в неактивное окно. |
|
|
Kibor |
Отправлено: 23 Марта, 2015 - 19:19:31
|
Эксперт
Просматривает форум
Сообщений всего: 8217
Дата рег-ции: Март 2013
Откуда: Одесса
Репутация: 357
|
yo1 пишет: Возник вопрос: буфер перезаписывается? Т.е. если 2й скрипт не успеет\не сможет (ну допустим) по каким либо причинам выполнить команду пришедшую в его буфер, а на буфер уже пришла следующая, то он выполнит эту следующую, пропустив ту, которую не успел? Или очередность какая?
перезаписывается. но...
это не проблема если очень хочется ничего не пропустить пусть принимающая програ после того как забрал с буфера пишет туда что то что значит что забрал.
передающая пусть ждет сигнала того и не спешит пока там не появится сигнал что забрали.
если сигнал есть - тогда команду следующую.
yo1 пишет: Заметил, что когда окна линейки "неактивны" так сказать, то скрипт выполняется медленнее, что ли. Делаю окно активным, прекрасно работает, неактивным - снова какие то замедления в скрипте (не знаю как объяснить эти долгие паузы). Команды sendkey и аналоги. В чем может быть причина?
Кстати, есть кликер написанный на коленке на с+ (не мной), он нормально работает в неактивное окно.
есть sendmessage есть post...
sendmessage сообщение отправляет и ждет пока обработает окно его.
post-у все равно. прошло не прошло..
проверьте авток, там режимы переключаются. если хотите можете сами реализовать в кибор отправку сообщений через postmessage. сделать свою функцию.
http://kibor-bot.com/forum/topic...m=1&topic=51 |
|
|
yo1 |
Отправлено: 23 Марта, 2015 - 19:40:31
|
Участник
Покинул форум
Сообщений всего: 110
Дата рег-ции: Окт. 2014
Репутация: 0
|
Т.е. вместо sendkey использовать postmessage(WM_KEYDOWN, 0, 0, w) и postmessage(WM_KEYUP, 0, 0, w)?
Как я понимаю postmessage(WM_CHAR, 0, 0, w) - просто нажатие? |
|
|
yo1 |
Отправлено: 25 Марта, 2015 - 13:42:36
|
Участник
Покинул форум
Сообщений всего: 110
Дата рег-ции: Окт. 2014
Репутация: 0
|
Возникла любопытная проблема. Отправляю из скрипта 1 в скрипт 2 число, скрипт 2 принимает и делает какое либо действие в соответствии с тем, какое число было принято. Сама проблема в том, что скрипт не останавливается после выполнения функции.
CODE:char s;
win wind=window ("Íîâûé òåêñòîâûé äîêóìåíò (2).txt — Áëîêíîò", "Notepad", -1);
loop:;
if (readbuffer(#s, 1)<1) goto er;
if (s=='1')
sendkey(F1, wind);
sleep(10);
goto loop;
er:;
Т.е. после того, как он нажмет F1 в блокноте он не останаливается на этом, а продолжает жать F1 бесконечно. Понятно, что там goto, но куда бы не ставил, получается ерунда.
И что означает "<1" в if (readbuffer(#s, 1)<1) goto er; ? Мысли, конечно есть, но хочется убедиться.(Отредактировано автором: 25 Марта, 2015 - 13:44:01) |
|
|
Kibor |
Отправлено: 25 Марта, 2015 - 14:38:30
|
Эксперт
Просматривает форум
Сообщений всего: 8217
Дата рег-ции: Март 2013
Откуда: Одесса
Репутация: 357
|
yo1 пишет: Возникла любопытная проблема. Отправляю из скрипта 1 в скрипт 2 число, скрипт 2 принимает и делает какое либо действие в соответствии с тем, какое число было принято. Сама проблема в том, что скрипт не останавливается после выполнения функции.
CODE:
char s;
win wind=window ("Íîâûé òåêñòîâûé äîêóìåíò (2).txt — Áëîêíîò", "Notepad", -1);
loop:;
if (readbuffer(#s, 1)<1) goto er;
if (s=='1')
sendkey(F1, wind);
sleep(10);
goto loop;
er:;
Т.е. после того, как он нажмет F1 в блокноте он не останаливается на этом, а продолжает жать F1 бесконечно. Понятно, что там goto, но куда бы не ставил, получается ерунда.
с какого перепуга остановиться должен?
он прочитал с буфера 1 и жмет..
потом опять прочитал.. там же опять 1 и жмет...
а если он прочитает 1 и перезапишет его.. к примеру в 0, то и выполнит только раз.
примерно вот так
CODE:char s;
char e='0';
win wind=window ("Безымянный — Блокнот", "Notepad", -1);
loop:;
if (readbuffer(#s, 1)<1) goto er;
if (s=='1')
{
writebuffer(#e, 1);// тут записать 0 чтоб больше не читать в буфере 1 изменить на 0
sendkey(F1, wind);
}
sleep(10);
goto loop;
er:;
или отправить 0 с другой программы для отмены 1..
yo1 пишет: И что означает "<1" в if (readbuffer(#s, 1)<1) goto er; ? Мысли, конечно есть, но хочется убедиться.
при удаче вернет 1.
если меньше ошибки разные.. |
|
|
Kibor |
Отправлено: 25 Марта, 2015 - 14:55:24
|
Эксперт
Просматривает форум
Сообщений всего: 8217
Дата рег-ции: Март 2013
Откуда: Одесса
Репутация: 357
|
yo1 пишет: Ага, т.е. путем создания другой переменной и её записи поверх старой.
можно и ту заюзать.
CODE:char s;
win wind=window ("Безымянный — Блокнот", "Notepad", -1);
loop:;
if (readbuffer(#s, 1)<1) goto er;
if (s=='1')sendkey(F1, wind);
if (s=='2')sendkey(F2, wind);
s='0'
writebuffer(#s, 1);// тут записать 0 чтоб больше не читать в буфере 1 изменить на 0
sleep(10);
goto loop;
er:;
yo1 пишет: Есть ли возможность просмотра всего, что пришло в буфер?
какой способ понравится более?
textout?
messagebox?
вывод в не модальный диалог?
пример чата между программами.
собрать эти 2 скрипта в exe......
1 скрипт. собрать в exe и назвать его Prog 1
Цитата: int col, x,y;
//=================================== кнопки
int pos_size_button[1][4];//две кнопки (позиции и размер)
string text_button[1];//названия кнопок
int flag_button[1];//флаг (нажата не нажата)
//устанавливаем позицию и рамер кнопки 1
pos_size_button[0][0]=5; pos_size_button[0][1]=57; pos_size_button[0][2]=235; pos_size_button[0][3]=20;
text_button[0]="Отправить";//название кнопки 1
//=================================== поля ввода текста
int pos_size_edit[1][4];//два поля ввода текста (позиции и размер)
string text_edit[1];//текст а полях
//устанавливаем позицию и рамер поля ввода текста 1
pos_size_edit[0][0]=5; pos_size_edit[0][1]=35; pos_size_edit[0][2]=235; pos_size_edit[0][3]=20;
text_edit[0]="";//начальный текст 1
//=================================== статичный текст (можно изменять)
int pos_size_static[1][4];//2 статичный текст (позиции и размер)
string text_static[1];//2 статичный текст (текст)
//устанавливаем позицию и рамер текста 1
pos_size_static[0][0]=5; pos_size_static[0][1]=10; pos_size_static[0][2]=235; pos_size_static[0][3]=18;
text_static[0]="";//текст 1
//Создаем диалог
createdialog(0,
EDIT, #pos_size_edit[0][0], #text_edit[0]|
STATIC, #pos_size_static[0][0], #text_static[0]|
BUTTON, #pos_size_button[0][0], #text_button[0], #flag_button[0]);
getdisplay(col, x, y);//узнаем разрешение что бы вывести по центру
//Визуализируем диалог
showdialog(0, "Prog 1", x/2-125, y/2-110, 250, 120, 1, 1);
enabletimer(0);
win w=window ("Prog 2");
char ch[512];
lop:
if (w==0)
{
w=window ("Prog 2");
sleep (20);
goto lop;
}
readbuffer(#ch[0], 512, w);//Читаем с буфера программы на которую указывает указатель w
text_static[0]=format(#ch[0]);
sleep(20);
goto lop ;
CREATE_TIMER(0, 50)//выполнение таймера через 50 мсек.
{
if (flag_button[0]>0)
{
flag_button[0]=0;//обнулить флаг нажатия кнопки..
strcpy(#ch[0], text_edit[0]);
writebuffer(#ch[0], 512, w);
}
}
2 скрипт. собрать в exe и назвать его Prog 2
Цитата: int col, x,y;
//=================================== кнопки
int pos_size_button[1][4];//две кнопки (позиции и размер)
string text_button[1];//названия кнопок
int flag_button[1];//флаг (нажата не нажата)
//устанавливаем позицию и рамер кнопки 1
pos_size_button[0][0]=5; pos_size_button[0][1]=57; pos_size_button[0][2]=235; pos_size_button[0][3]=20;
text_button[0]="Отправить";//название кнопки 1
//=================================== поля ввода текста
int pos_size_edit[1][4];//два поля ввода текста (позиции и размер)
string text_edit[1];//текст а полях
//устанавливаем позицию и рамер поля ввода текста 1
pos_size_edit[0][0]=5; pos_size_edit[0][1]=35; pos_size_edit[0][2]=235; pos_size_edit[0][3]=20;
text_edit[0]="";//начальный текст 1
//=================================== статичный текст (можно изменять)
int pos_size_static[1][4];//2 статичный текст (позиции и размер)
string text_static[1];//2 статичный текст (текст)
//устанавливаем позицию и рамер текста 1
pos_size_static[0][0]=5; pos_size_static[0][1]=10; pos_size_static[0][2]=235; pos_size_static[0][3]=18;
text_static[0]="";//текст 1
//Создаем диалог
createdialog(0,
EDIT, #pos_size_edit[0][0], #text_edit[0]|
STATIC, #pos_size_static[0][0], #text_static[0]|
BUTTON, #pos_size_button[0][0], #text_button[0], #flag_button[0]);
getdisplay(col, x, y);//узнаем разрешение что бы вывести по центру
//Визуализируем диалог
showdialog(0, "Prog 2", x/2-125, y/2-110, 250, 120, 1, 1);
enabletimer(0);
char ch[512];
lop:
readbuffer(#ch[0], 512);//Читаем с своего буфера
text_static[0]=format(#ch[0]);
sleep(20);
goto lop ;
CREATE_TIMER(0, 50)//выполнение таймера через 50 мсек.
{
if (flag_button[0]>0)
{
flag_button[0]=0;//обнулить флаг нажатия кнопки..
strcpy(#ch[0], text_edit[0]);
writebuffer(#ch[0], 512);
}
}
запустить эти программы. вводить и отправлять сообщения друг другу.. |
|
|
|