Keyman not Recognized by "Set Keyboard Layout To"

I have the Keyman app installed. It shows up in the system keyboard list:

image

but it is not recognized by "Set Keyboard Layout To".

image

Keyman is installed with a dmg file. I guess this is the reason. Is there a way to switch to Keyman with a shortcut?

Hey Martin,

Hmm... If it's seen by the system it ought to be seen by Keyboard Maestro.

@peternlewis?

In the meantime you could try using the system keyboard preferences to assign a global keyboard shortcut to “Keyman”.

-Chris

I was looking for the setting but could not find where it is. Can you point me to the right place? Here are where I have looked:

image

image

Put it under “All Applications” in “App Shortcuts”:

image

If it doesn't work reboot your system. Sometimes that will work.

-Chris

Thanks. But I don't know what to put in the Menu Title field.

image

Putting Keyman there does not help.
image

Unless @peternlewis comes up with a native KM solution, I've found a temporary solution here:

Following the solution provided by sbnc.eu on the page above, I made a keyman.m file:

#include <Carbon/Carbon.h>

int main (int argc, const char * argv[]) {
    NSArray* sources = CFBridgingRelease(TISCreateInputSourceList((__bridge CFDictionaryRef)@{ (__bridge NSString*)kTISPropertyInputSourceID : @"keyman.inputmethod.Keyman" }, FALSE));
    TISInputSourceRef source = (__bridge TISInputSourceRef)sources[0];
    OSStatus status = TISSelectInputSource(source);
    if (status != noErr)
        return -1;

    return 0;
}

The only thing I needed was to find keyman.inputmethod.Keyman in the ~/Library/Preferences/com.apple.HIToolbox.plist file and replace the one in the sample code.
Then I made an executable file out of the keyman.m file and named it keyman.

image

Once that is set up, the only thing I needed is to execute it in KM. It works great!
image

1 Like

Check the Engine.log file to see if there is a reported error.

They keyboard needs to have a kTISPropertyInputSourceCategory or kTISCategoryKeyboardInputSource and a kTISPropertyInputSourceType of kTISTypeKeyboardLayout or kTISTypeKeyboardInputMode to be recognised by Keyboard Maestro as a keyboard.

It only checks the former when setting the keyboard layout, so its possible you could use the Set Keyboard Layout action, export it as XML, change the XML to the keyman.inputmethod.Keyman ID, reimport the action and it might work.

The developers might be able to adjust the category or type, or if they are using a different category or type for some reason, I may be able to support another type.

2 Likes

You are genius! I just tried and it worked!

One question/problem: the switch sometimes is not complete. What I mean is: The keyboard icon shows that the keyboard has been switched to the target layout, but when I start typing, it is still outputting English letters. It happens to all other non-English keyboards.

It doesn't matter which layout I'm switching from or to, when the switch is incomplete, it will output only English letters.

Squirrel best illustrates the problem, as it as settings. When the switch is incomplete, all settings for Squirrel are not available. Only grey dots are shown.
image

Switch back to English, and switch to Squirrel, the switch is complete, then all settings will show (Deploy, Syn user data, etc.):
image

Any idea?

Not really, I have found the changing of the keyboard layout to be somewhat inconsistent. I suspect part of the system is caching things and the change is not made in its entirety. The code you posted earlier is essentially the same as what Keyboard Maestro does, so I expect it has the same issue.

Not sure what can be done about it to make it more robust.

Found a more reliable solution with AppleScript:

-- it looks like it needs to execute twice to work reliably.
changeKeyboardLayout("Squirrel")
changeKeyboardLayout("Squirrel")

on changeKeyboardLayout(layoutName)
	tell application "System Events" to ÂŹ
		tell application process "TextInputMenuAgent" to ÂŹ
			tell menu bar item 1 of menu bar 2
				click
				delay 0.1
				click menu item layoutName of menu 1
			end tell
end changeKeyboardLayout

Update:
I have found an app that does the job perfectly.
The developer explained the issues with CJK languages:

@peternlewis, can this bring some improvement to the way KM handles keyboard layout?

1 Like

No. UI scripting the Keyboard switch source input is something you can do with tools provided by Keyboard Maestro, like Execute AppleScript, but not something I am likely to support directly (though I do do it for the Fast User Switch).

It is unfortunately that the system APIs (which are not deprecated) do not always work reliably for these things.

1 Like

Thanks, Peter. Your reply prompted me to look into the code of the Github project. I know very little about AppleScript, but I found a familiar part. I copied that section out and found out it was exactly what I need.

This is the new code:

changeKeyboardLayout("Squirrel")

on changeKeyboardLayout(layoutName)
	tell application "System Events"
		tell process "TextInputMenuAgent"
			click menu item layoutName of menu 1 of menu bar item 1 of menu bar 2
			click menu bar item 1 of menu bar 2
		end tell
	end tell
end changeKeyboardLayout

Compared with the earlier one above, the difference is small. But I was still having trouble with that earlier one, while this new code works great so far.

(I'm gonna mark this post as solution, since I can do the switch with KM only and I don't have to install another app).

1 Like

Update:
macism appears to have solved the problem. I've been using it for about a whole day, and its working flawlessly.