diff --git a/Installer/Resources/Base.lproj/MainMenu.xib b/Installer/Resources/Base.lproj/MainMenu.xib index b0282031..2a204c55 100644 --- a/Installer/Resources/Base.lproj/MainMenu.xib +++ b/Installer/Resources/Base.lproj/MainMenu.xib @@ -61,6 +61,50 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + @@ -177,7 +221,7 @@ vChewing macOS Development: Shiki Suen, Hiraku Wang, etc.
vChewing Phrase Data - DISCLAIMER: The vChewing project, having no relationship of cooperation or affiliation with the OpenVanilla project, is not responsible for the phrase database shipped in the original McBopomofo project. Certain geopolitical and ideological contents, which are potentially harmful to the global spread of this software, have been removed from vChewing official phrase database. + DISCLAIMER: The vChewing project, having no relationship of cooperation or affiliation with the OpenVanilla project, is not responsible for the phrase database shipped in the original McBopomofo project. Certain geopolitical and ideological contents, which are potentially harmful to the global spread of this software, are not included in vChewing official phrase database. diff --git a/Installer/Resources/en.lproj/MainMenu.strings b/Installer/Resources/en.lproj/MainMenu.strings index c94af990..8c874b35 100644 --- a/Installer/Resources/en.lproj/MainMenu.strings +++ b/Installer/Resources/en.lproj/MainMenu.strings @@ -50,8 +50,8 @@ /* Class = "NSTextFieldCell"; title = "version_placeholder"; ObjectID = "JRP-At-H9q"; */ // "JRP-At-H9q.title" = "version_placeholder"; -/* Class = "NSTextFieldCell"; title = "DISCLAIMER: The vChewing project, having no relationship of cooperation or affiliation with the OpenVanilla project, is not responsible for the phrase database shipped in the original McBopomofo project. Certain geopolitical and ideological contents, which are potentially harmful to the global spread of this software, have been removed from vChewing official phrase database."; ObjectID = "Q9M-ni-kUM"; */ -"Q9M-ni-kUM.title" = "DISCLAIMER: The vChewing project, having no relationship of cooperation or affiliation with the OpenVanilla project, is not responsible for the phrase database shipped in the original McBopomofo project. Certain geopolitical and ideological contents, which are potentially harmful to the global spread of this software, have been removed from vChewing official phrase database."; +/* Class = "NSTextFieldCell"; title = "DISCLAIMER: The vChewing project, having no relationship of cooperation or affiliation with the OpenVanilla project, is not responsible for the phrase database shipped in the original McBopomofo project. Certain geopolitical and ideological contents, which are potentially harmful to the global spread of this software, are not included in vChewing official phrase database."; ObjectID = "Q9M-ni-kUM"; */ +"Q9M-ni-kUM.title" = "DISCLAIMER: The vChewing project, having no relationship of cooperation or affiliation with the OpenVanilla project, is not responsible for the phrase database shipped in the original McBopomofo project. Certain geopolitical and ideological contents, which are potentially harmful to the global spread of this software, are not included in vChewing official phrase database."; /* Class = "NSTextFieldCell"; title = "Derived from OpenVanilla McBopopmofo Project."; ObjectID = "QYf-Nf-hoi"; */ "QYf-Nf-hoi.title" = "Derived from OpenVanilla McBopopmofo Project."; diff --git a/Installer/Resources/ja.lproj/MainMenu.strings b/Installer/Resources/ja.lproj/MainMenu.strings index 03c967d2..9ac68c7b 100644 --- a/Installer/Resources/ja.lproj/MainMenu.strings +++ b/Installer/Resources/ja.lproj/MainMenu.strings @@ -50,8 +50,8 @@ /* Class = "NSTextFieldCell"; title = "version_placeholder"; ObjectID = "JRP-At-H9q"; */ "JRP-At-H9q.title" = "version_placeholder"; -/* Class = "NSTextFieldCell"; title = "DISCLAIMER: The vChewing project, having no relationship of cooperation or affiliation with the OpenVanilla project, is not responsible for the phrase database shipped in the original McBopomofo project. Certain geopolitical and ideological contents, which are potentially harmful to the global spread of this software, have been removed from vChewing official phrase database."; ObjectID = "Q9M-ni-kUM"; */ -"Q9M-ni-kUM.title" = "免責事項:vChewing Project は、OpenVanilla と協力関係や提携関係にあるわけではなく、OpenVanilla が小麦注音プロジェクトに同梱した辞書データについて、vChewing Project は一切責任負い兼ねる。特定な地政学的・観念形態的な内容は、vChewing アプリの世界的な普及に妨害する恐れがあるため、vChewing 公式辞書データから削除済みである。"; +/* Class = "NSTextFieldCell"; title = "DISCLAIMER: The vChewing project, having no relationship of cooperation or affiliation with the OpenVanilla project, is not responsible for the phrase database shipped in the original McBopomofo project. Certain geopolitical and ideological contents, which are potentially harmful to the global spread of this software, are not included in vChewing official phrase database."; ObjectID = "Q9M-ni-kUM"; */ +"Q9M-ni-kUM.title" = "免責事項:vChewing Project は、OpenVanilla と協力関係や提携関係にあるわけではなく、OpenVanilla が小麦注音プロジェクトに同梱した辞書データについて、vChewing Project は一切責任負い兼ねる。特定な地政学的・観念形態的な内容は、vChewing アプリの世界的な普及に妨害する恐れがあるため、vChewing 公式辞書データに不収録。"; /* Class = "NSTextFieldCell"; title = "Derived from OpenVanilla McBopopmofo Project."; ObjectID = "QYf-Nf-hoi"; */ "QYf-Nf-hoi.title" = "OpenVanilla 小麦注音プロジェクトから派生。"; diff --git a/Installer/Resources/zh-Hans.lproj/MainMenu.strings b/Installer/Resources/zh-Hans.lproj/MainMenu.strings index bbee8893..a1f23917 100644 --- a/Installer/Resources/zh-Hans.lproj/MainMenu.strings +++ b/Installer/Resources/zh-Hans.lproj/MainMenu.strings @@ -50,8 +50,8 @@ /* Class = "NSTextFieldCell"; title = "version_placeholder"; ObjectID = "JRP-At-H9q"; */ // "JRP-At-H9q.title" = "version_placeholder"; -/* Class = "NSTextFieldCell"; title = "DISCLAIMER: The vChewing project, having no relationship of cooperation or affiliation with the OpenVanilla project, is not responsible for the phrase database shipped in the original McBopomofo project. Certain geopolitical and ideological contents, which are potentially harmful to the global spread of this software, have been removed from vChewing official phrase database."; ObjectID = "Q9M-ni-kUM"; */ -"Q9M-ni-kUM.title" = "免责声明:威注音专案对小麦注音官方专案内赠的小麦注音原版词库内容不负任何责任。威注音输入法专用的威注音官方词库已清除任何「会在法理上妨碍威注音在全球传播」的「与地缘政治及政治意识形态有关的」内容。威注音专案与 OpenVanilla 专案之间无合作关系、无隶属关系。"; +/* Class = "NSTextFieldCell"; title = "DISCLAIMER: The vChewing project, having no relationship of cooperation or affiliation with the OpenVanilla project, is not responsible for the phrase database shipped in the original McBopomofo project. Certain geopolitical and ideological contents, which are potentially harmful to the global spread of this software, are not included in vChewing official phrase database."; ObjectID = "Q9M-ni-kUM"; */ +"Q9M-ni-kUM.title" = "免责声明:威注音专案对小麦注音官方专案内赠的小麦注音原版词库内容不负任何责任。威注音输入法专用的威注音官方词库不包含任何「会在法理上妨碍威注音在全球传播」的「与地缘政治及政治意识形态有关的」内容。威注音专案与 OpenVanilla 专案之间无合作关系、无隶属关系。"; /* Class = "NSTextFieldCell"; title = "Derived from OpenVanilla McBopopmofo Project."; ObjectID = "QYf-Nf-hoi"; */ "QYf-Nf-hoi.title" = "该专案由 OpenVanilla 小麦注音专案衍生而来。"; diff --git a/Installer/Resources/zh-Hant.lproj/MainMenu.strings b/Installer/Resources/zh-Hant.lproj/MainMenu.strings index 7e11c4a0..2a399d2f 100644 --- a/Installer/Resources/zh-Hant.lproj/MainMenu.strings +++ b/Installer/Resources/zh-Hant.lproj/MainMenu.strings @@ -50,8 +50,8 @@ /* Class = "NSTextFieldCell"; title = "version_placeholder"; ObjectID = "JRP-At-H9q"; */ // "JRP-At-H9q.title" = "version_placeholder"; -/* Class = "NSTextFieldCell"; title = "DISCLAIMER: The vChewing project, having no relationship of cooperation or affiliation with the OpenVanilla project, is not responsible for the phrase database shipped in the original McBopomofo project. Certain geopolitical and ideological contents, which are potentially harmful to the global spread of this software, have been removed from vChewing official phrase database."; ObjectID = "Q9M-ni-kUM"; */ -"Q9M-ni-kUM.title" = "免責聲明:威注音專案對小麥注音官方專案內贈的小麥注音原版詞庫內容不負任何責任。威注音輸入法專用的威注音官方詞庫已清除任何「會在法理上妨礙威注音在全球傳播」的「與地緣政治及政治意識形態有關的」內容。威註音專案與 OpenVanilla 專案之間無合作關係、無隸屬關係。"; +/* Class = "NSTextFieldCell"; title = "DISCLAIMER: The vChewing project, having no relationship of cooperation or affiliation with the OpenVanilla project, is not responsible for the phrase database shipped in the original McBopomofo project. Certain geopolitical and ideological contents, which are potentially harmful to the global spread of this software, are not included in vChewing official phrase database."; ObjectID = "Q9M-ni-kUM"; */ +"Q9M-ni-kUM.title" = "免責聲明:威注音專案對小麥注音官方專案內贈的小麥注音原版詞庫內容不負任何責任。威注音輸入法專用的威注音官方詞庫不包含任何「會在法理上妨礙威注音在全球傳播」的「與地緣政治及政治意識形態有關的」內容。威註音專案與 OpenVanilla 專案之間無合作關係、無隸屬關係。"; /* Class = "NSTextFieldCell"; title = "Derived from OpenVanilla McBopopmofo Project."; ObjectID = "QYf-Nf-hoi"; */ "QYf-Nf-hoi.title" = "該專案由 OpenVanilla 小麥注音專案衍生而來。"; diff --git a/Installer/pkgPostInstall.sh b/Installer/pkgPostInstall.sh index 9805eb5f..babb41e8 100644 --- a/Installer/pkgPostInstall.sh +++ b/Installer/pkgPostInstall.sh @@ -1,2 +1,18 @@ #!/bin/sh -~/Library/Input\ Methods/vChewing.app/Contents/MacOS/vChewing install --all +loggedInUser=$(stat -f%Su /dev/console) + +# First, copy the wrongfully installed contents to the right location: +cp -r /Library/Input\ Methods/vChewing.app /Users/$(stat -f%Su /dev/console)/Library/Input\ Methods/ || true +cp -r /Library/Keyboard\ Layouts/vChewing* /Users/$(stat -f%Su /dev/console)/Library/Keyboard\ Layouts/ || true +chown "$loggedInUser" /Users/$(stat -f%Su /dev/console)/Library/Input\ Methods/vChewing.app || true +chown "$loggedInUser" /Users/$(stat -f%Su /dev/console)/Library/Keyboard\ Layouts/vChewing* || true + +sleep 1 + +# Second, clean the wrongfully installed contents: +rm -rf /Library/Input\ Methods/vChewing.app || true +rm -rf /Library/Keyboard\ Layouts/vChewing* || true +sleep 1 + +# Finally, register the input method: +/Users/$(stat -f%Su /dev/console)/Library/Input\ Methods/vChewing.app/Contents/MacOS/vChewing install --all || true diff --git a/Installer/pkgPreInstall.sh b/Installer/pkgPreInstall.sh index 82d041b5..fc3cb9a6 100644 --- a/Installer/pkgPreInstall.sh +++ b/Installer/pkgPreInstall.sh @@ -1,5 +1,18 @@ #!/bin/sh -killall vChewing +loggedInUser=$(stat -f%Su /dev/console) + +killall vChewing || true + +if [ "$loggedInUser" = root ]; then + rm -rf /Library/Input\ Methods/vChewing.app || true + rm -rf /Library/Keyboard\ Layouts/vChewingKeyLayout.bundle || true + rm -rf /Library/Keyboard\ Layouts/vChewing\ Dachen.keylayout || true + rm -rf /Library/Keyboard\ Layouts/vChewing\ ETen.keylayout || true + rm -rf /Library/Keyboard\ Layouts/vChewing\ FakeSeigyou.keylayout || true + rm -rf /Library/Keyboard\ Layouts/vChewing\ IBM.keylayout || true + rm -rf /Library/Keyboard\ Layouts/vChewing\ MiTAC.keylayout || true +fi + rm -rf ~/Library/Input\ Methods/vChewing.app rm -rf ~/Library/Keyboard\ Layouts/vChewingKeyLayout.bundle rm -rf ~/Library/Keyboard\ Layouts/vChewing\ Dachen.keylayout diff --git a/Installer/pkgTextWarning-CHS.txt b/Installer/pkgTextWarning-CHS.txt index 673bf003..d176751f 100644 --- a/Installer/pkgTextWarning-CHS.txt +++ b/Installer/pkgTextWarning-CHS.txt @@ -1,5 +1,9 @@ 注意事项: -一、macOS 10.x-11.x 系统有 Bug、令该安装程式无法自动将安装目标设为当前使用者资料夹。如果您在 macOS 12 Monterey 之前的系统安装该输入法的话,请务必「手动」将安装目的地设为当前使用者资料夹。否则,当您今后(在升级系统之后)升级输入法的时候,可能会出现各种混乱情况。 +一、macOS 10.x-11.x 系统有 Bug、令该安装程式无法自动将安装目标设为当前使用者资料夹。如果您在 macOS 12 Monterey 之前的系统安装该输入法的话,请务必「手动」将安装目的地设为当前使用者资料夹。否则,当您今后(在升级系统之后)升级输入法的时候,可能会出现各种混乱情况。下述终端指令可修复这类混乱情况: + +sudo /Users/$(stat -f%Su /dev/console)/Library/Input\ Methods/vChewing.app/Contents/MacOS/vChewing uninstall + +该指令会将任何安装到错误位置的档案全部删除。 二、安装完毕之后,如果输入法无法正常使用的话,请重新登入即可。 diff --git a/Installer/pkgTextWarning-CHT.txt b/Installer/pkgTextWarning-CHT.txt index 25fd8f4f..bd125749 100644 --- a/Installer/pkgTextWarning-CHT.txt +++ b/Installer/pkgTextWarning-CHT.txt @@ -1,5 +1,9 @@ 注意事項: -一、macOS 10.x-11.x 系統有 Bug、令該安裝程式無法自動將安裝目標設為當前使用者資料夾。如果您在 macOS 12 Monterey 之前的系統安裝該輸入法的話,請務必「手動」將安裝目的地設為當前使用者資料夾。否則,當您今後(在升級系統之後)升級輸入法的時候,可能會出現各種混亂情況。 +一、macOS 10.x-11.x 系統有 Bug、令該安裝程式無法自動將安裝目標設為當前使用者資料夾。如果您在 macOS 12 Monterey 之前的系統安裝該輸入法的話,請務必「手動」將安裝目的地設為當前使用者資料夾。否則,當您今後(在升級系統之後)升級輸入法的時候,可能會出現各種混亂情況。下述終端指令可修復這類混亂情況: + +sudo /Users/$(stat -f%Su /dev/console)/Library/Input\ Methods/vChewing.app/Contents/MacOS/vChewing uninstall + +該指令會將任何安裝到錯誤位置的檔案全部刪除。 二、安裝完畢之後,如果輸入法無法正常使用的話,請重新登入即可。 diff --git a/Installer/pkgTextWarning-ENU.txt b/Installer/pkgTextWarning-ENU.txt index 99601c11..a45e3f2f 100644 --- a/Installer/pkgTextWarning-ENU.txt +++ b/Installer/pkgTextWarning-ENU.txt @@ -2,4 +2,8 @@ Notice: Due to a bug in macOS 10.x and 11.x, if you are trying to install this input method on macOS releases earlier than macOS 12 Monterey, PLEASE manually choose the install target to the user folder. Otherwise, there will be problems when you are trying to install this input method to later versions when your OS gets upgraded to macOS 12 Monterey or later. +The following terminal command can solve such probelems by removing all incorrectly-installed files: + +sudo /Users/$(stat -f%Su /dev/console)/Library/Input\ Methods/vChewing.app/Contents/MacOS/vChewing uninstall + Also, feel free to logout and re-login if the input method doesn't work after installation. diff --git a/Installer/pkgTextWarning-JPN.txt b/Installer/pkgTextWarning-JPN.txt index 51689bc3..db175173 100644 --- a/Installer/pkgTextWarning-JPN.txt +++ b/Installer/pkgTextWarning-JPN.txt @@ -1,6 +1,10 @@ ご注意: -macOS 12 Monterey 以前の OS(macOS 10.x-11.x)のバグのため、macOS 10.x-11.x でインストールする場合、この入力アプリ必ずご自分でユーザーフォルダをインストール先と設定してください。然もないと、いずれ macOS 12 にアップデートし、この入力アプリのもっと新しいバージョンをインストールする時に、予測できない支障が生ずる恐れがあります。 +macOS 12 Monterey 以前の OS(macOS 10.x-11.x)のバグのため、macOS 10.x-11.x でインストールする場合、この入力アプリ必ずご自分でユーザーフォルダをインストール先と設定してください。然もないと、いずれ macOS 12 にアップデートし、この入力アプリのもっと新しいバージョンをインストールする時に、予測できない支障が生ずる恐れがあります。下記のターミナル指令を実行すれば、この様な支障を解決することができます: + +sudo /Users/$(stat -f%Su /dev/console)/Library/Input\ Methods/vChewing.app/Contents/MacOS/vChewing uninstall + +これで、間違ったところへ実装したファイルだけは消されます。 そして、インストール直後、入力アプリがうまく使えない場合、再ログインすれば済ませることです。 diff --git a/LICENSE-CHS.txt b/LICENSE-CHS.txt index 2c8380e6..4cb6a2b5 100644 --- a/LICENSE-CHS.txt +++ b/LICENSE-CHS.txt @@ -1,3 +1,5 @@ +免责声明:威注音专案对小麦注音官方专案内赠的小麦注音原版词库内容不负任何责任。威注音输入法专用的威注音官方词库不包含任何「会在法理上妨碍威注音在全球传播」的「与地缘政治及政治意识形态有关的」内容。威注音专案与 OpenVanilla 专案之间无合作关系、无隶属关系。 + vChewing macOS: MIT-NTL License 麻理(去商标)授权合约 © 2011-2022 OpenVanilla Project & © 2021-2022 vChewing Project. diff --git a/LICENSE-CHT.txt b/LICENSE-CHT.txt index 518d06f8..c729ba13 100644 --- a/LICENSE-CHT.txt +++ b/LICENSE-CHT.txt @@ -1,3 +1,5 @@ +免責聲明:威注音專案對小麥注音官方專案內贈的小麥注音原版詞庫內容不負任何責任。威注音輸入法專用的威注音官方詞庫不包含任何「會在法理上妨礙威注音在全球傳播」的「與地緣政治及政治意識形態有關的」內容。威註音專案與 OpenVanilla 專案之間無合作關係、無隸屬關係。 + vChewing macOS: MIT-NTL License 麻理(去商標)授權合約 © 2011-2022 OpenVanilla Project & © 2021-2022 vChewing Project. diff --git a/LICENSE-JPN.txt b/LICENSE-JPN.txt index 28ecbc4c..bdfc2fb4 100644 --- a/LICENSE-JPN.txt +++ b/LICENSE-JPN.txt @@ -1,3 +1,5 @@ +免責事項:vChewing Project は、OpenVanilla と協力関係や提携関係にあるわけではなく、OpenVanilla が小麦注音プロジェクトに同梱した辞書データについて、vChewing Project は一切責任負い兼ねる。特定な地政学的・観念形態的な内容は、vChewing アプリの世界的な普及に妨害する恐れがあるため、vChewing 公式辞書データに不収録。 + vChewing macOS: MIT商標不許可ライセンス (MIT-NTL License) © 2011-2022 OpenVanilla Project & © 2021-2022 vChewing Project. diff --git a/LICENSE.txt b/LICENSE.txt index 319b514d..071de4ab 100644 --- a/LICENSE.txt +++ b/LICENSE.txt @@ -1,3 +1,5 @@ +DISCLAIMER: The vChewing project, having no relationship of cooperation or affiliation with the OpenVanilla project, is not responsible for the phrase database shipped in the original McBopomofo project. Certain geopolitical and ideological contents, which are potentially harmful to the global spread of this software, are not included in vChewing official phrase database. + vChewing macOS: MIT-NTL License © 2011-2022 OpenVanilla Project & © 2021-2022 vChewing Project. diff --git a/Source/Data b/Source/Data index 17fa40cc..bc331e0d 160000 --- a/Source/Data +++ b/Source/Data @@ -1 +1 @@ -Subproject commit 17fa40cc6e19cc31e4aefa8d3182a98c6596695f +Subproject commit bc331e0dd76e4888ac2ef1d945b191994b86fbf4 diff --git a/Source/Modules/AppDelegate.swift b/Source/Modules/AppDelegate.swift index b8bcf8df..7d69bd11 100644 --- a/Source/Modules/AppDelegate.swift +++ b/Source/Modules/AppDelegate.swift @@ -162,6 +162,7 @@ class AppDelegate: NSObject, NSApplicationDelegate, ctlNonModalAlertWindowDelega private var checkTask: URLSessionTask? private var updateNextStepURL: URL? private var fsStreamHelper = FSEventStreamHelper(path: mgrLangModel.dataFolderPath(isDefaultFolder: false), queue: DispatchQueue(label: "vChewing User Phrases")) + private var currentAlertType: String = "" // 補上 dealloc deinit { @@ -236,7 +237,7 @@ class AppDelegate: NSObject, NSApplicationDelegate, ctlNonModalAlertWindowDelega let nextUpdateDate = Date(timeInterval: kNextCheckInterval, since: Date()) UserDefaults.standard.set(nextUpdateDate, forKey: kNextUpdateCheckDateKey) - checkTask = VersionUpdateApi.check(forced: forced) { result in + checkTask = VersionUpdateApi.check(forced: forced) { [self] result in defer { self.checkTask = nil } @@ -252,6 +253,7 @@ class AppDelegate: NSObject, NSApplicationDelegate, ctlNonModalAlertWindowDelega report.remoteVersion, report.versionDescription) IME.prtDebugIntel("vChewingDebug: \(content)") + self.currentAlertType = "Update" ctlNonModalAlertWindow.shared.show(title: NSLocalizedString("New Version Available", comment: ""), content: content, confirmButtonTitle: NSLocalizedString("Visit Website", comment: ""), cancelButtonTitle: NSLocalizedString("Not Now", comment: ""), cancelAsDefault: false, delegate: self) NSApp.setActivationPolicy(.accessory) case .noNeedToUpdate, .ignored: @@ -264,6 +266,7 @@ class AppDelegate: NSObject, NSApplicationDelegate, ctlNonModalAlertWindowDelega let content = String(format: NSLocalizedString("There may be no internet connection or the server failed to respond.\n\nError message: %@", comment: ""), message) let buttonTitle = NSLocalizedString("Dismiss", comment: "") IME.prtDebugIntel("vChewingDebug: \(content)") + self.currentAlertType = "Update" ctlNonModalAlertWindow.shared.show(title: title, content: content, confirmButtonTitle: buttonTitle, cancelButtonTitle: nil, cancelAsDefault: false, delegate: nil) NSApp.setActivationPolicy(.accessory) default: @@ -273,15 +276,35 @@ class AppDelegate: NSObject, NSApplicationDelegate, ctlNonModalAlertWindowDelega } } + func selfUninstall() { + self.currentAlertType = "Uninstall" + let content = String(format: NSLocalizedString("This will remove vChewing Input Method from this user account, requiring your confirmation.", comment: "")) + ctlNonModalAlertWindow.shared.show(title: NSLocalizedString("Uninstallation", comment: ""), content: content, confirmButtonTitle: NSLocalizedString("OK", comment: ""), cancelButtonTitle: NSLocalizedString("Not Now", comment: ""), cancelAsDefault: false, delegate: self) + NSApp.setActivationPolicy(.accessory) + } + func ctlNonModalAlertWindowDidConfirm(_ controller: ctlNonModalAlertWindow) { - if let updateNextStepURL = updateNextStepURL { - NSWorkspace.shared.open(updateNextStepURL) + switch self.currentAlertType { + case "Uninstall": + NSWorkspace.shared.openFile(mgrLangModel.dataFolderPath(isDefaultFolder: true), withApplication: "Finder") + IME.uninstall(isSudo: false, selfKill: true) + case "Update": + if let updateNextStepURL = self.updateNextStepURL { + NSWorkspace.shared.open(updateNextStepURL) + } + self.updateNextStepURL = nil + default: + break } - updateNextStepURL = nil } func ctlNonModalAlertWindowDidCancel(_ controller: ctlNonModalAlertWindow) { - updateNextStepURL = nil + switch self.currentAlertType { + case "Update": + self.updateNextStepURL = nil + default: + break + } } // New About Window diff --git a/Source/Modules/IME.swift b/Source/Modules/IME.swift index 38f65151..df9e3666 100644 --- a/Source/Modules/IME.swift +++ b/Source/Modules/IME.swift @@ -22,15 +22,19 @@ import Cocoa static let dlgOpenPath = NSOpenPanel(); - // MARK: - Functions - - // Print debug information to the console. + // MARK: - Print debug information to the console. @objc static func prtDebugIntel(_ strPrint: String) { if mgrPrefs.isDebugModeEnabled { NSLog("vChewingErrorCallback: %@", strPrint) } } + // MARK: - Tell whether this IME is running with Root privileges. + @objc static var isSudoMode: Bool { + NSUserName() == "root" + } + + // MARK: - Initializing Language Models. @objc static func initLangModels(userOnly: Bool) { if !userOnly { mgrLangModel.loadDataModels() // 這句還是不要砍了。 @@ -43,6 +47,7 @@ import Cocoa mgrLangModel.loadUserAssociatedPhrases() } + // MARK: - System Dark Mode Status Detector. @objc static func isDarkMode() -> Bool { if #available(macOS 10.15, *) { let appearanceDescription = NSApplication.shared.effectiveAppearance.debugDescription.lowercased() @@ -58,4 +63,106 @@ import Cocoa } return false } + + // MARK: - Trash a file if it exists. + @discardableResult static func trashTargetIfExists(_ path: String) -> Bool { + do { + if FileManager.default.fileExists(atPath: path) { + // 塞入垃圾桶 + try FileManager.default.trashItem(at: URL(fileURLWithPath: path), resultingItemURL: nil) + } else { + NSLog("Item doesn't exist: \(path)") + } + } catch let error as NSError { + NSLog("Failed from removing this object: \(path) || Error: \(error)") + return false + } + return true + } + // MARK: - Uninstalling the input method. + @discardableResult static func uninstall(isSudo: Bool = false, selfKill: Bool = true) -> Int32 { + // 輸入法自毀處理。這裡不用「Bundle.main.bundleURL」是為了方便使用者以 sudo 身分來移除被錯誤安裝到系統目錄內的輸入法。 + guard let bundleID = Bundle.main.bundleIdentifier else { + NSLog("Failed to ensure the bundle identifier.") + return -1 + } + + let kTargetBin = "vChewing" + let kTargetBundle = "/vChewing.app" + let pathLibrary = isSudo ? "/Library" : FileManager.default.urls(for: .libraryDirectory, in: .userDomainMask)[0].path + let pathIMELibrary = isSudo ? "/Library/Input Methods" : FileManager.default.urls(for: .inputMethodsDirectory, in: .userDomainMask)[0].path + let pathUnitKeyboardLayouts = "/Keyboard Layouts" + let arrKeyLayoutFiles = ["/vChewing ETen.keylayout", "/vChewingKeyLayout.bundle", "/vChewing MiTAC.keylayout", "/vChewing IBM.keylayout", "/vChewing FakeSeigyou.keylayout", "/vChewing Dachen.keylayout"] + + // 先移除各種鍵盤佈局。 + for objPath in arrKeyLayoutFiles { + let objFullPath = pathLibrary + pathUnitKeyboardLayouts + objPath + if !IME.trashTargetIfExists(objFullPath) { return -1 } + } + if CommandLine.arguments.count > 2 && CommandLine.arguments[2] == "--all" && CommandLine.arguments[1] == "uninstall" { + // 再處理是否需要移除放在預設使用者資料夾內的檔案的情況。 + // 如果使用者有在輸入法偏好設定內將該目錄改到別的地方(而不是用 symbol link)的話,則不處理。 + // 目前暫時無法應對 symbol link 的情況。 + IME.trashTargetIfExists(mgrLangModel.dataFolderPath(isDefaultFolder: true)) + IME.trashTargetIfExists(pathLibrary + "/Preferences/" + bundleID + ".plist") // 之後移除 App 偏好設定 + } + if !IME.trashTargetIfExists(pathIMELibrary + kTargetBundle) { return -1 } // 最後移除 App 自身 + // 幹掉殘留在記憶體內的執行緒。 + if selfKill { + let killTask = Process() + killTask.launchPath = "/usr/bin/killall" + killTask.arguments = ["-9", kTargetBin] + killTask.launch() + killTask.waitUntilExit() + } + return 0 + } + + // MARK: - Registering the input method. + @discardableResult static func registerInputMethod() -> Int32 { + guard let bundleID = Bundle.main.bundleIdentifier else { + return -1 + } + let bundleUrl = Bundle.main.bundleURL + var maybeInputSource = InputSourceHelper.inputSource(for: bundleID) + + if maybeInputSource == nil { + NSLog("Registering input source \(bundleID) at \(bundleUrl.absoluteString)"); + // then register + let status = InputSourceHelper.registerTnputSource(at: bundleUrl) + + if !status { + NSLog("Fatal error: Cannot register input source \(bundleID) at \(bundleUrl.absoluteString).") + return -1 + } + + maybeInputSource = InputSourceHelper.inputSource(for: bundleID) + } + + guard let inputSource = maybeInputSource else { + NSLog("Fatal error: Cannot find input source \(bundleID) after registration.") + return -1 + } + + if !InputSourceHelper.inputSourceEnabled(for: inputSource) { + NSLog("Enabling input source \(bundleID) at \(bundleUrl.absoluteString).") + let status = InputSourceHelper.enable(inputSource: inputSource) + if !status { + NSLog("Fatal error: Cannot enable input source \(bundleID).") + return -1 + } + if !InputSourceHelper.inputSourceEnabled(for: inputSource) { + NSLog("Fatal error: Cannot enable input source \(bundleID).") + return -1 + } + } + + if CommandLine.arguments.count > 2 && CommandLine.arguments[2] == "--all" { + let enabled = InputSourceHelper.enableAllInputMode(for: bundleID) + NSLog(enabled ? "All input sources enabled for \(bundleID)" : "Cannot enable all input sources for \(bundleID), but this is ignored") + } + return 0 + } + + } diff --git a/Source/Modules/IMEModules/ctlInputMethod.swift b/Source/Modules/IMEModules/ctlInputMethod.swift index 9dea56d4..9500a800 100644 --- a/Source/Modules/IMEModules/ctlInputMethod.swift +++ b/Source/Modules/IMEModules/ctlInputMethod.swift @@ -136,9 +136,10 @@ class ctlInputMethod: IMKInputController { if !optionKeyPressed { menu.addItem(withTitle: NSLocalizedString("Check for Updates…", comment: ""), action: #selector(checkForUpdate(_:)), keyEquivalent: "") } + menu.addItem(withTitle: NSLocalizedString("Reboot vChewing…", comment: ""), action: #selector(selfTerminate(_:)), keyEquivalent: "") menu.addItem(withTitle: NSLocalizedString("About vChewing…", comment: ""), action: #selector(showAbout(_:)), keyEquivalent: "") if optionKeyPressed { - menu.addItem(withTitle: NSLocalizedString("Reboot vChewing…", comment: ""), action: #selector(selfTerminate(_:)), keyEquivalent: "") + menu.addItem(withTitle: NSLocalizedString("Uninstall vChewing…", comment: ""), action: #selector(selfUninstall(_:)), keyEquivalent: "") } // NSMenu 會阻止任何 modified key 相關的訊號傳回輸入法,所以咱們在此重設鍵盤佈局 @@ -273,6 +274,10 @@ class ctlInputMethod: IMKInputController { NotifierController.notify(message: String(format: "%@%@%@", NSLocalizedString("Use Phrase Replacement", comment: ""), "\n", mgrPrefs.togglePhraseReplacementEnabled() ? NSLocalizedString("NotificationSwitchON", comment: "") : NSLocalizedString("NotificationSwitchOFF", comment: ""))) } + @objc func selfUninstall(_ sender: Any?) { + (NSApp.delegate as? AppDelegate)?.selfUninstall() + } + @objc func selfTerminate(_ sender: Any?) { NSApp.terminate(nil) } diff --git a/Source/Modules/main.swift b/Source/Modules/main.swift index 4bf09c56..9996268f 100644 --- a/Source/Modules/main.swift +++ b/Source/Modules/main.swift @@ -20,56 +20,15 @@ TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR TH import Cocoa import InputMethodKit -private func install() -> Int32 { - guard let bundleID = Bundle.main.bundleIdentifier else { - return -1 - } - let bundleUrl = Bundle.main.bundleURL - var maybeInputSource = InputSourceHelper.inputSource(for: bundleID) - - if maybeInputSource == nil { - NSLog("Registering input source \(bundleID) at \(bundleUrl.absoluteString)"); - // then register - let status = InputSourceHelper.registerTnputSource(at: bundleUrl) - - if !status { - NSLog("Fatal error: Cannot register input source \(bundleID) at \(bundleUrl.absoluteString).") - return -1 - } - - maybeInputSource = InputSourceHelper.inputSource(for: bundleID) - } - - guard let inputSource = maybeInputSource else { - NSLog("Fatal error: Cannot find input source \(bundleID) after registration.") - return -1 - } - - if !InputSourceHelper.inputSourceEnabled(for: inputSource) { - NSLog("Enabling input source \(bundleID) at \(bundleUrl.absoluteString).") - let status = InputSourceHelper.enable(inputSource: inputSource) - if !status { - NSLog("Fatal error: Cannot enable input source \(bundleID).") - return -1 - } - if !InputSourceHelper.inputSourceEnabled(for: inputSource) { - NSLog("Fatal error: Cannot enable input source \(bundleID).") - return -1 - } - } - - if CommandLine.arguments.count > 2 && CommandLine.arguments[2] == "--all" { - let enabled = InputSourceHelper.enableAllInputMode(for: bundleID) - NSLog(enabled ? "All input sources enabled for \(bundleID)" : "Cannot enable all input sources for \(bundleID), but this is ignored") - } - return 0 -} - let kConnectionName = "vChewing_1_Connection" if CommandLine.arguments.count > 1 { if CommandLine.arguments[1] == "install" { - let exitCode = install() + let exitCode = IME.registerInputMethod() + exit(exitCode) + } + if CommandLine.arguments[1] == "uninstall" { + let exitCode = IME.uninstall(isSudo: IME.isSudoMode) exit(exitCode) } } diff --git a/Source/Resources/Base.lproj/Localizable.strings b/Source/Resources/Base.lproj/Localizable.strings index b90b9b8e..22739e01 100644 --- a/Source/Resources/Base.lproj/Localizable.strings +++ b/Source/Resources/Base.lproj/Localizable.strings @@ -1,5 +1,8 @@ "About vChewing…" = "About vChewing…"; "vChewing Preferences…" = "vChewing Preferences…"; +"Uninstallation" = "Uninstallation"; +"Uninstall vChewing…" = "Uninstall vChewing…"; +"This will remove vChewing Input Method from this user account, requiring your confirmation." = "This will remove vChewing Input Method from this user account, requiring your confirmation."; "Check Later" = "Check Later"; "Check for Updates…" = "Check for Updates…"; "Check for Update Completed" = "Check for Update Completed"; @@ -51,6 +54,7 @@ "Apple Zhuyin Bopomofo" = "Apple Zhuyin Bopomofo (Standard)"; "Apple Zhuyin Eten" = "Apple Zhuyin Eten"; "Symbol & Emoji Input" = "Symbol & Emoji Input"; +"Edit User Symbol & Emoji Data…" = "Edit User Symbol & Emoji Data…"; "Choose your desired user data folder." = "Choose your desired user data folder."; // The followings are the category names used in the Symbol menu. diff --git a/Source/Resources/en.lproj/Localizable.strings b/Source/Resources/en.lproj/Localizable.strings index 438017a6..22739e01 100644 --- a/Source/Resources/en.lproj/Localizable.strings +++ b/Source/Resources/en.lproj/Localizable.strings @@ -1,5 +1,8 @@ "About vChewing…" = "About vChewing…"; "vChewing Preferences…" = "vChewing Preferences…"; +"Uninstallation" = "Uninstallation"; +"Uninstall vChewing…" = "Uninstall vChewing…"; +"This will remove vChewing Input Method from this user account, requiring your confirmation." = "This will remove vChewing Input Method from this user account, requiring your confirmation."; "Check Later" = "Check Later"; "Check for Updates…" = "Check for Updates…"; "Check for Update Completed" = "Check for Update Completed"; diff --git a/Source/Resources/ja.lproj/Localizable.strings b/Source/Resources/ja.lproj/Localizable.strings index 706b3299..65715b6f 100644 --- a/Source/Resources/ja.lproj/Localizable.strings +++ b/Source/Resources/ja.lproj/Localizable.strings @@ -1,5 +1,8 @@ "About vChewing…" = "威注音について…"; "vChewing Preferences…" = "入力機能設定…"; +"Uninstallation" = "入力アプリの卸除(おろしのぞき)"; +"Uninstall vChewing…" = "入力アプリを卸除く…"; +"This will remove vChewing Input Method from this user account, requiring your confirmation." = "これにて威注音入力アプリをこのアカウントから卸除しますが、宜しいですか。"; "Check Later" = "後でやる"; "Check for Updates…" = "更新通知を受く…"; "Check for Update Completed" = "更新通知受信完了"; diff --git a/Source/Resources/zh-Hans.lproj/Localizable.strings b/Source/Resources/zh-Hans.lproj/Localizable.strings index 057af145..df5b4d25 100644 --- a/Source/Resources/zh-Hans.lproj/Localizable.strings +++ b/Source/Resources/zh-Hans.lproj/Localizable.strings @@ -1,5 +1,8 @@ "About vChewing…" = "关于威注音…"; "vChewing Preferences…" = "威注音偏好设定…"; +"Uninstallation" = "卸除输入法"; +"Uninstall vChewing…" = "卸除威注音…"; +"This will remove vChewing Input Method from this user account, requiring your confirmation." = "此举会将威注音自当前系统使用者帐户卸除。请确认。"; "Check Later" = "晚点再通知我"; "Check for Updates…" = "检查是否有新版…"; "Check for Update Completed" = "新版检查完毕"; diff --git a/Source/Resources/zh-Hant.lproj/Localizable.strings b/Source/Resources/zh-Hant.lproj/Localizable.strings index 0b529ba2..94998123 100644 --- a/Source/Resources/zh-Hant.lproj/Localizable.strings +++ b/Source/Resources/zh-Hant.lproj/Localizable.strings @@ -1,5 +1,8 @@ "About vChewing…" = "關於威注音…"; "vChewing Preferences…" = "威注音偏好設定…"; +"Uninstallation" = "卸除輸入法"; +"Uninstall vChewing…" = "卸除威注音…"; +"This will remove vChewing Input Method from this user account, requiring your confirmation." = "此舉會將威注音自當前系統使用者帳戶卸除。請確認。"; "Check Later" = "晚點再通知我"; "Check for Updates…" = "檢查是否有新版…"; "Check for Update Completed" = "新版檢查完畢"; diff --git a/Source/WindowNIBs/Base.lproj/frmAboutWindow.xib b/Source/WindowNIBs/Base.lproj/frmAboutWindow.xib index 33c00d01..ed7cce75 100644 --- a/Source/WindowNIBs/Base.lproj/frmAboutWindow.xib +++ b/Source/WindowNIBs/Base.lproj/frmAboutWindow.xib @@ -82,7 +82,7 @@ vChewing Phrase Database Maintained by Shiki Suen. - DISCLAIMER: The vChewing project, having no relationship of cooperation or affiliation with the OpenVanilla project, is not responsible for the phrase database shipped in the original McBopomofo project. Certain geopolitical and ideological contents, which are potentially harmful to the global spread of this software, have been removed from vChewing official phrase database. + DISCLAIMER: The vChewing project, having no relationship of cooperation or affiliation with the OpenVanilla project, is not responsible for the phrase database shipped in the original McBopomofo project. Certain geopolitical and ideological contents, which are potentially harmful to the global spread of this software, are not included in vChewing official phrase database. diff --git a/Source/WindowNIBs/Base.lproj/frmNonModalAlertWindow.xib b/Source/WindowNIBs/Base.lproj/frmNonModalAlertWindow.xib index 9a161183..20368443 100644 --- a/Source/WindowNIBs/Base.lproj/frmNonModalAlertWindow.xib +++ b/Source/WindowNIBs/Base.lproj/frmNonModalAlertWindow.xib @@ -22,7 +22,7 @@ - + diff --git a/Source/WindowNIBs/Source/WindowNIBs/Base.lproj/frmPrefWindow.xib b/Source/WindowNIBs/Source/WindowNIBs/Base.lproj/frmPrefWindow.xib index c815e053..c6501643 100644 --- a/Source/WindowNIBs/Source/WindowNIBs/Base.lproj/frmPrefWindow.xib +++ b/Source/WindowNIBs/Source/WindowNIBs/Base.lproj/frmPrefWindow.xib @@ -59,8 +59,8 @@ - - + + @@ -123,8 +123,8 @@ - - + + @@ -177,8 +177,8 @@ - - + + @@ -381,8 +381,8 @@ - - + + @@ -452,8 +452,8 @@ - - + + @@ -485,8 +485,8 @@ - - + +