Jump to content
NobbyNobbs

Программирование джойстиков CH Products

Recommended Posts

 

А что если стоя в гамаке и в противогазе?  :crazy:

....

Довольно остроумно скрипт написан, с интересом почитал, спасибо!

Share this post


Link to post
Share on other sites

 

 

Спасибо, Nobby. Всё работает... Пугает только объем скрипта.... для 6 кнопок набежит Хотя вешать на одну кнопку и single и  double и long - это через чур. Думаю придется обойтись только single (на отпускание) и long
 

 

Если честно, то это я написал типа "в порядке бреда, ну, то есть от фонаря, как говорится, из-под волос" (из Довлатова). Мне почему-то кажется, что аналогичную логику должно быть можно сделать через готовые таймеры (OnDelay, OffDelay и т.д.), должно получиться покороче. Но только вот тогда придется сперва думать, а потом писать  :biggrin:

 

Довольно остроумно скрипт написан, с интересом почитал, спасибо!

:blush:

  • Upvote 1

Share this post


Link to post
Share on other sites

2 Nobby, Спасибо за идеи. Красивый код получился! Может чуть излишен, (с таймерами правильно заметил короче будет) но зато в текущем представлении замечательно читается и понятен. :)

Edited by [I.B.]Zulu

Share this post


Link to post
Share on other sites

Поясните - подруливание это триммирование толкько средствами джойстика?

Share this post


Link to post
Share on other sites

Гы, гы. :) Тем, кто заглядывает, но скроллить тему лень. Облегчение понимания работы триггер-таймеров тут.   Очень хорошее подспорье для смыслового описания данного в  Help'е

:)

Edited by [I.B.]Zulu

Share this post


Link to post
Share on other sites

Поясните - подруливание это триммирование толкько средствами джойстика?

Нет. Триммирование от Terrora здесь. А это просто сдвиг оси на одну или другую фиксированную величину по нажатию хатки. Чес говоря не понял как это использовать...

Edited by =J13=Moroka

Share this post


Link to post
Share on other sites

Спасибо, Nobby. Всё работает... Пугает только объем скрипта.... для 6 кнопок набежит :) Хотя вешать на одну кнопку и single и  double и long - это через чур. Думаю придется обойтись только single (на отпускание) и long...

 

Не так страшно, на самом деле. Выделяй отдельные функциональные блоки каким либо обрамлением через комментарии. Можно применить прицип глав и параграфов

// *********************  ||| ОБРАБОТКА ДВОЙНЫХ ТРОЙНЫХ НАЖАТИЙ ||| ****************************

// -------------------------------------  ***** Для кнопки   JS1. B1  ********-----------------

SEQUENCE

    IF (TRUE)....

    .........     

    ENDIF

ENDSEQUENCE

// -----------------------------------------------------------------------------------------------------

//

// -------------------------------------  ***** Для кнопки   JS1. B2  ********-----------------                                          

SEQUENCE

    IF (TRUE)....

    .........     

    ENDIF

ENDSEQUENCE

// ----------------------------------------------------------------------------------------------------- 

Edited by [I.B.]Zulu

Share this post


Link to post
Share on other sites

Вот изюминка скрипта Nooby для дифференциациии одиночных, двойных и длинных нажатий в том, что он придумал как отделить одиночное от двойного.   Т.е. концептуально сделать двойной клик самостоятельным, а не состоящим из двух одиночных!!!  (Писать то мы все можем, а вот придумать, что писать, соображаем не всегда :))  

Правда там появляется задержка для срабатывания одиночного нажатия, но ИМХО, для большинства применений это не критично.   

 

Думаю только кнопки открытия огня и сброса бомб нельзя подвергать такой обработке. А все остальные кнопки можно - механизация там всякая, прицеливание, оглядывание и т.д...

Share this post


Link to post
Share on other sites

Гы, гы. :) Тем, кто заглядывает, но скроллить тему лень. Облегчение понимания работы триггер-таймеров тут.   Очень хорошее подспорье для смыслового описания данного в  Help'е

:)

 

Кстати, как раз втыкал в эти графики и думал, что переписать вчерашний скрипт будет несложно, но увы, нашел там одну неточность и теперь мне кажется, что малой кровью обойтись вряд ли удастся.

 

На самом деле по OffDelay логическое устройство сразу становится True и продолжает быть таким T времени после отпускания кнопки.

И картинка с период неполная. Там не показано, что D1 будет true T времени вне зависимости от того, что у него на входе.

 

должно быть как-то вот так

 

post-14111-0-71777600-1411896873_thumb.png

Share this post


Link to post
Share on other sites

Да.. Период в общем то без ошибки показан, просто не указывалось, что его длительность не изменится как долго кнопку не держать.

 

А вот OFFDELAY - замечание серьезное.   И если действительно так, то схемку мне надо перерисовать....

Share this post


Link to post
Share on other sites

А тебя что именно измененный OFFDELAY смущает?   Маскируй его условием на вызвавшую его кнопку и получишь результат как на моей исходной картинке

 

TIMER (OFFDELAY, D1, 20) = JS1.B1 

 

WHILE (D1) - условие будет выполнятся сразу после нажатия JS1.B1 и до момента исхода 20 интервалов после отжатия

 

WHILE(D1 AND NOT JS1.B1)  - условие будет выполнятся после отжатия JS1.B1 и до исхода 20 интервалов  (как на рисунке)

Share this post


Link to post
Share on other sites

 

 

Zulu" post="205767" timestamp="1411899085"]
А тебя что именно измененный OFFDELAY смущает?   Маскируй его условием на вызвавшую его кнопку и получишь результат как на моей исходной картинке

 

показалось  :)
маленько затупил сначала.
в общем и целом тут то же самое, но другими словами.
 
 

 

%define FirstPush b1
%define SecondPush b2
%define LongPush b3
script
 
sequence
wait(js1.b13 and !FirstPush);
FirstPush=true;
endsequence
 
timer(Period,d2,5)=!js1.b13 and FirstPush;//Фиксируем отпускание кнопки
                                            //и ждем второго нажатия ~четверть секунды
timer(period,d3, 7)=!js1.b13 and FirstPush; //нужен чтобы отследить продолжительность паузы между нажатиями
 
sequence                                        //если через четверть секунды ничего не произошло
wait(d3 and !d2 and FirstPush); //генерируем нажатие и сбрасываем флаг
FirstPush=false;
cms.b3=true;
delay(5);
cms.b3=false;
endsequence
 
 
if((d2 and js1.b13) or SecondPush) then //если во время работы d2 нажали кнопку,
FirstPush=false;                        //то распознаем "даблклик"
SecondPush=true;
cms.b2=js1.b13;
endif
 
sequence                                //тот же фокус с флагом для выхода из условия что и в прошлом скрипте
wait(SecondPush and !js1.b13); //(удивлен, но это корректно работает и без строки cms.b2=false o_O )
SecondPush=false;
endsequence
 
timer(ondelay,d1,10)=js1.b13; //для длинного нажатия самый обыкновенный таймер
if((d1 and !SecondPush) or LongPush)then //отсекаем срабатываение при даблклике с последующим удержанием кнопки
cms.b1=js1.b13;               
LongPush=true;
endif
if (LongPush and !js1.b13) then
LongPush=false;
FirstPush=false;
endif
 
endScript
 

timers.zip

Edited by NobbyNobbs
  • Upvote 2

Share this post


Link to post
Share on other sites

Кстати, как раз втыкал в эти графики и думал, что переписать вчерашний скрипт будет несложно, но увы, нашел там одну неточность и теперь мне кажется, что малой кровью обойтись вряд ли удастся.

 

На самом деле по OffDelay логическое устройство сразу становится True и продолжает быть таким T времени после отпускания кнопки.

И картинка с период неполная. Там не показано, что D1 будет true T времени вне зависимости от того, что у него на входе.

 

должно быть как-то вот так

 

attachicon.giftimers.png

Вот диаграммы логики триггер-таймеров с учетом примечания по PEROID и исправления в OFFDELAY

 

post-4254-0-76312700-1411906437_thumb.gif

  • Upvote 2

Share this post


Link to post
Share on other sites

Вот диаграммы логики триггер-таймеров с учетом примечания по PEROID и исправления в OFFDELAY

 

attachicon.gifCMLogics2.gif

 

спасибо, утащил-распечатал. 

Share this post


Link to post
Share on other sites

2Nobby

 

Пока искал способ убить уже запущенный таймер раньше срока заметил прикольную вещь.   Знание её позволит экономить на объявлении переменных типа D (позволит её использовать в разных триггерах без влияния друг на друга).  Даже не подозревал об этом.

 

TIMER(PERIOD,D1,10) = JS4.B7;
BTN0 = D1;
TIMER(PERIOD,D1,40) = JS4.B7;
BTN1 = D1;
TIMER(PERIOD,D1,80) = JS4.B7;
BTN2 = D1;

 

Несмотря на использование одного и того же логического устройства D1 - фактически будет создано три независымх таймер-триггера, которые запустятся одновременно (по JS4.B7), а вот закончат свою работу в разное, строго определенное в теле, время. Гы-Гы, что можно видеть по времени отжатия кнопок BTN0 - BTN2

 

:wacko:  :o:  ;)  :biggrin:  :lol: 

 

А убить уже запущенный на определенное время таймер уже видимо никак нельзя.... Очень жаль..

Edited by [I.B.]Zulu
  • Upvote 1

Share this post


Link to post
Share on other sites

Несмотря на использование одного и того же логического устройства D1 фактически будет создано три независымх таймер-триггера, которые запустятся одновременно (по JS4.B7), а вот закончат свою работу в разное, строго определенное в теле, время.

 

да уж. то что называется фича ))

 

а чтобы убить toggle(d1) не прокатывает?

Share this post


Link to post
Share on other sites
 

 

 

Пощу только самую мякоту (без скрипт-ендскрипт и прочих define, должно быть понятно и так)

 

Э парни :wacko: я ж не программист.Можно весь скрипт с DEFINE.К тому же у меня стоит скрипт триммирования,надо будет их как то совместить.

Share this post


Link to post
Share on other sites

Э парни :wacko: я ж не программист.Можно весь скрипт с DEFINE.К тому же у меня стоит скрипт триммирования,надо будет их как то совместить.

 

%Define J_Stick JS?.A? // Вместо ? - указать № твоего устройства и № его оси, которую хотим "сгладить" 
%Define C_Stick CMS.A? // Вместо ? - указать № оси CMS устройства, ось которого будет "сглажена"
//
script
 if ( [ J_Stick != C_Stick ] ) then
      if ( [ ( J_Stick + 1 ) > C_Stick ] ) then
        C_Stick = J_Stick - 1;
      endif
      if ( [ ( J_Stick - 1 ) < C_Stick ] ) then
        C_Stick = J_Stick + 1;
      endif
      if ( [ J_Stick == 255 ] ) then
        C_Stick = 255;
      endif
      if ( [ J_Stick == 0 ] ) then
        C_Stick = 0;
      endif
    endif
endScript
 
На самом деле скрипт просто задает "мертвую зону" +/-1. Поэтому результат "отстает" от входного значения на единицу... и, собственно поэтому, чтобы получить макс (255) и мин (0) отдельно два блока if внизу...
 
П.С. Сначала Terror , а потом и Nobby научились красиво вставлять в свои посты код... Как это? Научите, то же хочется быть "опрятным"
Edited by =J13=Moroka

Share this post


Link to post
Share on other sites

@@=J13=Moroka  

я у Террора подсмотрел  :) 
надо код засунуть в блок {code=auto:0} здесь ваш код {/code}, только использовать квадратные скобки.
 

@Zulu'] 

попробовал поубивать таймеры... тоже не получилось.

  • Upvote 1

Share this post


Link to post
Share on other sites

Нашел маленький косяк в скрипте с таймерами.

FirstPush лучше обнулять в предпоследнем условии, то есть при срабатывании длинного нажатия. Если обнулять в последнем, как у меня написано, то при быстром повторном нажатии кнопки срабатывает двойной клик  :)

Share this post


Link to post
Share on other sites

да уж. то что называется фича ))

 

а чтобы убить toggle(d1) не прокатывает?

Неа, будет создан еще один триггер и всего то.   D1 походу только нам нужна при письме.  В железе видимо после каждой записи создается свой девайс, со своим внутренним id  и связями  которые действовали на момент последовательного чтения компилятором нашего скрипта и прямого отношения к D1 они не имеют...

 

 

Нашел маленький косяк в скрипте с таймерами.

FirstPush лучше обнулять в предпоследнем условии, то есть при срабатывании длинного нажатия. Если обнулять в последнем, как у меня написано, то при быстром повторном нажатии кнопки срабатывает двойной клик  :)

 

Вот  по сходной причине я и хотел научиться убивать уже активыне таймеры

Share this post


Link to post
Share on other sites

 

 

На самом деле скрипт просто задает "мертвую зону" +/-1. Поэтому результат "отстает" от входного значения на единицу... и, собственно поэтому, чтобы получить макс (255) и мин (0) отдельно два блока if внизу...

Чё та не получилось у меня :( Скрипт триммирования я убрал,что бы не мешал пока.Всё равно колбасит кружочек.

Share this post


Link to post
Share on other sites

Чё та не получилось у меня :( Скрипт триммирования я убрал,что бы не мешал пока.Всё равно колбасит кружочек.

Я так мыслю :scratch_one-s_head: надо увеличить мёртвую зону.

Share this post


Link to post
Share on other sites

Чё та не получилось у меня :( Скрипт триммирования я убрал,что бы не мешал пока.Всё равно колбасит кружочек.

Скажи, в какой проге именно смотришь, что колбасит? Какие значения читаются?   Мертва зона помогает только в случае нечеткого центрального положения (это к микростику, можно применить например).  А вот дрожжание, убрать можно только сглаживанием.

Share this post


Link to post
Share on other sites

Скажи, в какой проге именно смотришь, что колбасит? Какие значения читаются?   Мертва зона помогает только в случае нечеткого центрального положения (это к микростику, можно применить например).  А вот дрожжание, убрать можно только сглаживанием.

Смотрю в CH control manager.Вот она где собака порылась.Так в центре оси он стоит как вкопанный.А при отклонении больше половины,в некоторых положениях его колбасит.На глаз амплитуда где то 3 единицы.

Share this post


Link to post
Share on other sites

Смотрю в CH control manager.Вот она где собака порылась.Так в центре оси он стоит как вкопанный.А при отклонении больше половины,в некоторых положениях его колбасит.На глаз амплитуда где то 3 единицы.

попробуй в скрипте вместо единички поставить 2.

тогда у тебя при "дрожании" в диапазоне +/- 2 cms дергаться не будет. Мертвая зона в скрипте не только в центре... Она относительно cms оси... cms ось "волочится" за J_Stick как привязанная на веревочке длинной в 1 шаг :) Если увеличить "длину веревочки" до 2 - то будет на 2 шага отставать...

а триммирование на должно мешать! В его тело, вместо оси JS надо подставить ось cms из сглаживания...

Edited by =J13=Moroka

Share this post


Link to post
Share on other sites

Нет :( не работает скрипт нет изменений после замены значений

Вот он

%Define J_Stick JS3.a3   //реальная ось отключена NONE
%Define C_Stick CMS.a3 // виртуальная ось в вкладке cms control

script

if ( [ J_Stick!= C_Stick ] ) then
if ( [ ( J_Stick + 1 ) > C_Stick ] ) then
C_Stick = J_Stick - 1;
endif
if ( [ ( J_Stick - 1 ) < C_Stick ] ) then
C_Stick = J_Stick + 1;
endif
if ( [ J_Stick == 255 ] ) then
C_Stick = 255;
endif
if ( [ J_Stick == 0 ] ) then
C_Stick = 0;
endif
endif

Может что то я не так сделал?

 

Edited by beretta5

Share this post


Link to post
Share on other sites

Нет :( не работает скрипт нет изменений после замены значений

Вот он

...

Может что то я не так сделал?

А что значит не работает? Не сглаживает? или вообще не реагирует?

Если второе, то у тебя в конце endscript не стоит... или ты cms ось "на вывод" не назначил  :rolleyes:

...а так всё работает.. у себя проверил именно твой! взял копипастом ;)

Edited by =J13=Moroka

Share this post


Link to post
Share on other sites

2 beretta5

... попробовал... просто подставить 2-ку вместо единички - не работает :(

Edited by =J13=Moroka

Share this post


Link to post
Share on other sites

А что значит не работает? Не сглаживает? или вообще не реагирует?

Если второе, то у тебя в конце endscript не стоит... или ты cms ось "на вывод" не назначил  :rolleyes:

...а так всё работает.. у себя проверил именно твой! взял копипастом ;)

Стоит в конце endscript,я просто забыл его в посте приписать.Не сглаживает он.Я так понял cms.a3 ось не волочится за js3.a3.

В центре ось немного подрагивает а со скриптом стоит как вкопанная.А по сторонам водишь её она дрожит.

Так 2-ки ставить вместо всех единичек?

Share this post


Link to post
Share on other sites

У меня сложилось впечатление что скрипт влияет только  когда ось в центральном положении :sorry: он создаёт мертвую зону в центре.

Вот к примеру если

C_Stick = J_Stick - 1;

.......

C_Stick = J_Stick +1 ;

то показания в центре 129-127 единиц после возвращения педалей в центр.

 

когда меняю на

C_Stick = J_Stick - 2;

.....

C_Stick = J_Stick - 2;

то показания становятся 130-126 единиц.

Причём "железно" и постоянно без каких либо колебаний.

 

 

Edited by beretta5

Share this post


Link to post
Share on other sites
У меня сложилось впечатление что скрипт влияет только  когда ось в центральном положении

 

 

Не, не. Работает четко.   У меня подрагивала ось маслорадиатора в пределах 1%.   В результате предыдущий РД дрожжал строкой технострима об этом радиаторе.  После применения скрипта, ось как вкопанная.

Edited by [I.B.]Zulu

Share this post


Link to post
Share on other sites
Так 2-ки ставить вместо всех единичек?

Нет, просто подставить не получится!, НО

если чуть изменить скрипт:

 

%Define J_Stick JS1.A3 // здесь свои оси ставь

%Define C_Stick CMS.A1 // и здесь свои...
%Define mz 10 // сколько здесь поставишь, такой диапазон +/- mz и будет...
//
script
  if ( [ J_Stick > C_Stick+(mz-1) ] ) then
      if ( [ ( J_Stick + 1 ) > C_Stick ] ) then
        C_Stick = J_Stick - mz;
      endif
  endif
  if ( [ J_Stick < C_Stick-(mz-1) ] ) then
      if ( [ ( J_Stick - 1 ) < C_Stick ] ) then
        C_Stick = J_Stick + mz;
      endif
  endif
      if ( [ J_Stick == 255 ] ) then
        C_Stick = 255;
      endif
      if ( [ J_Stick == 0 ] ) then
        C_Stick = 0;
   endif
endScript

 

...меняя значение mz от 1 до .... можно регулировать "зону сглаживания"

 

п.с. Проверено... мин нет ;)

Edited by =J13=Moroka

Share this post


Link to post
Share on other sites

 

 

если чуть изменить скрипт:

 

Уря :dance: заработало.Есть,правда небольшая мёртвая зона в центре,но это пустяки.Я выставил %Define mz 4,что бы совсем не дрожало :good:

Share this post


Link to post
Share on other sites

....Есть,правда небольшая мёртвая зона в центре,но это пустяки.Я выставил %Define mz 4,что бы совсем не дрожало :good:

Мертвая зона и есть тот коридор, внутри которого входная дрожь оси джойстика не передается на выход.

Вообще этот алгоритм вернее называть не "сглаживание", а "пороговый шумоподавитель" ....

Share this post


Link to post
Share on other sites

Вот диаграммы логики триггер-таймеров с учетом примечания по PEROID и исправления в OFFDELAY

 

attachicon.gifCMLogics2.gif

О, блин! Ой, спасибо, блин, большое! Ой, очень большое, блин, спасибо!! :clapping: А то у меня регулярно мозги заклинивает на тему того или иного on/offdelay.

@@=J13=Moroka

я у Террора подсмотрел  :) 

надо код засунуть в блок {code=auto:0} здесь ваш код {/code}, только использовать квадратные скобки.

Точно так. Только я auto:0 не пишу, это форум подставляет. Я просто code /code рисую и всё.

Спасибо, парни, что Беретте помогли с этим кусочком, а то я только сейчас увидел. С вами не пропадёшь!

Share this post


Link to post
Share on other sites

А у кого проблемы были с интеграцией сглаживания в уже работающие скрипты?

 

Принцип следующий. В два этапа:

1) Код сглаживания помещаем в самый верх скрипта.  И производим предварительное сглаживание физической оси JS в аналоговую переменную, например А1.

2) Далее в последующем коде на том месте где присутствовала ваша физическая ось ставим уже сглаженное значение А1. 


 

 

О, блин! Ой, спасибо, блин, большое! Ой, очень большое, блин, спасибо!!

 

Всегда пожалуйста :) 

Share this post


Link to post
Share on other sites

 

 

Zulu' timestamp='1412033084' post='206697'] А у кого проблемы были с интеграцией сглаживания в уже работающие скрипты?

У мну скрипт "пороговый шумоподавитель" не работает со скриптом "триммирование".Я пока не переживаю,потом может поставлю скрипт подруливание.Просто информация к размышлению :gamer:

Share this post


Link to post
Share on other sites

Опаньки! Нашел... ещё пару лишних строк кода в нашем "сглаживателе" ;)

Оказывается, чтобы "получить" нужный люфт в передаче от оси джоя к cms-оси можно отлично обойтись:

(%define опущено)
script
  if ( [ J_Stick > C_Stick+(mz-1) ] ) then
  //  ЗАБАНЕНО  if ( [ ( J_Stick + 1 ) > C_Stick ] ) then
        C_Stick = J_Stick - mz;
   // ЗАБАНЕНО  endif
  endif
  if ( [ J_Stick < C_Stick-(mz-1) ] ) then
   //  ЗАБАНЕНО if ( [ ( J_Stick - 1 ) < C_Stick ] ) then
        C_Stick = J_Stick + mz;
    //  ЗАБАНЕНО endif
  endif
      if ( [ J_Stick == 255 ] ) then
        C_Stick = 255;
      endif
      if ( [ J_Stick == 0 ] ) then
        C_Stick = 0;
   endif
endScript

В самом деле, ведь первое и второе условие IF идущие подряд работают по логике И. Но посмотрите... первое условие уже подразумевает выполнение второго :)

..тогда, что называется, зачем платить больше? Смело вычеркиваем 4 строки из скрипта... проверяем... Работает!

Однако, в первой, оригинальной версии (с люфтом +/-1) Так Не получится! ... а потому что автор исходной версии уже один раз упростил скрипт, ограничиваясь в первом IF проверкой неравенства Js и Cms вместо двух проверок отклонения Js от Cms на единицу в одну и в другую сторону. Ведь это неравенство как раз и выполняется при отклонении на 1. В результате он "экономит" 2 строки, а мы, со своей дотошностью - 4! :) да ещё имеем возможность задавать величину лофта.... люфта ;)

П.С. Ура! Наши победили :)

 

2Terror, 2Nobby спасибо за code.../code наконец получилось!

Edited by =J13=Moroka
  • Upvote 2

Share this post


Link to post
Share on other sites

У мну скрипт "пороговый шумоподавитель" не работает со скриптом "триммирование".Я пока не переживаю,потом может поставлю скрипт подруливание.Просто информация к размышлению :gamer:

Прикрепи скрипт. Я тебе интегрирую. :)

Опаньки! Нашел... ещё пару лишних строк кода в нашем "сглаживателе" ;)

....

Утянул, спасибо!

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

×
×
  • Create New...