Automation Challenge

Get help with using AutoHotkey and its commands and hotkeys
User avatar
mikeyww
Posts: 5386
Joined: 09 Sep 2014, 18:38

Re: Automation Challenge

03 Nov 2020, 17:08

You're right. We already sold this to Microsoft. Better luck next time.

:wave: :D

OK, you inspired me to go get a 32-key MIDI controller. It will take me about a week to figure this out!
elad770
Posts: 81
Joined: 30 Oct 2020, 16:21

Re: Automation Challenge

03 Nov 2020, 17:17

I'm not sure I understand your question.

My midi controller is connected right now and messages are coming in.

I activated your script and i understand that i need to press something (F1?) and see if it capture something?
malcev
Posts: 865
Joined: 12 Aug 2014, 12:37

Re: Automation Challenge

03 Nov 2020, 17:21

No, You have to press midi buttons and see msgbox in ahk.
elad770
Posts: 81
Joined: 30 Oct 2020, 16:21

Re: Automation Challenge

03 Nov 2020, 17:24

mikeyww wrote:
03 Nov 2020, 17:08
You're right. We already sold this to Microsoft. Better luck next time.

:wave: :D

OK, you inspired me to go get a 32-key MIDI controller. It will take me about a week to figure this out!

I'm just speechless Mikey! You have no idea how much I appreciate the fact that you are being a sport when it comes to my ignorance.

I KNOW THAT YOU ARE BOTH RIGHT and probably you both understand and got it to work, but if I don't have a step by step of what EXACTLY I need to be doing for you to assess whether it works or not, it will be challenging

I speak fluent Hebrew and English but when you dominate code you tend to speak like a coder and my brain is detecting it like a new language. Try to guide me like this:

1. Download this script, copy paste, and run it
2. Enter the script and inline xxxx change it to the name of your midi device
3. open a folder and press on F3,F3,F10
4. Hit your controller
5. Does it responds? Did you notice a message coming in?

Something like that.

I promise you guys I can follow directions very well but with specificity
Last edited by elad770 on 03 Nov 2020, 17:32, edited 2 times in total.
elad770
Posts: 81
Joined: 30 Oct 2020, 16:21

Re: Automation Challenge

03 Nov 2020, 17:27

malcev wrote:
03 Nov 2020, 17:21
No, You have to press midi buttons and see msgbox in ahk.
Ok, that's a specific command i can follow! Yeh!

I understood that there's a line in the script called msgbox where the midi message is suppose to appear?
Ok, i can do that

1. Run the script
2. Hit a key on my keboard
3. Enter the script to see if there's something appear in the msgbox

Standby...
elad770
Posts: 81
Joined: 30 Oct 2020, 16:21

Re: Automation Challenge

03 Nov 2020, 17:30

Nothing happened
malcev
Posts: 865
Joined: 12 Aug 2014, 12:37

Re: Automation Challenge

03 Nov 2020, 17:32

Run this script.
Hit your controller.
Do You see any messages?

Code: Select all

Global mode := ""
DllCall("LoadLibrary", "Str", "winmm.dll", "Ptr")
OnMessage(MIDI_OPEN := 0x3C1, "MidiInCallback")
OnMessage(MIDI_CLOSE := 0x3C2, "MidiInCallback")
OnMessage(MIDI_DATA := 0x3C3, "MidiInCallback")
OnMessage(MIDI_LONGDATA := 0x3C4, "MidiInCallback")
OnMessage(MIDI_ERROR := 0x3C5, "MidiInCallback")
OnMessage(MIDI_LONGERROR := 0x3C6, "MidiInCallback")
OnMessage(MIDI_MOREDATA := 0x3CC, "MidiInCallback")
OpenMidiIn()
return

f1::
mode := "listen"
; some code
mode := ""
return



OpenMidiIn()
{
   count := DllCall("winmm.dll\midiOutGetNumDevs") - 1
   if (count = 0)
   {
      msgbox no midi devices
      exitapp
   }
   loop % count
   {
      id := A_Index-1
      hr := DllCall("winmm.dll\midiInOpen", "ptr*", midiInHandle, "uint", id, "ptr", A_ScriptHwnd, "uint", 0, "uint", MIDI_CALLBACK_WINDOW := 0x10000)
      if hr or ErrorLevel
      {
         msgbox % "midiInOpen error `nid = " id "`nhr = " hr "`nErrorLevel = " ErrorLevel
         exitapp
      }
      hr := DllCall("winmm.dll\midiInStart", "ptr", midiInHandle)
      if hr or ErrorLevel
      {
         msgbox % "midiInStart error `nid = " id "`nhr = " hr "`nErrorLevel = " ErrorLevel
         exitapp
      }
   }
   return
}
MidiInCallback(wParam, lParam, msg)
{
   Critical
   highByte := lParam & 0xF0 
   lowByte := lParam & 0x0F
   data1 := (lParam >> 8) & 0xFF
   data2 := (lParam >> 16) & 0xFF
   if (data2 = 0)
      return
   key := highByte "-" lowByte "-" data1
   if (mode = "listen")
   {
      msgbox % "listen`n" key
      return
   }
   ; here get info from ini file if key exist then run its value
   msgbox  % "run`n" key
   return
}
elad770
Posts: 81
Joined: 30 Oct 2020, 16:21

Re: Automation Challenge

03 Nov 2020, 18:10

Yes Sir!!!! Something came up!

I ran the script and hit a regular key, any key.

This message comes up (see attached)
Attachments
Capture_2020_11_03_18_09_24_961.png
Capture_2020_11_03_18_09_24_961.png (81.7 KiB) Viewed 174 times
malcev
Posts: 865
Joined: 12 Aug 2014, 12:37

Re: Automation Challenge

03 Nov 2020, 18:18

Why do You have error in second message box?
What is written there?
elad770
Posts: 81
Joined: 30 Oct 2020, 16:21

Re: Automation Challenge

03 Nov 2020, 18:23

Sorry for that.

Here you go...
Attachments
Capture_2020_11_03_18_22_55_713.png
Capture_2020_11_03_18_22_55_713.png (97.99 KiB) Viewed 165 times
elad770
Posts: 81
Joined: 30 Oct 2020, 16:21

Re: Automation Challenge

03 Nov 2020, 18:26

I had a lot of programs running in the background. LOOPmidi, Midi-osx. Misi2key

I closed everything and this is the message that appears
Attachments
Capture_2020_11_03_18_24_57_968.png
Capture_2020_11_03_18_24_57_968.png (97.99 KiB) Viewed 161 times
malcev
Posts: 865
Joined: 12 Aug 2014, 12:37

Re: Automation Challenge

03 Nov 2020, 18:33

Try to restart computer.
elad770
Posts: 81
Joined: 30 Oct 2020, 16:21

Re: Automation Challenge

03 Nov 2020, 18:42

Same behavior.

The same message comes up. But it does respond to the midi press on my keyboard.

Here's the whole action

https://youtu.be/yDNOGqHIcCw
malcev
Posts: 865
Joined: 12 Aug 2014, 12:37

Re: Automation Challenge

03 Nov 2020, 19:23

Strange, but OK.
I combined mikeyww code with mine.
Change path of ini file to Yours
Then select any file, press f3
Hit your controller
after that You should see key name in inputbox
Press OK.
Hit your controller once again - file will open.
To delete key of you controller - select any file press f3, hit controller button that You want to delete, and write "DEL" before or after key in input box.

Code: Select all

Global ini := "D:\temp\mwMIDI.ini" ; Path to your INI file

setbatchlines -1
Global mode := ""
DllCall("LoadLibrary", "Str", "winmm.dll", "Ptr")
OnMessage(MIDI_OPEN := 0x3C1, "MidiInCallback")
OnMessage(MIDI_CLOSE := 0x3C2, "MidiInCallback")
OnMessage(MIDI_DATA := 0x3C3, "MidiInCallback")
OnMessage(MIDI_LONGDATA := 0x3C4, "MidiInCallback")
OnMessage(MIDI_ERROR := 0x3C5, "MidiInCallback")
OnMessage(MIDI_LONGERROR := 0x3C6, "MidiInCallback")
OnMessage(MIDI_MOREDATA := 0x3CC, "MidiInCallback")
OpenMidiIn()
return

#If WinActive("ahk_class Progman") or WinActive("ahk_class WorkerW") or WinActive("ahk_class CabinetWClass") or WinActive("ahk_class ExploreWClass") 
F3:: ; Map the file to a string
file := Explorer_GetSelection().1 ; Get the path of file selected in Windows Explorer
if !file
{
   msgbox file not selected
   return
}
mode := "listen"
SplitPath, file, fn ; Get the file name
InputBox, newMidi, %fn%, Current mapping: %midi%`n`nEnter new mapping.,, 300, 125 ; Ask user for string assignment
if InStr(newMidi, "del")
{
   newMidi := RegexReplace(newMidi, "[a-zA-Z\s]")
   IniRead, file, %ini%, maps, %newMidi%
   IniDelete, %ini%, maps, % newMidi ; Delete the assignment
   MsgBox, 64, Deleted, % "Mapped: " file "`n`n        To: " newMidi " [DELETED]"
}
else if (newMidi != "")
{
   IniWrite, %file%, %ini%, maps, %newMidi% ; Save the assignment
   {
      If ErrorLevel
         MsgBox, 48, Error, An error occurred during the mapping.
      Else
         MsgBox, 64, Changed, % "Mapped: " file "`n`n        To: " newMidi
   }
}
mode := ""
Return
#IfWinActive


OpenMidiIn()
{
   count := DllCall("winmm.dll\midiOutGetNumDevs") - 1
   if (count = 0)
   {
      msgbox no midi devices
      exitapp
   }
   loop % count
   {
      id := A_Index-1
      hr := DllCall("winmm.dll\midiInOpen", "ptr*", midiInHandle, "uint", id, "ptr", A_ScriptHwnd, "uint", 0, "uint", MIDI_CALLBACK_WINDOW := 0x10000)
      if hr or ErrorLevel
      {
         Continue
         msgbox % "midiInOpen error `nid = " id "`nhr = " hr "`nErrorLevel = " ErrorLevel
         exitapp
      }
      hr := DllCall("winmm.dll\midiInStart", "ptr", midiInHandle)
      if hr or ErrorLevel
      {
         Continue
         msgbox % "midiInStart error `nid = " id "`nhr = " hr "`nErrorLevel = " ErrorLevel
         exitapp
      }
   }
   return
}
MidiInCallback(wParam, lParam, msg)
{
   Critical
   highByte := lParam & 0xF0 
   lowByte := lParam & 0x0F
   data1 := (lParam >> 8) & 0xFF
   data2 := (lParam >> 16) & 0xFF
   if (data2 = 0)
      return
   key := highByte "-" lowByte "-" data1
   if (mode = "listen")
   {
      ControlSetText, Edit1, % key, ahk_class #32770, Enter new mapping.
      return
   }
   IniRead, file, %ini%, maps, %key% ; Find the assigned string that matches this file
   If !(file ~= "ERROR|^$") ; An assigned string was found
      Run, %file%
   return
}

Explorer_GetSelection() {
 ; https://www.autohotkey.com/boards/viewtopic.php?style=17&t=60403#p255256
 array := []
 WinGetClass, winClass, % "ahk_id " (hWnd := WinExist("A"))
 If !(winClass ~="Progman|WorkerW|(Cabinet|Explore)WClass")
  Return
 shellWindows := ComObjCreate("Shell.Application").Windows
 If !(winClass ~= "Progman|WorkerW") {
  For window in shellWindows
   If (hWnd = window.HWND) && (shellFolderView := window.Document)
    Break
 } Else shellFolderView := shellWindows.FindWindowSW(0, 0, SWC_DESKTOP := 8, 0, SWFO_NEEDDISPATCH := 1).Document
 For item in shellFolderView.SelectedItems
  result .= (result = "" ? "" : "`n") . item.Path, array.Push(item.Path)
 If !result
  result := shellFolderView.Folder.Self.Path
 Return array
}
elad770
Posts: 81
Joined: 30 Oct 2020, 16:21

Re: Automation Challenge

03 Nov 2020, 20:33

I'm very excited to try it.

Before I do, one final question because I didn't get it before:

What is INI file? Where is it located?

I understand how to change the path in the script but I still don't know where is it by default?
malcev
Posts: 865
Joined: 12 Aug 2014, 12:37

Re: Automation Challenge

03 Nov 2020, 20:38

It is configuration file.
It can be at any location.
If ini does not exist, script creates it.
elad770
Posts: 81
Joined: 30 Oct 2020, 16:21

Re: Automation Challenge

03 Nov 2020, 20:39

Got it!

Trying it now.. Fingures crossed
elad770
Posts: 81
Joined: 30 Oct 2020, 16:21

Re: Automation Challenge

03 Nov 2020, 20:43

This is the message that i get - error message

- The script excute without errors
- F3 pop up open
- Midi is receiving - a midi message

Upon hitting OK - the error message appears
Attachments
Capture_2020_11_03_20_41_48_444.png
Capture_2020_11_03_20_41_48_444.png (109.5 KiB) Viewed 75 times
elad770
Posts: 81
Joined: 30 Oct 2020, 16:21

Re: Automation Challenge

03 Nov 2020, 20:44

I don't know if this is related but out of curiosity i checked the target folder i placed for the INI file ---> C:\Users\eladb\Desktop\TEST

I saw that no file was created

Maybe i should change to lower case folder name?

Didn't work, same error message appears
malcev
Posts: 865
Joined: 12 Aug 2014, 12:37

Re: Automation Challenge

03 Nov 2020, 20:51

May be there is no folder test on desktop?
Run this code, what errorlevel You will get?

Code: Select all

Global ini := "D:\test.ini" ; Path to your INI file

setbatchlines -1
Global mode := ""
DllCall("LoadLibrary", "Str", "winmm.dll", "Ptr")
OnMessage(MIDI_OPEN := 0x3C1, "MidiInCallback")
OnMessage(MIDI_CLOSE := 0x3C2, "MidiInCallback")
OnMessage(MIDI_DATA := 0x3C3, "MidiInCallback")
OnMessage(MIDI_LONGDATA := 0x3C4, "MidiInCallback")
OnMessage(MIDI_ERROR := 0x3C5, "MidiInCallback")
OnMessage(MIDI_LONGERROR := 0x3C6, "MidiInCallback")
OnMessage(MIDI_MOREDATA := 0x3CC, "MidiInCallback")
OpenMidiIn()
return

#If WinActive("ahk_class Progman") or WinActive("ahk_class WorkerW") or WinActive("ahk_class CabinetWClass") or WinActive("ahk_class ExploreWClass") 
F3:: ; Map the file to a string
file := Explorer_GetSelection().1 ; Get the path of file selected in Windows Explorer
if !file
{
   msgbox file not selected
   return
}
mode := "listen"
SplitPath, file, fn ; Get the file name
InputBox, newMidi, %fn%, Current mapping: %midi%`n`nEnter new mapping.,, 300, 125 ; Ask user for string assignment
if InStr(newMidi, "del")
{
   newMidi := RegexReplace(newMidi, "[a-zA-Z\s]")
   IniRead, file, %ini%, maps, %newMidi%
   IniDelete, %ini%, maps, % newMidi ; Delete the assignment
   MsgBox, 64, Deleted, % "Mapped: " file "`n`n        To: " newMidi " [DELETED]"
}
else if (newMidi != "")
{
   IniWrite, %file%, %ini%, maps, %newMidi% ; Save the assignment
   {
      If ErrorLevel
         MsgBox, 48, Error, An error occurred during the mapping. errorlevel - %errorlevel%
      Else
         MsgBox, 64, Changed, % "Mapped: " file "`n`n        To: " newMidi
   }
}
mode := ""
Return
#IfWinActive


OpenMidiIn()
{
   count := DllCall("winmm.dll\midiOutGetNumDevs") - 1
   if (count = 0)
   {
      msgbox no midi devices
      exitapp
   }
   loop % count
   {
      id := A_Index-1
      hr := DllCall("winmm.dll\midiInOpen", "ptr*", midiInHandle, "uint", id, "ptr", A_ScriptHwnd, "uint", 0, "uint", MIDI_CALLBACK_WINDOW := 0x10000)
      if hr or ErrorLevel
      {
         Continue
         msgbox % "midiInOpen error `nid = " id "`nhr = " hr "`nErrorLevel = " ErrorLevel
         exitapp
      }
      hr := DllCall("winmm.dll\midiInStart", "ptr", midiInHandle)
      if hr or ErrorLevel
      {
         Continue
         msgbox % "midiInStart error `nid = " id "`nhr = " hr "`nErrorLevel = " ErrorLevel
         exitapp
      }
   }
   return
}
MidiInCallback(wParam, lParam, msg)
{
   Critical
   highByte := lParam & 0xF0 
   lowByte := lParam & 0x0F
   data1 := (lParam >> 8) & 0xFF
   data2 := (lParam >> 16) & 0xFF
   if (data2 = 0)
      return
   key := highByte "-" lowByte "-" data1
   if (mode = "listen")
   {
      ControlSetText, Edit1, % key, ahk_class #32770, Enter new mapping.
      return
   }
   IniRead, file, %ini%, maps, %key% ; Find the assigned string that matches this file
   If !(file ~= "ERROR|^$") ; An assigned string was found
      Run, %file%
   return
}

Explorer_GetSelection() {
 ; https://www.autohotkey.com/boards/viewtopic.php?style=17&t=60403#p255256
 array := []
 WinGetClass, winClass, % "ahk_id " (hWnd := WinExist("A"))
 If !(winClass ~="Progman|WorkerW|(Cabinet|Explore)WClass")
  Return
 shellWindows := ComObjCreate("Shell.Application").Windows
 If !(winClass ~= "Progman|WorkerW") {
  For window in shellWindows
   If (hWnd = window.HWND) && (shellFolderView := window.Document)
    Break
 } Else shellFolderView := shellWindows.FindWindowSW(0, 0, SWC_DESKTOP := 8, 0, SWFO_NEEDDISPATCH := 1).Document
 For item in shellFolderView.SelectedItems
  result .= (result = "" ? "" : "`n") . item.Path, array.Push(item.Path)
 If !result
  result := shellFolderView.Folder.Self.Path
 Return array
}

Return to “Ask For Help”

Who is online

Users browsing this forum: ark, Google [Bot], piddly and 33 guests