Skip to content

Commit

Permalink
Fix IME activation issues on macOS 12
Browse files Browse the repository at this point in the history
Cherry-picked from McBopomofo commits 120e1596 and 57d31a82.

See openvanilla/McBopomofo@120e1596 for how
this fixes the various activation issues.
  • Loading branch information
lukhnos committed Nov 25, 2021
1 parent 0ef4c59 commit 6c6703c
Show file tree
Hide file tree
Showing 5 changed files with 104 additions and 14 deletions.
12 changes: 10 additions & 2 deletions OpenVanilla.xcodeproj/project.pbxproj
Expand Up @@ -9,7 +9,6 @@
/* Begin PBXBuildFile section */
6A0BEB6A161573A400FCB59A /* OVBaseModulePreferencesViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = 6A0BEB65161573A400FCB59A /* OVBaseModulePreferencesViewController.m */; };
6A0BEB6B161573A400FCB59A /* OVGeneralPreferencesViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = 6A0BEB67161573A400FCB59A /* OVGeneralPreferencesViewController.m */; };
6A0E0AA11623EDAA004FED10 /* Cocoa.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 6ABBAEF415CD58F90080EE7D /* Cocoa.framework */; };
6A0E0ACE1623EDF5004FED10 /* AppDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = 6A0E0ABE1623EDF5004FED10 /* AppDelegate.m */; };
6A0E0ACF1623EDF5004FED10 /* InfoPlist.strings in Resources */ = {isa = PBXBuildFile; fileRef = 6A0E0ABF1623EDF5004FED10 /* InfoPlist.strings */; };
6A0E0AD01623EDF5004FED10 /* License.rtf in Resources */ = {isa = PBXBuildFile; fileRef = 6A0E0AC11623EDF5004FED10 /* License.rtf */; };
Expand Down Expand Up @@ -43,6 +42,10 @@
6A88323B1605C2D200FBEB85 /* array-shortcode.cin in Copy Array Input Method Tables */ = {isa = PBXBuildFile; fileRef = 6A8832341605C1FE00FBEB85 /* array-shortcode.cin */; };
6A88323C1605C2D600FBEB85 /* array-special.cin in Copy Array Input Method Tables */ = {isa = PBXBuildFile; fileRef = 6A8832351605C1FE00FBEB85 /* array-special.cin */; };
6A88323D1605C2D800FBEB85 /* array30.cin in Copy Array Input Method Tables */ = {isa = PBXBuildFile; fileRef = 6A8832361605C1FE00FBEB85 /* array30.cin */; };
6AA7C2AB274F490400B84443 /* OVInputSourceHelper.m in Sources */ = {isa = PBXBuildFile; fileRef = 6ABBAF2015CD615B0080EE7D /* OVInputSourceHelper.m */; };
6AA7C2AD274F4FC000B84443 /* Cocoa.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 6ABBAEF415CD58F90080EE7D /* Cocoa.framework */; };
6AA7C2AE274F4FC900B84443 /* InputMethodKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 6ABBAF2915CD61B60080EE7D /* InputMethodKit.framework */; };
6AA7C2AF274F4FF000B84443 /* Carbon.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 6ABBAF2B15CD61BE0080EE7D /* Carbon.framework */; };
6AAB3401162E529E00C4C22F /* OVToolTipWindowController.m in Sources */ = {isa = PBXBuildFile; fileRef = 6AAB3400162E529E00C4C22F /* OVToolTipWindowController.m */; };
6AB4A07815ED2BBA00E78557 /* preferences.xib in Resources */ = {isa = PBXBuildFile; fileRef = 6AB4A07715ED2BBA00E78557 /* preferences.xib */; };
6ABBAEF515CD58F90080EE7D /* Cocoa.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 6ABBAEF415CD58F90080EE7D /* Cocoa.framework */; };
Expand Down Expand Up @@ -326,7 +329,9 @@
isa = PBXFrameworksBuildPhase;
buildActionMask = 2147483647;
files = (
6A0E0AA11623EDAA004FED10 /* Cocoa.framework in Frameworks */,
6AA7C2AF274F4FF000B84443 /* Carbon.framework in Frameworks */,
6AA7C2AE274F4FC900B84443 /* InputMethodKit.framework in Frameworks */,
6AA7C2AD274F4FC000B84443 /* Cocoa.framework in Frameworks */,
);
runOnlyForDeploymentPostprocessing = 0;
};
Expand Down Expand Up @@ -843,6 +848,7 @@
files = (
6A0E0ACE1623EDF5004FED10 /* AppDelegate.m in Sources */,
6ACD128623688A23005046C7 /* ArchiveUtil.m in Sources */,
6AA7C2AB274F490400B84443 /* OVInputSourceHelper.m in Sources */,
6A0E0AD41623EDF5004FED10 /* main.m in Sources */,
);
runOnlyForDeploymentPostprocessing = 0;
Expand Down Expand Up @@ -995,6 +1001,7 @@
COMBINE_HIDPI_IMAGES = YES;
GCC_PRECOMPILE_PREFIX_HEADER = YES;
GCC_PREFIX_HEADER = "Source/Mac/Installer/OpenVanillaInstaller-Prefix.pch";
HEADER_SEARCH_PATHS = ../;
INFOPLIST_FILE = "Source/Mac/Installer/OpenVanillaInstaller-Info.plist";
MACOSX_DEPLOYMENT_TARGET = 10.10;
PRODUCT_BUNDLE_IDENTIFIER = "org.openvanilla.${PRODUCT_NAME:rfc1034identifier}";
Expand All @@ -1015,6 +1022,7 @@
COMBINE_HIDPI_IMAGES = YES;
GCC_PRECOMPILE_PREFIX_HEADER = YES;
GCC_PREFIX_HEADER = "Source/Mac/Installer/OpenVanillaInstaller-Prefix.pch";
HEADER_SEARCH_PATHS = ../;
INFOPLIST_FILE = "Source/Mac/Installer/OpenVanillaInstaller-Info.plist";
MACOSX_DEPLOYMENT_TARGET = 10.10;
PRODUCT_BUNDLE_IDENTIFIER = "org.openvanilla.${PRODUCT_NAME:rfc1034identifier}";
Expand Down
79 changes: 67 additions & 12 deletions Source/Mac/Installer/AppDelegate.m
Expand Up @@ -27,6 +27,7 @@

#import "AppDelegate.h"
#import <sys/mount.h>
#import "OVInputSourceHelper.h"

static NSString *const kTargetBin = @"OpenVanilla";
static NSString *const kTargetType = @"app";
Expand Down Expand Up @@ -182,9 +183,9 @@ - (void)removeThenInstallInputMethod
// Schedule the install action in runloop so that the sheet gets a change to dismiss itself.
dispatch_async(dispatch_get_main_queue(), ^{
if (returnCode == NSModalResponseContinue) {
[self installInputMethodWithWarning:NO];
[self installInputMethodWithPreviousExists:YES previousVersionNotFullyDeactivatedWarning:NO];
} else {
[self installInputMethodWithWarning:YES];
[self installInputMethodWithPreviousExists:YES previousVersionNotFullyDeactivatedWarning:YES];
}
});
}];
Expand All @@ -195,7 +196,7 @@ - (void)removeThenInstallInputMethod
}
}

[self installInputMethodWithWarning:NO];
[self installInputMethodWithPreviousExists:NO previousVersionNotFullyDeactivatedWarning:NO];
}

- (void)timerTick:(NSTimer *)timer
Expand All @@ -214,7 +215,7 @@ - (void)timerTick:(NSTimer *)timer
}


- (void)installInputMethodWithWarning:(BOOL)warning
- (void)installInputMethodWithPreviousExists:(BOOL)previousVersionExists previousVersionNotFullyDeactivatedWarning:(BOOL)warning
{
// If the unzipped archive does not exist, this must be a dev-mode installer.
NSString *targetBundle = [_archiveUtil unzipNotarizedArchive];
Expand All @@ -229,12 +230,57 @@ - (void)installInputMethodWithWarning:(BOOL)warning
[NSApp terminate:self];
}

NSArray *installArgs = [NSArray arrayWithObjects:@"install", nil];
NSTask *installTask = [NSTask launchedTaskWithLaunchPath:[kTargetFullBinPartialPath stringByExpandingTildeInPath] arguments:installArgs];
[installTask waitUntilExit];
if ([installTask terminationStatus] != 0) {
RunAlertPanel(NSLocalizedString(@"Install Failed", nil), NSLocalizedString(@"Cannot activate the input method.", nil), NSLocalizedString(@"Cancel", nil), nil, nil);
[NSApp terminate:self];
NSBundle *imeBundle = [NSBundle bundleWithPath:[kTargetPartialPath stringByExpandingTildeInPath]];
NSCAssert(imeBundle != nil, @"Target bundle must exists");
NSURL *imeBundleURL = imeBundle.bundleURL;
NSString *imeIdentifier = imeBundle.bundleIdentifier;

TISInputSourceRef inputSource = [OVInputSourceHelper inputSourceForInputSourceID:imeIdentifier];

// if this IME name is not found in the list of available IMEs
if (!inputSource) {
NSLog(@"Registering input source %@ at %@.", imeIdentifier, imeBundleURL.absoluteString);
// then register
BOOL status = [OVInputSourceHelper registerInputSource:imeBundleURL];

if (!status) {
NSString *message = [NSString stringWithFormat:NSLocalizedString(@"Cannot register input source %@ at %@.", nil), imeIdentifier, imeBundleURL.absoluteString];
RunAlertPanel(NSLocalizedString(@"Fatal Error", nil), message, NSLocalizedString(@"Abort", nil), nil, nil);
[self endAppWithDelay];
return;
}

inputSource = [OVInputSourceHelper inputSourceForInputSourceID:imeIdentifier];
// if it still doesn't register successfully, bail.
if (!inputSource) {
NSString *message = [NSString stringWithFormat:NSLocalizedString(@"Cannot find input source %@ after registration.", nil), imeIdentifier];
RunAlertPanel(NSLocalizedString(@"Fatal Error", nil), message, NSLocalizedString(@"Abort", nil), nil, nil);
[self endAppWithDelay];
return;
}
}

BOOL isMacOS12OrAbove = NO;
if (@available(macOS 12.0, *)) {
NSLog(@"macOS 12 or later detected.");
isMacOS12OrAbove = YES;
} else {
NSLog(@"Installer runs with the pre-macOS 12 flow.");
}

// If the IME is not enabled, enable it. Also, unconditionally enable it on macOS 12.0+,
// as the kTISPropertyInputSourceIsEnabled can still be true even if the IME is *not*
// enabled in the user's current set of IMEs (which means the IME does not show up in
// the user's input menu).
BOOL mainInputSourceEnabled = [OVInputSourceHelper inputSourceEnabled:inputSource];
if (!mainInputSourceEnabled || isMacOS12OrAbove) {

mainInputSourceEnabled = [OVInputSourceHelper enableInputSource:inputSource];
if (mainInputSourceEnabled) {
NSLog(@"Input method enabled: %@", imeIdentifier);
} else {
NSLog(@"Failed to enable input method: %@", imeIdentifier);
}
}

if (_upgradingFromLegacy) {
Expand Down Expand Up @@ -263,13 +309,22 @@ - (void)installInputMethodWithWarning:(BOOL)warning
if (warning) {
RunAlertPanel(NSLocalizedString(@"Attention", nil), NSLocalizedString(@"OpenVanilla is upgraded, but please log out or reboot for the new version to be fully functional.", nil), NSLocalizedString(@"OK", nil), nil, nil);
} else {
RunAlertPanel(NSLocalizedString(@"Installation Successful", nil), NSLocalizedString(@"OpenVanilla is ready to use.", nil), NSLocalizedString(@"OK", nil), nil, nil);
// Only prompt a warning if pre-macOS 12. The flag is not indicative of anything meaningful due to the need of user intervention in Prefernces.app on macOS 12.
if (!mainInputSourceEnabled && !isMacOS12OrAbove) {
RunAlertPanel(NSLocalizedString(@"Warning", nil), NSLocalizedString(@"Input method may not be fully enabled. Please enable it through System Preferences > Keyboard > Input Sources.", nil), NSLocalizedString(@"Continue", nil), nil, nil);
} else {
RunAlertPanel(NSLocalizedString(@"Installation Successful", nil), NSLocalizedString(@"OpenVanilla is ready to use.", nil), NSLocalizedString(@"OK", nil), nil, nil);
}
}
}

[self endAppWithDelay];
}

- (void)endAppWithDelay
{
[[NSApplication sharedApplication] performSelector:@selector(terminate:) withObject:self afterDelay:0.1];
}


- (IBAction)cancelAction:(id)sender
{
Expand Down
9 changes: 9 additions & 0 deletions Source/Mac/Installer/en.lproj/Localizable.strings
Expand Up @@ -46,3 +46,12 @@
"Stopping the old version. This may take up to one minute…" = "Stopping the old version. This may take up to one minute…";
"Attention" = "Attention";
"OpenVanilla is upgraded, but please log out or reboot for the new version to be fully functional." = "OpenVanilla is upgraded, but please log out or reboot for the new version to be fully functional.";

"Fatal Error" = "Fatal Error";
"Abort" = "Abort";
"Cannot register input source %@ at %@." = "Cannot register input source %@ at %@.";
"Cannot find input source %@ after registration." = "Cannot find input source %@ after registration.";

"Warning" = "Warning";
"Input method may not be fully enabled. Please enable it through System Preferences > Keyboard > Input Sources." = "Input method may not be fully enabled. Please enable it through System Preferences > Keyboard > Input Sources.";
"Continue" = "Continue";
9 changes: 9 additions & 0 deletions Source/Mac/Installer/zh-Hans.lproj/Localizable.strings
Expand Up @@ -45,3 +45,12 @@
"Finish" = "结束";
"Attention" = "请注意";
"OpenVanilla is upgraded, but please log out or reboot for the new version to be fully functional." = "OpenVanilla 安装完成,但建议您登出或重新开机,以便顺利使用新版。";

"Fatal Error" = "安装错误";
"Abort" = "放弃安装";
"Cannot register input source %@ at %@." = "无法从文件位置 %2$@ 安装输入法 \"%1$@\"。";
"Cannot find input source %@ after registration." = "在注册完输入法 \"%@\" 仍然无法找到输入法。";

"Warning" = "安装不完整";
"Input method may not be fully enabled. Please enable it through System Preferences > Keyboard > Input Sources." = "输入法已经安装好,但可能没有完全激活。请从 “系统偏好设置” > “键盘” > “输入法” 分页加入输入法。";
"Continue" = "继续";
9 changes: 9 additions & 0 deletions Source/Mac/Installer/zh-Hant.lproj/Localizable.strings
Expand Up @@ -45,3 +45,12 @@
"Finish" = "結束";
"Attention" = "請注意";
"OpenVanilla is upgraded, but please log out or reboot for the new version to be fully functional." = "OpenVanilla 安裝完成,但建議您登出或重新開機,以便順利使用新版。";

"Fatal Error" = "安裝錯誤";
"Abort" = "放棄安裝";
"Cannot register input source %@ at %@." = "無法從檔案位置 %2$@ 安裝輸入法 \"%1$@\"。";
"Cannot find input source %@ after registration." = "在註冊完輸入法 \"%@\" 仍然無法找到輸入法。";

"Warning" = "安裝不完整";
"Input method may not be fully enabled. Please enable it through System Preferences > Keyboard > Input Sources." = "輸入法已經安裝好,但可能沒有完全啟用。請從「系統偏好設定」 > 「鍵盤」 > 「輸入方式」分頁加入輸入法。";
"Continue" = "繼續";

0 comments on commit 6c6703c

Please sign in to comment.