Pre Merge pull request !82 from ShikiSuen/upd/1.9.2

This commit is contained in:
ShikiSuen 2022-08-13 08:08:16 +00:00 committed by Gitee
commit 68e50fc9ce
No known key found for this signature in database
GPG Key ID: 173E9B9CA92EEF8F
52 changed files with 767 additions and 129 deletions

@ -1 +1 @@
Subproject commit 1daf4d576a248373889889213bea4bd3cbb4b5d4
Subproject commit 3cb476e7c884198fe91ce7d7ccc1ac0e082e007e

View File

@ -214,6 +214,11 @@ struct InputSignal: CustomStringConvertible {
18: "1", 19: "2", 20: "3", 21: "4", 23: "5", 22: "6", 26: "7", 28: "8", 25: "9", 29: "0",
]
var isCandidateKey: Bool {
mgrPrefs.candidateKeys.contains(inputText)
|| mgrPrefs.candidateKeys.contains(inputTextIgnoringModifiers ?? "114514")
}
/// flags KeyCode
var isNumericPadKey: Bool { arrNumpadKeyCodes.contains(keyCode) }
var isMainAreaNumKey: Bool { arrMainAreaNumKey.contains(keyCode) }

View File

@ -280,9 +280,9 @@ public enum InputState {
private var markedTargetExists = false
var tooltip: String {
if composingBuffer.count != readings.count {
ctlInputMethod.tooltipController.setColor(state: .denialOverflow)
ctlInputMethod.tooltipController.setColor(state: .redAlert)
return NSLocalizedString(
"⚠︎ Beware: Chars and Readings in buffer doesn't match.", comment: ""
"⚠︎ Unhandlable: Chars and Readings in buffer doesn't match.", comment: ""
)
}
if mgrPrefs.phraseReplacementEnabled {
@ -398,11 +398,9 @@ public enum InputState {
return state
}
var validToFilter: Bool {
///
/// deleteTargetExists 使
markedTargetExists ? allowedMarkRange.contains(literalMarkedRange.count) : false
}
var validToFilter: Bool { markedTargetExists ? allowedMarkRange.contains(literalMarkedRange.count) : false }
var bufferReadingCountMisMatch: Bool { composingBuffer.count != readings.count }
var chkIfUserPhraseExists: Bool {
let text = composingBuffer.utf16SubString(with: markedRange)

View File

@ -229,8 +229,6 @@ public class KeyHandler {
)
}
walk()
} else {
IME.prtDebugIntel("UOM: Blank suggestion retrieved, dismissing.")
}
}
arrResult = arrResult.stableSort { $0.1.score > $1.1.score }

View File

@ -25,7 +25,8 @@ class ctlInputMethod: IMKInputController {
static var areWeNerfing = false
///
static var ctlCandidateCurrent: ctlCandidateProtocol = ctlCandidateUniversal.init(.horizontal)
static var ctlCandidateCurrent: ctlCandidateProtocol =
mgrPrefs.useIMKCandidateWindow ? ctlCandidateIMK.init(.horizontal) : ctlCandidateUniversal.init(.horizontal)
///
static let tooltipController = TooltipController()
@ -47,7 +48,7 @@ class ctlInputMethod: IMKInputController {
}
/// `handle(event:)` Shift
private var rencentKeyHandledByKeyHandler = false
var rencentKeyHandledByKeyHandler = false
// MARK: -
@ -205,6 +206,12 @@ class ctlInputMethod: IMKInputController {
}
}
/// IMK IMK
if let ctlCandidateCurrent = ctlInputMethod.ctlCandidateCurrent as? ctlCandidateIMK, ctlCandidateCurrent.visible {
ctlCandidateCurrent.interpretKeyEvents([event])
return true
}
/// flags使 KeyHandler
/// flags
/// event.type == .flagsChanged return false
@ -270,14 +277,12 @@ class ctlInputMethod: IMKInputController {
let theConverted = IME.kanjiConversionIfRequired(theCandidate.1)
return (theCandidate.1 == theConverted) ? theCandidate.1 : "\(theConverted)(\(theCandidate.1))"
}
}
if let state = state as? InputState.ChoosingCandidate {
} else if let state = state as? InputState.SymbolTable {
return state.candidates.map { theCandidate -> String in
let theConverted = IME.kanjiConversionIfRequired(theCandidate.1)
return (theCandidate.1 == theConverted) ? theCandidate.1 : "\(theConverted)(\(theCandidate.1))"
}
}
if let state = state as? InputState.SymbolTable {
} else if let state = state as? InputState.ChoosingCandidate {
return state.candidates.map { theCandidate -> String in
let theConverted = IME.kanjiConversionIfRequired(theCandidate.1)
return (theCandidate.1 == theConverted) ? theCandidate.1 : "\(theConverted)(\(theCandidate.1))"
@ -285,4 +290,53 @@ class ctlInputMethod: IMKInputController {
}
return .init()
}
override open func candidateSelectionChanged(_: NSAttributedString!) {
//
}
override open func candidateSelected(_ candidateString: NSAttributedString!) {
if state is InputState.AssociatedPhrases {
if !mgrPrefs.alsoConfirmAssociatedCandidatesByEnter {
handle(state: InputState.EmptyIgnoringPreviousState())
handle(state: InputState.Empty())
return
}
}
var indexDeducted = 0
if let state = state as? InputState.AssociatedPhrases {
for (i, neta) in state.candidates.map(\.1).enumerated() {
let theConverted = IME.kanjiConversionIfRequired(neta)
let netaShown = (neta == theConverted) ? neta : "\(theConverted)(\(neta))"
if candidateString.string == netaShown {
indexDeducted = i
break
}
}
} else if let state = state as? InputState.SymbolTable {
for (i, neta) in state.candidates.map(\.1).enumerated() {
let theConverted = IME.kanjiConversionIfRequired(neta)
let netaShown = (neta == theConverted) ? neta : "\(theConverted)(\(neta))"
if candidateString.string == netaShown {
indexDeducted = i
break
}
}
} else if let state = state as? InputState.ChoosingCandidate {
for (i, neta) in state.candidates.map(\.1).enumerated() {
let theConverted = IME.kanjiConversionIfRequired(neta)
let netaShown = (neta == theConverted) ? neta : "\(theConverted)(\(neta))"
if candidateString.string == netaShown {
indexDeducted = i
break
}
}
}
keyHandler(
keyHandler,
didSelectCandidateAt: indexDeducted,
ctlCandidate: ctlInputMethod.ctlCandidateCurrent
)
}
}

View File

@ -26,6 +26,7 @@ extension ctlInputMethod: KeyHandlerDelegate {
-> Bool
{
guard let state = state as? InputState.Marking else { return false }
if state.bufferReadingCountMisMatch { return false }
let refInputModeReversed: InputMode =
(keyHandler.inputMode == InputMode.imeModeCHT)
? InputMode.imeModeCHS : InputMode.imeModeCHT
@ -49,7 +50,70 @@ extension ctlInputMethod: KeyHandlerDelegate {
// MARK: - Candidate Controller Delegate
extension ctlInputMethod: ctlCandidateDelegate {
func handleDelegateEvent(_ event: NSEvent!) -> Bool { handle(event, client: client()) }
func handleDelegateEvent(_ event: NSEvent!) -> Bool {
// Shift macOS 10.15 macOS
if #available(macOS 10.15, *) {
if ShiftKeyUpChecker.check(event) {
if !rencentKeyHandledByKeyHandler {
NotifierController.notify(
message: String(
format: "%@%@%@", NSLocalizedString("Alphanumerical Mode", comment: ""), "\n",
toggleASCIIMode()
? NSLocalizedString("NotificationSwitchON", comment: "")
: NSLocalizedString("NotificationSwitchOFF", comment: "")
)
)
}
rencentKeyHandledByKeyHandler = false
return false
}
}
/// flags使 KeyHandler
/// flags
/// event.type == .flagsChanged return false
/// NSInternalInconsistencyException
if event.type == .flagsChanged { return false }
//
ctlInputMethod.areWeNerfing = event.modifierFlags.contains([.shift, .command])
var textFrame = NSRect.zero
let attributes: [AnyHashable: Any]? = client().attributes(
forCharacterIndex: 0, lineHeightRectangle: &textFrame
)
let isTypingVertical =
(attributes?["IMKTextOrientation"] as? NSNumber)?.intValue == 0 || false
if client().bundleIdentifier()
== "org.atelierInmu.vChewing.vChewingPhraseEditor"
{
IME.areWeUsingOurOwnPhraseEditor = true
} else {
IME.areWeUsingOurOwnPhraseEditor = false
}
var input = InputSignal(event: event, isVerticalTyping: isTypingVertical)
input.isASCIIModeInput = isASCIIMode
//
// KeyHandler
if !input.charCode.isPrintable {
return false
}
/// 調
/// result bool IMK
let result = keyHandler.handleCandidate(state: state, input: input) { newState in
self.handle(state: newState)
} errorCallback: {
clsSFX.beep()
}
rencentKeyHandledByKeyHandler = result
return result
}
func candidateCountForController(_ controller: ctlCandidateProtocol) -> Int {
_ = controller //

View File

@ -46,6 +46,8 @@ extension ctlInputMethod {
candidates = state.candidates
}
if isTypingVertical { return true }
// IMK
guard ctlInputMethod.ctlCandidateCurrent is ctlCandidateUniversal else { return false }
// 使
//
// 使
@ -64,13 +66,14 @@ extension ctlInputMethod {
/// layoutCandidateView
/// macOS 10.x SwiftUI
if isCandidateWindowVertical { // 使
ctlInputMethod.ctlCandidateCurrent = ctlCandidateUniversal.init(.vertical)
} else if mgrPrefs.useHorizontalCandidateList {
ctlInputMethod.ctlCandidateCurrent = ctlCandidateUniversal.init(.horizontal)
} else {
ctlInputMethod.ctlCandidateCurrent = ctlCandidateUniversal.init(.vertical)
}
let candidateLayout: CandidateLayout =
((isCandidateWindowVertical || !mgrPrefs.useHorizontalCandidateList)
? CandidateLayout.vertical
: CandidateLayout.horizontal)
ctlInputMethod.ctlCandidateCurrent =
mgrPrefs.useIMKCandidateWindow
? ctlCandidateIMK.init(candidateLayout) : ctlCandidateUniversal.init(candidateLayout)
// set the attributes for the candidate panel (which uses NSAttributedString)
let textSize = mgrPrefs.candidateListTextSize

View File

@ -103,7 +103,8 @@ extension ctlInputMethod {
/// .NotEmpty()
/// setInlineDisplayWithCursor()
private func clearInlineDisplay() {
client().setMarkedText(
guard let theClient = client() else { return }
theClient.setMarkedText(
"", selectionRange: NSRange(location: 0, length: 0),
replacementRange: NSRange(location: NSNotFound, length: NSNotFound)
)

View File

@ -49,6 +49,8 @@ public enum UserDef: String, CaseIterable {
case kKeepReadingUponCompositionError = "KeepReadingUponCompositionError"
case kTogglingAlphanumericalModeWithLShift = "TogglingAlphanumericalModeWithLShift"
case kUpperCaseLetterKeyBehavior = "UpperCaseLetterKeyBehavior"
case kUseIMKCandidateWindow = "UseIMKCandidateWindow"
case kHandleDefaultCandidateFontsByLangIdentifier = "HandleDefaultCandidateFontsByLangIdentifier"
case kCandidateTextFontName = "CandidateTextFontName"
case kCandidateKeyLabelFontName = "CandidateKeyLabelFontName"
@ -275,6 +277,13 @@ public enum mgrPrefs {
UserDefaults.standard.setDefault(
mgrPrefs.upperCaseLetterKeyBehavior, forKey: UserDef.kUpperCaseLetterKeyBehavior.rawValue
)
UserDefaults.standard.setDefault(
mgrPrefs.useIMKCandidateWindow, forKey: UserDef.kUseIMKCandidateWindow.rawValue
)
UserDefaults.standard.setDefault(
mgrPrefs.handleDefaultCandidateFontsByLangIdentifier,
forKey: UserDef.kHandleDefaultCandidateFontsByLangIdentifier.rawValue
)
UserDefaults.standard.setDefault(mgrPrefs.usingHotKeySCPC, forKey: UserDef.kUsingHotKeySCPC.rawValue)
UserDefaults.standard.setDefault(mgrPrefs.usingHotKeyAssociates, forKey: UserDef.kUsingHotKeyAssociates.rawValue)
@ -379,6 +388,17 @@ public enum mgrPrefs {
@UserDefault(key: UserDef.kUpperCaseLetterKeyBehavior.rawValue, defaultValue: 0)
static var upperCaseLetterKeyBehavior: Int
@UserDefault(key: UserDef.kUseIMKCandidateWindow.rawValue, defaultValue: false)
static var useIMKCandidateWindow: Bool {
didSet {
NSLog("vChewing App self-terminated due to enabling / disabling IMK candidate window.")
NSApplication.shared.terminate(nil)
}
}
@UserDefault(key: UserDef.kHandleDefaultCandidateFontsByLangIdentifier.rawValue, defaultValue: false)
static var handleDefaultCandidateFontsByLangIdentifier: Bool
// MARK: - Settings (Tier 2)
@UserDefault(key: UserDef.kTogglingAlphanumericalModeWithLShift.rawValue, defaultValue: true)

View File

@ -278,26 +278,19 @@ extension vChewing.LMUserOverride {
saveCallback()
return
}
// TODO:
// decayCallback
if var theNeta = mutLRUMap[key] {
_ = getSuggestion(
key: key, timestamp: timestamp, headReading: "",
decayCallback: {
theNeta.observation.update(
candidate: candidate, timestamp: timestamp, forceHighScoreOverride: forceHighScoreOverride
)
self.mutLRUList.insert(theNeta, at: 0)
self.mutLRUMap[key] = theNeta
mutLRUList.insert(theNeta, at: 0)
mutLRUMap[key] = theNeta
IME.prtDebugIntel("UOM: Observation finished with existing observation: \(key)")
saveCallback()
}
)
}
}
private func getSuggestion(
key: String, timestamp: Double, headReading: String, decayCallback: @escaping () -> Void = {}
) -> Suggestion {
private func getSuggestion(key: String, timestamp: Double, headReading: String) -> Suggestion {
guard !key.isEmpty, let kvPair = mutLRUMap[key] else { return .init() }
let observation: Observation = kvPair.observation
var candidates: [(String, Megrez.Unigram)] = .init()
@ -309,11 +302,6 @@ extension vChewing.LMUserOverride {
eventTimestamp: theObservation.timestamp, timestamp: timestamp, lambda: mutDecayExponent
)
if (0...currentHighScore).contains(overrideScore) { continue }
let overrideDetectionScore: Double = getScore(
eventCount: theObservation.count, totalCount: observation.count,
eventTimestamp: theObservation.timestamp, timestamp: timestamp, lambda: mutDecayExponent * 2
)
if (0...currentHighScore).contains(overrideDetectionScore) { decayCallback() }
candidates.append((headReading, .init(value: i, score: overrideScore)))
forceHighScoreOverride = theObservation.forceHighScoreOverride

View File

@ -18,6 +18,14 @@ public enum clsSFX {
AudioServicesPlaySystemSound(soundID)
}
static func fart() {
let filePath = Bundle.main.path(forResource: "Fart", ofType: "m4a")!
let fileURL = URL(fileURLWithPath: filePath)
var soundID: SystemSoundID = 0
AudioServicesCreateSystemSoundID(fileURL as CFURL, &soundID)
AudioServicesPlaySystemSound(soundID)
}
static func beep(count: Int = 1) {
if count <= 1 {
clsSFX.beep()

View File

@ -39,7 +39,7 @@
"Please specify at least 4 candidate keys." = "Please specify at least 4 candidate keys.";
"Maximum 15 candidate keys allowed." = "Maximum 15 candidate keys allowed.";
"⚠︎ Phrase replacement mode enabled, interfering user phrase entry." = "⚠︎ Phrase replacement mode enabled, interfering user phrase entry.";
"⚠︎ Beware: Chars and Readings in buffer doesn't match." = "⚠︎ Beware: Chars and Readings in buffer doesn't match.";
"⚠︎ Unhandlable: Chars and Readings in buffer doesn't match." = "⚠︎ Unhandlable: Chars and Readings in buffer doesn't match.";
"Per-Char Select Mode" = "Per-Char Select Mode";
"CNS11643 Mode" = "CNS11643 Mode";
"JIS Shinjitai Output" = "JIS Shinjitai Output";
@ -123,6 +123,7 @@
"Dachen (Microsoft Standard / Wang / 01, etc.)" = "Dachen (Microsoft Standard / Wang / 01, etc.)";
"Dachen 26 (libChewing)" = "Dachen 26 (libChewing)";
"Debug Mode" = "Debug Mode";
"DevZone" = "DevZone";
"Dictionary" = "Dictionary";
"Directly commit lowercased letters" = "Directly commit lowercased letters";
"Directly commit uppercased letters" = "Directly commit uppercased letters";
@ -144,6 +145,7 @@
"Hsu" = "Hsu";
"Hualuo Pinyin with Numeral Intonation" = "Hualuo Pinyin with Numeral Intonation";
"IBM" = "IBM";
"IMK candidate window is plagued with issues like failed selection keys." = "IMK candidate window is plagued with issues like failed selection keys.";
"in front of the phrase (like macOS built-in Zhuyin IME)" = "in front of the phrase (like macOS built-in Zhuyin IME)";
"Japanese" = "Japanese";
"Keyboard Shortcuts:" = "Keyboard Shortcuts:";
@ -166,11 +168,15 @@
"Space to +cycle pages, Shift+Space to +cycle candidates" = "Space to +cycle pages, Shift+Space to +cycle candidates";
"Starlight" = "Starlight";
"Stop farting (when typed phonetic combination is invalid, etc.)" = "Stop farting (when typed phonetic combination is invalid, etc.)";
"This only works since macOS 12 with non-IMK candidate window as an alternative wordaround of Apple Bug Report #FB10978412. Apple should patch that for macOS 11 and later." = "This only works since macOS 12 with non-IMK candidate window as an alternative wordaround of Apple Bug Report #FB10978412. Apple should patch that for macOS 11 and later.";
"Traditional Chinese" = "Traditional Chinese";
"Type them into inline composition buffer" = "Type them into inline composition buffer";
"Typing Style:" = "Typing Style:";
"UI Language:" = "UI Language:";
"Universal Pinyin with Numeral Intonation" = "Universal Pinyin with Numeral Intonation";
"Use .langIdentifier to handle UI fonts in candidate window" = "Use .langIdentifier to handle UI fonts in candidate window";
"Use ESC key to clear the entire input buffer" = "Use ESC key to clear the entire input buffer";
"Use IMK Candidate Window instead (will reboot the IME)" = "Use IMK Candidate Window instead (will reboot the IME)";
"Vertical" = "Vertical";
"Warning: This page is for testing future features. \nFeatures listed here may not work as expected." = "Warning: This page is for testing future features. \nFeatures listed here may not work as expected.";
"Yale Pinyin with Numeral Intonation" = "Yale Pinyin with Numeral Intonation";

View File

@ -0,0 +1,22 @@
{
"images" : [
{
"filename" : "DevZone.png",
"idiom" : "universal",
"scale" : "1x"
},
{
"filename" : "DevZone@2x.png",
"idiom" : "universal",
"scale" : "2x"
},
{
"idiom" : "universal",
"scale" : "3x"
}
],
"info" : {
"author" : "xcode",
"version" : 1
}
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.4 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 572 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 879 B

View File

@ -0,0 +1,22 @@
{
"images" : [
{
"filename" : "Dictionary.png",
"idiom" : "universal",
"scale" : "1x"
},
{
"filename" : "Dictionary@2x.png",
"idiom" : "universal",
"scale" : "2x"
},
{
"idiom" : "universal",
"scale" : "3x"
}
],
"info" : {
"author" : "xcode",
"version" : 1
}
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 749 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 KiB

View File

@ -0,0 +1,22 @@
{
"images" : [
{
"filename" : "Experiences.png",
"idiom" : "universal",
"scale" : "1x"
},
{
"filename" : "Experiences@2x.png",
"idiom" : "universal",
"scale" : "2x"
},
{
"idiom" : "universal",
"scale" : "3x"
}
],
"info" : {
"author" : "xcode",
"version" : 1
}
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.9 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 2.0 KiB

View File

@ -0,0 +1,22 @@
{
"images" : [
{
"filename" : "General.png",
"idiom" : "universal",
"scale" : "1x"
},
{
"filename" : "General@2x.png",
"idiom" : "universal",
"scale" : "2x"
},
{
"idiom" : "universal",
"scale" : "3x"
}
],
"info" : {
"author" : "xcode",
"version" : 1
}
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.7 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.9 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 942 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.4 KiB

View File

@ -0,0 +1,22 @@
{
"images" : [
{
"filename" : "Keyboard.png",
"idiom" : "universal",
"scale" : "1x"
},
{
"filename" : "Keyboard@2x.png",
"idiom" : "universal",
"scale" : "2x"
},
{
"idiom" : "universal",
"scale" : "3x"
}
],
"info" : {
"author" : "xcode",
"version" : 1
}
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.0 KiB

View File

@ -39,7 +39,7 @@
"Please specify at least 4 candidate keys." = "Please specify at least 4 candidate keys.";
"Maximum 15 candidate keys allowed." = "Maximum 15 candidate keys allowed.";
"⚠︎ Phrase replacement mode enabled, interfering user phrase entry." = "⚠︎ Phrase replacement mode enabled, interfering user phrase entry.";
"⚠︎ Beware: Chars and Readings in buffer doesn't match." = "⚠︎ Beware: Chars and Readings in buffer doesn't match.";
"⚠︎ Unhandlable: Chars and Readings in buffer doesn't match." = "⚠︎ Unhandlable: Chars and Readings in buffer doesn't match.";
"Per-Char Select Mode" = "Per-Char Select Mode";
"CNS11643 Mode" = "CNS11643 Mode";
"JIS Shinjitai Output" = "JIS Shinjitai Output";
@ -123,6 +123,7 @@
"Dachen (Microsoft Standard / Wang / 01, etc.)" = "Dachen (Microsoft Standard / Wang / 01, etc.)";
"Dachen 26 (libChewing)" = "Dachen 26 (libChewing)";
"Debug Mode" = "Debug Mode";
"DevZone" = "DevZone";
"Dictionary" = "Dictionary";
"Directly commit lowercased letters" = "Directly commit lowercased letters";
"Directly commit uppercased letters" = "Directly commit uppercased letters";
@ -144,6 +145,7 @@
"Hsu" = "Hsu";
"Hualuo Pinyin with Numeral Intonation" = "Hualuo Pinyin with Numeral Intonation";
"IBM" = "IBM";
"IMK candidate window is plagued with issues like failed selection keys." = "IMK candidate window is plagued with issues like failed selection keys.";
"in front of the phrase (like macOS built-in Zhuyin IME)" = "in front of the phrase (like macOS built-in Zhuyin IME)";
"Japanese" = "Japanese";
"Keyboard Shortcuts:" = "Keyboard Shortcuts:";
@ -166,11 +168,15 @@
"Space to +cycle pages, Shift+Space to +cycle candidates" = "Space to +cycle pages, Shift+Space to +cycle candidates";
"Starlight" = "Starlight";
"Stop farting (when typed phonetic combination is invalid, etc.)" = "Stop farting (when typed phonetic combination is invalid, etc.)";
"This only works since macOS 12 with non-IMK candidate window as an alternative wordaround of Apple Bug Report #FB10978412. Apple should patch that for macOS 11 and later." = "This only works since macOS 12 with non-IMK candidate window as an alternative wordaround of Apple Bug Report #FB10978412. Apple should patch that for macOS 11 and later.";
"Traditional Chinese" = "Traditional Chinese";
"Type them into inline composition buffer" = "Type them into inline composition buffer";
"Typing Style:" = "Typing Style:";
"UI Language:" = "UI Language:";
"Universal Pinyin with Numeral Intonation" = "Universal Pinyin with Numeral Intonation";
"Use .langIdentifier to handle UI fonts in candidate window" = "Use .langIdentifier to handle UI fonts in candidate window";
"Use ESC key to clear the entire input buffer" = "Use ESC key to clear the entire input buffer";
"Use IMK Candidate Window instead (will reboot the IME)" = "Use IMK Candidate Window instead (will reboot the IME)";
"Vertical" = "Vertical";
"Warning: This page is for testing future features. \nFeatures listed here may not work as expected." = "Warning: This page is for testing future features. \nFeatures listed here may not work as expected.";
"Yale Pinyin with Numeral Intonation" = "Yale Pinyin with Numeral Intonation";

View File

@ -39,7 +39,7 @@
"Please specify at least 4 candidate keys." = "言選り用キー陣列に少なくとも4つのキーをご登録ください。";
"Maximum 15 candidate keys allowed." = "言選り用キー陣列には最多15つキー登録できます。";
"⚠︎ Phrase replacement mode enabled, interfering user phrase entry." = "⚠︎ 言葉置換機能稼働中、新添付言葉にも影響。";
"⚠︎ Beware: Chars and Readings in buffer doesn't match." = "⚠︎ 注意:緩衝列の字数は読みの数と不同等。";
"⚠︎ Unhandlable: Chars and Readings in buffer doesn't match." = "⚠︎ 対処不可:緩衝列の字数は読みの数と不同等。";
"Per-Char Select Mode" = "全候補入力モード";
"CNS11643 Mode" = "全字庫モード";
"JIS Shinjitai Output" = "JIS 新字体モード";
@ -123,6 +123,7 @@
"Dachen (Microsoft Standard / Wang / 01, etc.)" = "大千配列 (Microsoft 標準・王安・零壹など)";
"Dachen 26 (libChewing)" = "酷音大千 26 キー配列";
"Debug Mode" = "欠陥辿着モード";
"DevZone" = "開発道場";
"Dictionary" = "辞書設定";
"Directly commit lowercased letters" = "ローマ字(小文字)を直接出力";
"Directly commit uppercased letters" = "ローマ字(大文字)を直接出力";
@ -144,6 +145,7 @@
"Hsu" = "許氏国音自然配列";
"Hualuo Pinyin with Numeral Intonation" = "中華ローマ弁音 (ローマ字+数字音調)";
"IBM" = "IBM 配列";
"IMK candidate window is plagued with issues like failed selection keys." = "IMK 候補陳列ウィンドウで言選り用キーは現時点で利用不可、尚他故障あり。";
"in front of the phrase (like macOS built-in Zhuyin IME)" = "単語の前で // macOS 内蔵注音入力のやり方";
"Japanese" = "和語";
"Keyboard Shortcuts:" = "ショートカット:";
@ -166,11 +168,15 @@
"Space to +cycle pages, Shift+Space to +cycle candidates" = "Space で次のページ、Shift+Space で次の候補文字を";
"Starlight" = "星光配列";
"Stop farting (when typed phonetic combination is invalid, etc.)" = "マナーモード // 外すと入力間違った時に変な声が出る";
"This only works since macOS 12 with non-IMK candidate window as an alternative wordaround of Apple Bug Report #FB10978412. Apple should patch that for macOS 11 and later." = "これは Apple Bug Report #FB10978412 の臨時対策であり、macOS 12 からの macOS に効き、IMK 以外の候補陳列ウィンドウに作用する。Apple は macOS 11 からの macOS のために該当 Bug を修復すべきである。";
"Traditional Chinese" = "繁体中国語";
"Type them into inline composition buffer" = "入力緩衝列にローマ字入力";
"Typing Style:" = "入力習慣:";
"UI Language:" = "表示用言語:";
"Universal Pinyin with Numeral Intonation" = "汎用弁音 (ローマ字+数字音調)";
"Use .langIdentifier to handle UI fonts in candidate window" = "「.langIdentifier」を使って候補陳列ウィンドウのフォントを取り扱う";
"Use ESC key to clear the entire input buffer" = "ESC キーで入力緩衝列を消す";
"Use IMK Candidate Window instead (will reboot the IME)" = "IMK 候補陳列ウィンドウを起用(入力アプリは自動的に再起動)";
"Vertical" = "縦型陳列";
"Warning: This page is for testing future features. \nFeatures listed here may not work as expected." = "警告:これからの新機能テストのために作ったページですから、\nここで陳列されている諸機能は予想通り動けるだと思わないでください。";
"Yale Pinyin with Numeral Intonation" = "イェール弁音 (ローマ字+数字音調)";

View File

@ -39,7 +39,7 @@
"Please specify at least 4 candidate keys." = "请至少指定四个选字键。";
"Maximum 15 candidate keys allowed." = "选字键最多只能指定十五个。";
"⚠︎ Phrase replacement mode enabled, interfering user phrase entry." = "⚠︎ 语汇置换功能已启用,会波及语汇自订。";
"⚠︎ Beware: Chars and Readings in buffer doesn't match." = "⚠︎ 注意:组字区字数与读音数不对应。";
"⚠︎ Unhandlable: Chars and Readings in buffer doesn't match." = "⚠︎ 无法处理:组字区字数与读音数不对应。";
"Per-Char Select Mode" = "仿真逐字选字输入";
"CNS11643 Mode" = "全字库模式";
"JIS Shinjitai Output" = "JIS 新字体模式";
@ -123,7 +123,8 @@
"Dachen (Microsoft Standard / Wang / 01, etc.)" = "大千排列 (微软标准/王安/零壹/仲鼎/国乔)";
"Dachen 26 (libChewing)" = "酷音大千二十六键排列";
"Debug Mode" = "侦错模式";
"Dictionary" = "辞典";
"DevZone" = "开发道场";
"Dictionary" = "辞典设定";
"Directly commit lowercased letters" = "直接递交小写字母";
"Directly commit uppercased letters" = "直接递交大写字母";
"Emulating select-candidate-per-character mode" = "模拟 90 年代前期注音逐字选字输入风格";
@ -133,22 +134,23 @@
"English" = "英语";
"Eten 26" = "倚天忘形排列 (26 键)";
"Eten Traditional" = "倚天传统排列";
"Experience" = "体验";
"Experience" = "体验设定";
"Fake Seigyou" = "伪精业排列";
"Follow OS settings" = "依系统设定";
"for cycling candidates" = "轮替候选字";
"for cycling pages" = "轮替页面";
"General" = "通用";
"General" = "通用设定";
"Hanyu Pinyin with Numeral Intonation" = "汉语拼音+数字标调";
"Horizontal" = "横向布局";
"Hsu" = "许氏国音自然排列";
"Hualuo Pinyin with Numeral Intonation" = "华罗拼音+数字标调";
"Hualuo Pinyin with Numeral Intonation" = "華羅拼音+数字标调";
"IBM" = "IBM 排列";
"IMK candidate window is plagued with issues like failed selection keys." = "IMK 选字窗目前暂时无法正常使用选字键,并具其它未知故障。";
"in front of the phrase (like macOS built-in Zhuyin IME)" = "将游标置于词语前方 // macOS 内建注音风格";
"Japanese" = "和语";
"Keyboard Shortcuts:" = "键盘快捷键:";
"Keyboard" = "键盘";
"Keyboard" = "键盘设定";
"Misc Settings:" = "杂项:";
"MiTAC" = "神通排列";
"Non-QWERTY alphanumerical keyboard layouts are for Hanyu Pinyin parser only." = "QWERTY 以外的英数布局是为了汉语拼音排列使用者而准备的。";
@ -167,12 +169,16 @@
"Space to +cycle pages, Shift+Space to +cycle candidates" = "空格键 换下一页Shift+空格键 换选下一个后选字";
"Starlight" = "星光排列";
"Stop farting (when typed phonetic combination is invalid, etc.)" = "廉耻模式 // 取消勾选的话,敲错字时会有异音";
"This only works since macOS 12 with non-IMK candidate window as an alternative wordaround of Apple Bug Report #FB10978412. Apple should patch that for macOS 11 and later." = "该方法是 Apple Bug Report #FB10978412 的保守治疗方案,用来仅针对 macOS 12 开始的系统,且仅对非 IMK 选字窗起作用。Apple 应该对 macOS 11 开始的系统修复这个 Bug。";
"Traditional Chinese" = "繁体中文";
"Type them into inline composition buffer" = "直接键入内文组字区";
"Typing Style:" = "输入风格:";
"UI Language:" = "介面语言:";
"Universal Pinyin with Numeral Intonation" = "通用拼音+数字标调";
"Universal Pinyin with Numeral Intonation" = "通用拼音+数字标调";
"Use .langIdentifier to handle UI fonts in candidate window" = "使用 .langIdentifier 来管理选字窗的预设介面字型";
"Use ESC key to clear the entire input buffer" = "敲 ESC 键以清空整个组字缓冲区";
"Use IMK Candidate Window instead (will reboot the IME)" = "启用 IMK 选字窗(会自动重启输入法)";
"Vertical" = "纵向布局";
"Warning: This page is for testing future features. \nFeatures listed here may not work as expected." = "警告:该页面仅作未来功能测试所用。\n在此列出的功能并非处于完全可用之状态。";
"Yale Pinyin with Numeral Intonation" = "耶鲁拼音+数字标调";

View File

@ -39,7 +39,7 @@
"Please specify at least 4 candidate keys." = "請至少指定四個選字鍵。";
"Maximum 15 candidate keys allowed." = "選字鍵最多只能指定十五個。";
"⚠︎ Phrase replacement mode enabled, interfering user phrase entry." = "⚠︎ 語彙置換功能已啟用,會波及語彙自訂。";
"⚠︎ Beware: Chars and Readings in buffer doesn't match." = "⚠︎ 注意:組字區字數與讀音數不對應。";
"⚠︎ Unhandlable: Chars and Readings in buffer doesn't match." = "⚠︎ 無法處理:組字區字數與讀音數不對應。";
"Per-Char Select Mode" = "模擬逐字選字輸入";
"CNS11643 Mode" = "全字庫模式";
"JIS Shinjitai Output" = "JIS 新字體模式";
@ -123,7 +123,8 @@
"Dachen (Microsoft Standard / Wang / 01, etc.)" = "大千排列 (微軟標準/王安/零壹/仲鼎/國喬)";
"Dachen 26 (libChewing)" = "酷音大千二十六鍵排列";
"Debug Mode" = "偵錯模式";
"Dictionary" = "辭典";
"DevZone" = "開發道場";
"Dictionary" = "辭典設定";
"Directly commit lowercased letters" = "直接遞交小寫字母";
"Directly commit uppercased letters" = "直接遞交大寫字母";
"Emulating select-candidate-per-character mode" = "模擬 90 年代前期注音逐字選字輸入風格";
@ -133,21 +134,22 @@
"English" = "英語";
"Eten 26" = "倚天忘形排列 (26 鍵)";
"Eten Traditional" = "倚天傳統排列";
"Experience" = "體驗";
"Experience" = "體驗設定";
"Fake Seigyou" = "偽精業排列";
"Follow OS settings" = "依系統設定";
"for cycling candidates" = "輪替候選字";
"for cycling pages" = "輪替頁面";
"General" = "通用";
"General" = "通用設定";
"Hanyu Pinyin with Numeral Intonation" = "漢語拼音+數字標調";
"Horizontal" = "橫向佈局";
"Hsu" = "許氏國音自然排列";
"Hualuo Pinyin with Numeral Intonation" = "華羅拼音+數字標調";
"IBM" = "IBM 排列";
"IMK candidate window is plagued with issues like failed selection keys." = "IMK 選字窗目前暫時無法正常使用選字鍵,併具其它未知故障。";
"in front of the phrase (like macOS built-in Zhuyin IME)" = "將游標置於詞語前方 // macOS 內建注音風格";
"Japanese" = "和語";
"Keyboard Shortcuts:" = "鍵盤快速鍵:";
"Keyboard" = "鍵盤";
"Keyboard" = "鍵盤設定";
"Misc Settings:" = "雜項:";
"MiTAC" = "神通排列";
"Non-QWERTY alphanumerical keyboard layouts are for Hanyu Pinyin parser only." = "QWERTY 以外的英數佈局是為了漢語拼音排列使用者而準備的。";
@ -166,11 +168,15 @@
"Space to +cycle pages, Shift+Space to +cycle candidates" = "空格鍵 換下一頁Shift+空格鍵 換選下一個後選字";
"Starlight" = "星光排列";
"Stop farting (when typed phonetic combination is invalid, etc.)" = "廉恥模式 // 取消勾選的話,敲錯字時會有異音";
"This only works since macOS 12 with non-IMK candidate window as an alternative wordaround of Apple Bug Report #FB10978412. Apple should patch that for macOS 11 and later." = "該方法是 Apple Bug Report #FB10978412 的保守治療方案,用來僅針對 macOS 12 開始的系統,且僅對非 IMK 選字窗起作用。Apple 應該對 macOS 11 開始的系統修復這個 Bug。";
"Traditional Chinese" = "繁體中文";
"Type them into inline composition buffer" = "直接鍵入內文組字區";
"Typing Style:" = "輸入風格:";
"UI Language:" = "介面語言:";
"Universal Pinyin with Numeral Intonation" = "通用拼音+數字標調";
"Use .langIdentifier to handle UI fonts in candidate window" = "使用 .langIdentifier 來管理選字窗的預設介面字型";
"Use ESC key to clear the entire input buffer" = "敲 ESC 鍵以清空整個組字緩衝區";
"Use IMK Candidate Window instead (will reboot the IME)" = "啟用 IMK 選字窗(會自動重啟輸入法)";
"Vertical" = "縱向佈局";
"Warning: This page is for testing future features. \nFeatures listed here may not work as expected." = "警告:該頁面僅作未來功能測試所用。\n在此列出的功能並非處於完全可用之狀態。";
"Yale Pinyin with Numeral Intonation" = "耶魯拼音+數字標調";

View File

@ -18,8 +18,6 @@ public class ctlCandidateIMK: IMKCandidates, ctlCandidateProtocol {
}
}
public var selectedCandidateIndex: Int = .max
public var visible: Bool = false {
didSet {
if visible {
@ -30,10 +28,14 @@ public class ctlCandidateIMK: IMKCandidates, ctlCandidateProtocol {
}
}
public var windowTopLeftPoint: NSPoint = .init(x: 0, y: 0) {
didSet {
public var windowTopLeftPoint: NSPoint {
get {
let frameRect = candidateFrame()
return NSPoint(x: frameRect.minX, y: frameRect.maxY)
}
set {
DispatchQueue.main.asyncAfter(deadline: DispatchTime.now()) {
self.set(windowTopLeftPoint: self.windowTopLeftPoint, bottomOutOfScreenAdjustmentHeight: 0)
self.set(windowTopLeftPoint: newValue, bottomOutOfScreenAdjustmentHeight: 0)
}
}
}
@ -60,7 +62,8 @@ public class ctlCandidateIMK: IMKCandidates, ctlCandidateProtocol {
case .vertical:
setPanelType(kIMKSingleColumnScrollingCandidatePanel)
}
setAttributes([IMKCandidatesSendServerKeyEventFirst: false])
// true ctlIME
setAttributes([IMKCandidatesSendServerKeyEventFirst: true])
}
public required init(_ layout: CandidateLayout = .horizontal) {
@ -86,40 +89,151 @@ public class ctlCandidateIMK: IMKCandidates, ctlCandidateProtocol {
update()
}
/// IMKCandidates
/// IMK keyHandler `ctlIME_Core`
private var currentPageIndex: Int = 0
private var pageCount: Int {
guard let delegate = delegate else {
return 0
}
let totalCount = delegate.candidateCountForController(self)
let keyLabelCount = keyLabels.count
return totalCount / keyLabelCount + ((totalCount % keyLabelCount) != 0 ? 1 : 0)
}
public func showNextPage() -> Bool {
guard delegate != nil else { return false }
if pageCount == 1 { return highlightNextCandidate() }
if currentPageIndex + 1 >= pageCount { clsSFX.beep() }
currentPageIndex = (currentPageIndex + 1 >= pageCount) ? 0 : currentPageIndex + 1
if selectedCandidateIndex == candidates(self).count - 1 { return false }
selectedCandidateIndex = min(selectedCandidateIndex + keyCount, candidates(self).count - 1)
return selectCandidate(withIdentifier: selectedCandidateIndex)
pageDownAndModifySelection(self)
return true
}
public func showPreviousPage() -> Bool {
guard delegate != nil else { return false }
if pageCount == 1 { return highlightPreviousCandidate() }
if currentPageIndex == 0 { clsSFX.beep() }
currentPageIndex = (currentPageIndex == 0) ? pageCount - 1 : currentPageIndex - 1
if selectedCandidateIndex == 0 { return true }
selectedCandidateIndex = max(selectedCandidateIndex - keyCount, 0)
return selectCandidate(withIdentifier: selectedCandidateIndex)
pageUpAndModifySelection(self)
return true
}
public func highlightNextCandidate() -> Bool {
if selectedCandidateIndex == candidates(self).count - 1 { return false }
selectedCandidateIndex = min(selectedCandidateIndex + 1, candidates(self).count - 1)
return selectCandidate(withIdentifier: selectedCandidateIndex)
guard let delegate = delegate else { return false }
selectedCandidateIndex =
(selectedCandidateIndex + 1 >= delegate.candidateCountForController(self))
? 0 : selectedCandidateIndex + 1
switch currentLayout {
case .horizontal:
moveRight(self)
return true
case .vertical:
moveDown(self)
return true
}
}
public func highlightPreviousCandidate() -> Bool {
if selectedCandidateIndex == 0 { return true }
selectedCandidateIndex = max(selectedCandidateIndex - 1, 0)
return selectCandidate(withIdentifier: selectedCandidateIndex)
}
public func candidateIndexAtKeyLabelIndex(_: Int) -> Int {
selectedCandidateIndex
}
public func set(windowTopLeftPoint: NSPoint, bottomOutOfScreenAdjustmentHeight _: CGFloat = 0) {
setCandidateFrameTopLeft(windowTopLeftPoint)
}
override public func handle(_ event: NSEvent!, client _: Any!) -> Bool {
guard let delegate = delegate else { return false }
return delegate.handleDelegateEvent(event)
selectedCandidateIndex =
(selectedCandidateIndex == 0)
? delegate.candidateCountForController(self) - 1 : selectedCandidateIndex - 1
switch currentLayout {
case .horizontal:
moveLeft(self)
return true
case .vertical:
moveUp(self)
return true
}
}
public func candidateIndexAtKeyLabelIndex(_ index: Int) -> Int {
guard let delegate = delegate else {
return Int.max
}
let result = currentPageIndex * keyLabels.count + index
return result < delegate.candidateCountForController(self) ? result : Int.max
}
public var selectedCandidateIndex: Int {
get {
selectedCandidate()
}
set {
selectCandidate(withIdentifier: newValue)
}
}
public func set(windowTopLeftPoint: NSPoint, bottomOutOfScreenAdjustmentHeight height: CGFloat) {
DispatchQueue.main.asyncAfter(deadline: DispatchTime.now()) {
self.doSet(
windowTopLeftPoint: windowTopLeftPoint, bottomOutOfScreenAdjustmentHeight: height
)
}
}
func doSet(windowTopLeftPoint: NSPoint, bottomOutOfScreenAdjustmentHeight height: CGFloat) {
var adjustedPoint = windowTopLeftPoint
var adjustedHeight = height
var screenFrame = NSScreen.main?.visibleFrame ?? NSRect.zero
for screen in NSScreen.screens {
let frame = screen.visibleFrame
if windowTopLeftPoint.x >= frame.minX, windowTopLeftPoint.x <= frame.maxX,
windowTopLeftPoint.y >= frame.minY, windowTopLeftPoint.y <= frame.maxY
{
screenFrame = frame
break
}
}
if adjustedHeight > screenFrame.size.height / 2.0 {
adjustedHeight = 0.0
}
let windowSize = candidateFrame().size
// bottom beneath the screen?
if adjustedPoint.y - windowSize.height < screenFrame.minY {
adjustedPoint.y = windowTopLeftPoint.y + adjustedHeight + windowSize.height
}
// top over the screen?
if adjustedPoint.y >= screenFrame.maxY {
adjustedPoint.y = screenFrame.maxY - 1.0
}
// right
if adjustedPoint.x + windowSize.width >= screenFrame.maxX {
adjustedPoint.x = screenFrame.maxX - windowSize.width
}
// left
if adjustedPoint.x < screenFrame.minX {
adjustedPoint.x = screenFrame.minX
}
setCandidateFrameTopLeft(adjustedPoint)
}
override public func interpretKeyEvents(_ eventArray: [NSEvent]) {
guard !eventArray.isEmpty else { return }
let event = eventArray[0]
let input = InputSignal(event: event)
guard let delegate = delegate else { return }
if input.isEsc || input.isBackSpace || input.isDelete || input.isShiftHold {
_ = delegate.handleDelegateEvent(event)
} else {
super.interpretKeyEvents(eventArray)
}
}
}

View File

@ -82,7 +82,7 @@ private class vwrCandidateUniversal: NSView {
switch isVerticalLayout {
case true:
if calculatedWindowWidth < rctCandidate.size.width {
calculatedWindowWidth = rctCandidate.size.width + cellPadding
calculatedWindowWidth = rctCandidate.size.width + cellPadding * 2
}
case false:
if cellWidth < cellHeight * 1.35 {
@ -137,46 +137,40 @@ private class vwrCandidateUniversal: NSView {
NSColor.controlBackgroundColor.setFill() // Candidate list panel base background
NSBezierPath.fill(bounds)
NSColor.systemGray.withAlphaComponent(0.75).setStroke()
NSBezierPath.strokeLine(
from: NSPoint(x: bounds.size.width, y: 0.0),
to: NSPoint(x: bounds.size.width, y: bounds.size.height)
)
switch isVerticalLayout {
case true:
var accuHeight: CGFloat = 0
for (index, elementHeight) in elementHeights.enumerated() {
let currentHeight = elementHeight
let rctCandidateArea = NSRect(
x: 0.0, y: accuHeight, width: windowWidth, height: candidateTextHeight + cellPadding
x: 3.0, y: accuHeight + 3.0, width: windowWidth - 6.0,
height: candidateTextHeight + cellPadding - 6.0
)
let rctLabel = NSRect(
x: cellPadding / 2 - 1, y: accuHeight + cellPadding / 2, width: keyLabelWidth,
x: cellPadding / 2 + 2, y: accuHeight + cellPadding / 2, width: keyLabelWidth,
height: keyLabelHeight * 2.0
)
let rctCandidatePhrase = NSRect(
x: cellPadding / 2 - 1 + keyLabelWidth, y: accuHeight + cellPadding / 2 - 1,
x: cellPadding / 2 + 2 + keyLabelWidth, y: accuHeight + cellPadding / 2 - 1,
width: windowWidth - keyLabelWidth, height: candidateTextHeight
)
var activeCandidateIndexAttr = keyLabelAttrDict
var activeCandidateAttr = candidateAttrDict
if index == highlightedIndex {
let colorBlendAmount: CGFloat = IME.isDarkMode() ? 0.25 : 0
let colorBlendAmount: CGFloat = IME.isDarkMode() ? 0.3 : 0
// The background color of the highlightened candidate
switch IME.currentInputMode {
case InputMode.imeModeCHS:
NSColor.systemRed.blended(
withFraction: colorBlendAmount,
of: NSColor.controlBackgroundColor
of: NSColor.black
)!
.setFill()
case InputMode.imeModeCHT:
NSColor.systemBlue.blended(
withFraction: colorBlendAmount,
of: NSColor.controlBackgroundColor
of: NSColor.black
)!
.setFill()
default:
@ -190,7 +184,24 @@ private class vwrCandidateUniversal: NSView {
} else {
NSColor.controlBackgroundColor.setFill()
}
NSBezierPath.fill(rctCandidateArea)
if mgrPrefs.handleDefaultCandidateFontsByLangIdentifier {
switch IME.currentInputMode {
case InputMode.imeModeCHS:
if #available(macOS 12.0, *) {
activeCandidateAttr[.languageIdentifier] = "zh-Hans" as AnyObject
}
case InputMode.imeModeCHT:
if #available(macOS 12.0, *) {
activeCandidateAttr[.languageIdentifier] =
(mgrPrefs.shiftJISShinjitaiOutputEnabled || mgrPrefs.chineseConversionEnabled)
? "ja" as AnyObject : "zh-Hant" as AnyObject
}
default:
break
}
}
let path: NSBezierPath = .init(roundedRect: rctCandidateArea, xRadius: 5, yRadius: 5)
path.fill()
(keyLabels[index] as NSString).draw(
in: rctLabel, withAttributes: activeCandidateIndexAttr
)
@ -204,8 +215,8 @@ private class vwrCandidateUniversal: NSView {
for (index, elementWidth) in elementWidths.enumerated() {
let currentWidth = elementWidth
let rctCandidateArea = NSRect(
x: accuWidth, y: 0.0, width: currentWidth + 1.0,
height: candidateTextHeight + cellPadding
x: accuWidth + 3.0, y: 3.0, width: currentWidth + 1.0 - 6.0,
height: candidateTextHeight + cellPadding - 6.0
)
let rctLabel = NSRect(
x: accuWidth + cellPadding / 2 - 1, y: cellPadding / 2, width: keyLabelWidth,
@ -220,19 +231,19 @@ private class vwrCandidateUniversal: NSView {
var activeCandidateIndexAttr = keyLabelAttrDict
var activeCandidateAttr = candidateAttrDict
if index == highlightedIndex {
let colorBlendAmount: CGFloat = IME.isDarkMode() ? 0.25 : 0
let colorBlendAmount: CGFloat = IME.isDarkMode() ? 0.3 : 0
// The background color of the highlightened candidate
switch IME.currentInputMode {
case InputMode.imeModeCHS:
NSColor.systemRed.blended(
withFraction: colorBlendAmount,
of: NSColor.controlBackgroundColor
of: NSColor.black
)!
.setFill()
case InputMode.imeModeCHT:
NSColor.systemBlue.blended(
withFraction: colorBlendAmount,
of: NSColor.controlBackgroundColor
of: NSColor.black
)!
.setFill()
default:
@ -246,7 +257,24 @@ private class vwrCandidateUniversal: NSView {
} else {
NSColor.controlBackgroundColor.setFill()
}
NSBezierPath.fill(rctCandidateArea)
if mgrPrefs.handleDefaultCandidateFontsByLangIdentifier {
switch IME.currentInputMode {
case InputMode.imeModeCHS:
if #available(macOS 12.0, *) {
activeCandidateAttr[.languageIdentifier] = "zh-Hans" as AnyObject
}
case InputMode.imeModeCHT:
if #available(macOS 12.0, *) {
activeCandidateAttr[.languageIdentifier] =
(mgrPrefs.shiftJISShinjitaiOutputEnabled || mgrPrefs.chineseConversionEnabled)
? "ja" as AnyObject : "zh-Hant" as AnyObject
}
default:
break
}
}
let path: NSBezierPath = .init(roundedRect: rctCandidateArea, xRadius: 5, yRadius: 5)
path.fill()
(keyLabels[index] as NSString).draw(
in: rctLabel, withAttributes: activeCandidateIndexAttr
)
@ -352,10 +380,10 @@ public class ctlCandidateUniversal: ctlCandidate {
candidateView.wantsLayer = true
candidateView.layer?.borderColor =
NSColor.selectedMenuItemTextColor.withAlphaComponent(0.10).cgColor
NSColor.selectedMenuItemTextColor.withAlphaComponent(0.20).cgColor
candidateView.layer?.borderWidth = 1.0
if #available(macOS 10.13, *) {
candidateView.layer?.cornerRadius = 6.0
candidateView.layer?.cornerRadius = 8.0
}
panel.contentView?.addSubview(candidateView)

View File

@ -15,6 +15,7 @@ class ctlPrefUI {
private(set) var tabImageExperiences: NSImage! = NSImage(named: "PrefToolbar-Experiences")
private(set) var tabImageDictionary: NSImage! = NSImage(named: "PrefToolbar-Dictionary")
private(set) var tabImageKeyboard: NSImage! = NSImage(named: "PrefToolbar-Keyboard")
private(set) var tabImageDevZone: NSImage! = NSImage(named: "PrefToolbar-DevZone")
init() {
if #available(macOS 11.0, *) {
@ -30,6 +31,9 @@ class ctlPrefUI {
tabImageKeyboard = NSImage(
systemSymbolName: "keyboard.macwindow", accessibilityDescription: "Keyboard Preferences"
)
tabImageDevZone = NSImage(
systemSymbolName: "hand.raised.circle", accessibilityDescription: "DevZone Preferences"
)
}
}
@ -63,6 +67,13 @@ class ctlPrefUI {
) {
suiPrefPaneKeyboard()
},
Preferences.Pane(
identifier: Preferences.PaneIdentifier(rawValue: "DevZone"),
title: NSLocalizedString("DevZone", comment: ""),
toolbarIcon: tabImageDevZone
) {
suiPrefPaneDevZone()
},
],
style: .toolbarItems
)

View File

@ -0,0 +1,69 @@
// Copyright (c) 2021 and onwards The vChewing Project (MIT-NTL License).
// ====================
// This code is released under the MIT license (SPDX-License-Identifier: MIT)
// ... with NTL restriction stating that:
// No trademark license is granted to use the trade names, trademarks, service
// marks, or product names of Contributor, except as required to fulfill notice
// requirements defined in MIT License.
import SwiftUI
@available(macOS 10.15, *)
struct suiPrefPaneDevZone: View {
@State private var selUseIMKCandidateWindow: Bool = UserDefaults.standard.bool(
forKey: UserDef.kUseIMKCandidateWindow.rawValue)
@State private var selHandleDefaultCandidateFontsByLangIdentifier: Bool = UserDefaults.standard.bool(
forKey: UserDef.kHandleDefaultCandidateFontsByLangIdentifier.rawValue)
private let contentWidth: Double = {
switch mgrPrefs.appleLanguages[0] {
case "ja":
return 520
default:
if mgrPrefs.appleLanguages[0].contains("zh-Han") {
return 480
} else {
return 550
}
}
}()
var body: some View {
Preferences.Container(contentWidth: contentWidth) {
Preferences.Section(title: "", bottomDivider: true) {
Text(
LocalizedStringKey(
"Warning: This page is for testing future features. \nFeatures listed here may not work as expected.")
)
.fixedSize(horizontal: false, vertical: true)
Divider()
Toggle(
LocalizedStringKey("Use IMK Candidate Window instead (will reboot the IME)"),
isOn: $selUseIMKCandidateWindow.onChange {
mgrPrefs.useIMKCandidateWindow = selUseIMKCandidateWindow
}
)
Text(LocalizedStringKey("IMK candidate window is plagued with issues like failed selection keys."))
.preferenceDescription().fixedSize(horizontal: false, vertical: true)
Toggle(
LocalizedStringKey("Use .langIdentifier to handle UI fonts in candidate window"),
isOn: $selHandleDefaultCandidateFontsByLangIdentifier.onChange {
mgrPrefs.handleDefaultCandidateFontsByLangIdentifier = selHandleDefaultCandidateFontsByLangIdentifier
}
)
Text(
LocalizedStringKey(
"This only works since macOS 12 with non-IMK candidate window as an alternative wordaround of Apple Bug Report #FB10978412. Apple should patch that for macOS 11 and later."
)
)
.preferenceDescription().fixedSize(horizontal: false, vertical: true)
}
}
}
}
@available(macOS 11.0, *)
struct suiPrefPaneDevZone_Previews: PreviewProvider {
static var previews: some View {
suiPrefPaneDevZone()
}
}

View File

@ -18,6 +18,7 @@ extension NSToolbarItem.Identifier {
fileprivate static let ofExperience = NSToolbarItem.Identifier(rawValue: "tabExperience")
fileprivate static let ofDictionary = NSToolbarItem.Identifier(rawValue: "tabDictionary")
fileprivate static let ofKeyboard = NSToolbarItem.Identifier(rawValue: "tabKeyboard")
fileprivate static let ofDevZone = NSToolbarItem.Identifier(rawValue: "tabDevZone")
}
// Please note that the class should be exposed using the same class name
@ -32,11 +33,13 @@ class ctlPrefWindow: NSWindowController {
@IBOutlet var chkTrad2KangXi: NSButton!
@IBOutlet var chkTrad2JISShinjitai: NSButton!
@IBOutlet var lblCurrentlySpecifiedUserDataFolder: NSTextFieldCell!
@IBOutlet var tglControlDevZoneIMKCandidate: NSButton!
@IBOutlet var vwrGeneral: NSView!
@IBOutlet var vwrExperience: NSView!
@IBOutlet var vwrDictionary: NSView!
@IBOutlet var vwrKeyboard: NSView!
@IBOutlet var vwrDevZone: NSView!
var currentLanguageSelectItem: NSMenuItem?
@ -236,6 +239,10 @@ class ctlPrefWindow: NSWindowController {
}
}
@IBAction func updateIMKCandidateEnableStatusAction(_: Any) {
NSApplication.shared.terminate(nil)
}
@IBAction func clickedWhetherIMEShouldNotFartToggleAction(_: Any) {
clsSFX.beep()
}
@ -329,15 +336,15 @@ extension ctlPrefWindow: NSToolbarDelegate {
}
func toolbarDefaultItemIdentifiers(_: NSToolbar) -> [NSToolbarItem.Identifier] {
[.ofGeneral, .ofExperience, .ofDictionary, .ofKeyboard]
[.ofGeneral, .ofExperience, .ofDictionary, .ofKeyboard, .ofDevZone]
}
func toolbarAllowedItemIdentifiers(_: NSToolbar) -> [NSToolbarItem.Identifier] {
[.ofGeneral, .ofExperience, .ofDictionary, .ofKeyboard]
[.ofGeneral, .ofExperience, .ofDictionary, .ofKeyboard, .ofDevZone]
}
func toolbarSelectableItemIdentifiers(_: NSToolbar) -> [NSToolbarItem.Identifier] {
[.ofGeneral, .ofExperience, .ofDictionary, .ofKeyboard]
[.ofGeneral, .ofExperience, .ofDictionary, .ofKeyboard, .ofDevZone]
}
@objc func showGeneralView(_: Any?) {
@ -360,6 +367,11 @@ extension ctlPrefWindow: NSToolbarDelegate {
window?.toolbar?.selectedItemIdentifier = .ofKeyboard
}
@objc func showDevZoneView(_: Any?) {
use(view: vwrDevZone)
window?.toolbar?.selectedItemIdentifier = .ofDevZone
}
func toolbar(
_: NSToolbar, itemForItemIdentifier itemIdentifier: NSToolbarItem.Identifier,
willBeInsertedIntoToolbar _: Bool
@ -413,6 +425,18 @@ extension ctlPrefWindow: NSToolbarDelegate {
}
item.action = #selector(showKeyboardView(_:))
case .ofDevZone:
let title = NSLocalizedString("DevZone", comment: "")
item.label = title
if #available(macOS 11.0, *) {
item.image = NSImage(
systemSymbolName: "hand.raised.circle", accessibilityDescription: "DevZone Preferences"
)
} else {
item.image = NSImage(named: "PrefToolbar-DevZone")
}
item.action = #selector(showDevZoneView(_:))
default:
return nil
}

View File

@ -14,7 +14,9 @@
<outlet property="fontSizePopUpButton" destination="90" id="108"/>
<outlet property="lblCurrentlySpecifiedUserDataFolder" destination="REC-r4-T7m" id="eEq-XN-mMq"/>
<outlet property="selectionKeyComboBox" destination="uHU-aL-du7" id="cEx-Ui-Phc"/>
<outlet property="tglControlDevZoneIMKCandidate" destination="tglControlDevZoneIMKCandidate" id="eyT-uP-QU6"/>
<outlet property="uiLanguageButton" destination="oS6-u5-7dP" id="V3u-XK-z7G"/>
<outlet property="vwrDevZone" destination="Qd7-ln-nNO" id="8mw-wO-gXS"/>
<outlet property="vwrDictionary" destination="Rnp-LM-RIF" id="8gY-ah-RT8"/>
<outlet property="vwrExperience" destination="XWo-36-xGi" id="hC5-gV-NWn"/>
<outlet property="vwrGeneral" destination="BUt-lg-GPp" id="PC2-Sj-V4Q"/>
@ -1054,5 +1056,92 @@
</constraints>
<point key="canvasLocation" x="-392" y="-704"/>
</visualEffectView>
<visualEffectView blendingMode="behindWindow" material="sidebar" state="followsWindowActiveState" id="Qd7-ln-nNO" userLabel="vwrDevZone">
<rect key="frame" x="0.0" y="0.0" width="445" height="261"/>
<autoresizingMask key="autoresizingMask"/>
<subviews>
<textField verticalHuggingPriority="750" translatesAutoresizingMaskIntoConstraints="NO" id="lblControlDevZoneTitleDescription" userLabel="lblControlDevZoneTitleDescription">
<rect key="frame" x="18" y="211" width="409" height="30"/>
<textFieldCell key="cell" scrollable="YES" lineBreakMode="clipping" sendsActionOnEndEditing="YES" alignment="left" id="lblDevZoneTitleDescription">
<font key="font" metaFont="cellTitle"/>
<string key="title">Warning: This page is for testing future features.
Features listed here may not work as expected.</string>
<color key="textColor" name="labelColor" catalog="System" colorSpace="catalog"/>
<color key="backgroundColor" name="textBackgroundColor" catalog="System" colorSpace="catalog"/>
</textFieldCell>
</textField>
<box verticalHuggingPriority="750" boxType="separator" translatesAutoresizingMaskIntoConstraints="NO" id="P1o-bW-Tjn">
<rect key="frame" x="20" y="200" width="405" height="5"/>
</box>
<button verticalHuggingPriority="750" translatesAutoresizingMaskIntoConstraints="NO" id="tglControlDevZoneIMKCandidate" userLabel="tglControlDevZoneIMKCandidate">
<rect key="frame" x="19" y="178.5" width="406" height="17"/>
<constraints>
<constraint firstAttribute="height" constant="16" id="1fy-CP-mlB"/>
</constraints>
<buttonCell key="cell" type="check" title="Use IMK Candidate Window instead (will reboot the IME)" bezelStyle="regularSquare" imagePosition="left" controlSize="small" state="on" inset="2" id="tglDevZoneIMKCandidate" userLabel="tglDevZoneIMKCandidate">
<behavior key="behavior" changeContents="YES" doesNotDimImage="YES" lightByContents="YES"/>
<font key="font" metaFont="cellTitle"/>
</buttonCell>
<connections>
<action selector="updateIMKCandidateEnableStatusAction:" target="-2" id="mkT-P8-reE"/>
<binding destination="32" name="value" keyPath="values.UseIMKCandidateWindow" id="XjP-hu-rUm"/>
</connections>
</button>
<textField wantsLayer="YES" verticalHuggingPriority="750" translatesAutoresizingMaskIntoConstraints="NO" id="lblControlDevZoneIMKCandidate" userLabel="lblControlDevZoneIMKCandidate">
<rect key="frame" x="18" y="142" width="409" height="28"/>
<textFieldCell key="cell" sendsActionOnEndEditing="YES" alignment="left" title="IMK candidate window is plagued with issues like malfunctioned selection keys, etc." id="lblDevZoneIMKCandidate">
<font key="font" metaFont="smallSystem"/>
<color key="textColor" name="secondaryLabelColor" catalog="System" colorSpace="catalog"/>
<color key="backgroundColor" name="textBackgroundColor" catalog="System" colorSpace="catalog"/>
</textFieldCell>
</textField>
<button verticalHuggingPriority="750" translatesAutoresizingMaskIntoConstraints="NO" id="tglControlDevZoneCandidateFont" userLabel="tglControlDevZoneCandidateFont">
<rect key="frame" x="19" y="118.5" width="406" height="18"/>
<constraints>
<constraint firstAttribute="height" constant="17" id="eCc-Cc-xvc"/>
</constraints>
<buttonCell key="cell" type="check" title="Use .langIdentifier to handle UI fonts in candidate window" bezelStyle="regularSquare" imagePosition="left" controlSize="small" state="on" inset="2" id="tglDevZoneCandidateFont" userLabel="tglDevZoneCandidateFont">
<behavior key="behavior" changeContents="YES" doesNotDimImage="YES" lightByContents="YES"/>
<font key="font" metaFont="cellTitle"/>
</buttonCell>
<connections>
<binding destination="32" name="value" keyPath="values.HandleDefaultCandidateFontsByLangIdentifier" id="EEd-Z8-b5S"/>
</connections>
</button>
<textField wantsLayer="YES" verticalHuggingPriority="750" translatesAutoresizingMaskIntoConstraints="NO" id="lblControlDevZoneCandidateFont" userLabel="lblControlDevZoneCandidateFont">
<rect key="frame" x="18" y="68" width="409" height="42"/>
<constraints>
<constraint firstAttribute="width" constant="405" id="1OL-J2-FUX"/>
</constraints>
<textFieldCell key="cell" sendsActionOnEndEditing="YES" alignment="left" id="lblDevZoneCandidateFont">
<font key="font" metaFont="smallSystem"/>
<string key="title">This only works since macOS 12 with non-IMK candidate window as an alternative wordaround of Apple Bug Report #FB10978412. Apple should patch that for macOS 11 and later.</string>
<color key="textColor" name="secondaryLabelColor" catalog="System" colorSpace="catalog"/>
<color key="backgroundColor" name="textBackgroundColor" catalog="System" colorSpace="catalog"/>
</textFieldCell>
</textField>
</subviews>
<constraints>
<constraint firstItem="lblControlDevZoneTitleDescription" firstAttribute="leading" secondItem="Qd7-ln-nNO" secondAttribute="leading" constant="20" symbolic="YES" id="0Ia-ut-ksj"/>
<constraint firstItem="tglControlDevZoneIMKCandidate" firstAttribute="top" secondItem="P1o-bW-Tjn" secondAttribute="bottom" constant="7.5" id="3as-Db-NwQ"/>
<constraint firstItem="tglControlDevZoneIMKCandidate" firstAttribute="leading" secondItem="lblControlDevZoneIMKCandidate" secondAttribute="leading" id="59X-nd-Otf"/>
<constraint firstItem="lblControlDevZoneIMKCandidate" firstAttribute="leading" secondItem="tglControlDevZoneCandidateFont" secondAttribute="leading" id="COk-L6-3R8"/>
<constraint firstItem="lblControlDevZoneCandidateFont" firstAttribute="top" secondItem="tglControlDevZoneCandidateFont" secondAttribute="bottom" constant="8.5" id="EyK-gG-Xhd"/>
<constraint firstItem="P1o-bW-Tjn" firstAttribute="trailing" secondItem="tglControlDevZoneIMKCandidate" secondAttribute="trailing" id="LM7-ov-mng"/>
<constraint firstItem="lblControlDevZoneTitleDescription" firstAttribute="trailing" secondItem="P1o-bW-Tjn" secondAttribute="trailing" id="LqC-ii-aOO"/>
<constraint firstAttribute="bottom" relation="lessThanOrEqual" secondItem="lblControlDevZoneCandidateFont" secondAttribute="bottom" constant="82" id="NVG-bX-Lgd"/>
<constraint firstItem="tglControlDevZoneCandidateFont" firstAttribute="top" secondItem="lblControlDevZoneIMKCandidate" secondAttribute="bottom" constant="6.5" id="UXh-8X-5wM"/>
<constraint firstItem="lblControlDevZoneTitleDescription" firstAttribute="leading" secondItem="P1o-bW-Tjn" secondAttribute="leading" id="Wc3-Oe-D2E"/>
<constraint firstItem="P1o-bW-Tjn" firstAttribute="top" secondItem="lblControlDevZoneTitleDescription" secondAttribute="bottom" constant="8" symbolic="YES" id="Whf-Gf-g65"/>
<constraint firstItem="lblControlDevZoneIMKCandidate" firstAttribute="top" secondItem="tglControlDevZoneIMKCandidate" secondAttribute="bottom" constant="8.5" id="awf-DD-u2k"/>
<constraint firstItem="P1o-bW-Tjn" firstAttribute="leading" secondItem="tglControlDevZoneIMKCandidate" secondAttribute="leading" id="f2q-KJ-bvO"/>
<constraint firstItem="tglControlDevZoneCandidateFont" firstAttribute="trailing" secondItem="lblControlDevZoneCandidateFont" secondAttribute="trailing" id="gWx-J5-kgO"/>
<constraint firstItem="tglControlDevZoneIMKCandidate" firstAttribute="trailing" secondItem="lblControlDevZoneIMKCandidate" secondAttribute="trailing" id="lQf-A0-TPV"/>
<constraint firstItem="tglControlDevZoneCandidateFont" firstAttribute="leading" secondItem="lblControlDevZoneCandidateFont" secondAttribute="leading" id="oCd-O4-Qfg"/>
<constraint firstItem="lblControlDevZoneTitleDescription" firstAttribute="top" secondItem="Qd7-ln-nNO" secondAttribute="top" constant="20" symbolic="YES" id="vYg-x4-tfo"/>
<constraint firstItem="lblControlDevZoneIMKCandidate" firstAttribute="trailing" secondItem="tglControlDevZoneCandidateFont" secondAttribute="trailing" id="z47-zE-rak"/>
</constraints>
<point key="canvasLocation" x="-393.5" y="-70.5"/>
</visualEffectView>
</objects>
</document>

View File

@ -63,6 +63,9 @@
"jQC-12-UuK.ibShadowedObjectValues[0]" = "Item 1";
"jQC-12-UuK.ibShadowedObjectValues[1]" = "Item 2";
"jQC-12-UuK.ibShadowedObjectValues[2]" = "Item 3";
"lblDevZoneCandidateFont.title" = "This only works since macOS 12 with non-IMK candidate window as an alternative wordaround of Apple Bug Report #FB10978412. Apple should patch that for macOS 11 and later.";
"lblDevZoneIMKCandidate.title" = "IMK candidate window is plagued with issues like failed selection keys.";
"lblDevZoneTitleDescription.title" = "Warning: This page is for testing future features. \nFeatures listed here may not work as expected.";
"lblUpperCaseLetterKeyBehavior.title" = "Choose the behavior of Shift+Letter key with letter inputs.";
"Parser11.title" = "Secondary Pinyin with Numeral Intonation";
"Parser12.title" = "Yale Pinyin with Numeral Intonation";
@ -78,6 +81,8 @@
"rVQ-Hx-cGi.title" = "Japanese";
"s7u-Fm-dVg.title" = "Cycling Pages";
"shc-Nu-UsM.title" = "Show page buttons in candidate list";
"tglDevZoneCandidateFont.title" = "Use .langIdentifier to handle UI fonts in candidate window";
"tglDevZoneIMKCandidate.title" = "Use IMK Candidate Window instead (will reboot the IME)";
"TXr-FF-ehw.title" = "Traditional Chinese";
"ueU-Rz-a1C.title" = "Choose the behavior of (Shift+)Tab key in the candidate window.";
"VdT-fw-7pQ.title" = "Debug Mode";

View File

@ -63,6 +63,9 @@
"jQC-12-UuK.ibShadowedObjectValues[0]" = "Item 1";
"jQC-12-UuK.ibShadowedObjectValues[1]" = "Item 2";
"jQC-12-UuK.ibShadowedObjectValues[2]" = "Item 3";
"lblDevZoneCandidateFont.title" = "これは Apple Bug Report #FB10978412 の臨時対策であり、macOS 12 からの macOS に効き、IMK 以外の候補陳列ウィンドウに作用する。Apple は macOS 11 からの macOS のために該当 Bug を修復すべきである。";
"lblDevZoneIMKCandidate.title" = "IMK 候補陳列ウィンドウで言選り用キーは現時点で利用不可、尚他故障あり。";
"lblDevZoneTitleDescription.title" = "警告:これからの新機能テストのために作ったページですから、\nここで陳列されている諸機能は予想通り動けるだと思わないでください。";
"lblUpperCaseLetterKeyBehavior.title" = "Shift+文字キーの行為をご指定ください。";
"Parser11.title" = "国音二式 (ローマ字+数字音調)";
"Parser12.title" = "イェール弁音 (ローマ字+数字音調)";
@ -78,6 +81,8 @@
"rVQ-Hx-cGi.title" = "和語";
"s7u-Fm-dVg.title" = "ページ";
"shc-Nu-UsM.title" = "ページボタンを表示";
"tglDevZoneCandidateFont.title" = "「.langIdentifier」を使って候補陳列ウィンドウのフォントを取り扱う";
"tglDevZoneIMKCandidate.title" = "IMK 候補陳列ウィンドウを起用(入力アプリは自動的に再起動)";
"TXr-FF-ehw.title" = "繁体中国語";
"ueU-Rz-a1C.title" = "入力候補陳列での (Shift+)Tab キーの輪番切替対象をご指定ください。";
"VdT-fw-7pQ.title" = "欠陥辿着モード";

View File

@ -63,6 +63,9 @@
"jQC-12-UuK.ibShadowedObjectValues[0]" = "Item 1";
"jQC-12-UuK.ibShadowedObjectValues[1]" = "Item 2";
"jQC-12-UuK.ibShadowedObjectValues[2]" = "Item 3";
"lblDevZoneCandidateFont.title" = "该方法是 Apple Bug Report #FB10978412 的保守治疗方案,用来仅针对 macOS 12 开始的系统,且仅对非 IMK 选字窗起作用。Apple 应该对 macOS 11 开始的系统修复这个 Bug。";
"lblDevZoneIMKCandidate.title" = "IMK 选字窗目前暂时无法正常使用选字键,并具其它未知故障。";
"lblDevZoneTitleDescription.title" = "警告:该页面仅作未来功能测试所用。\n在此列出的功能并非处于完全可用之状态。";
"lblUpperCaseLetterKeyBehavior.title" = "指定 Shift+字母键 的行为。";
"Parser11.title" = "国音二式+数字标调";
"Parser12.title" = "耶鲁拼音+数字标调";
@ -78,6 +81,8 @@
"rVQ-Hx-cGi.title" = "和语";
"s7u-Fm-dVg.title" = "轮替页面";
"shc-Nu-UsM.title" = "在选字窗内显示翻页按钮";
"tglDevZoneCandidateFont.title" = "使用 .langIdentifier 来管理选字窗的预设介面字型";
"tglDevZoneIMKCandidate.title" = "启用 IMK 选字窗(会自动重启输入法)";
"TXr-FF-ehw.title" = "繁体中文";
"ueU-Rz-a1C.title" = "指定 (Shift+)Tab 热键在选字窗内的轮替操作对象。";
"VdT-fw-7pQ.title" = "侦错模式";

View File

@ -63,6 +63,9 @@
"jQC-12-UuK.ibShadowedObjectValues[0]" = "Item 1";
"jQC-12-UuK.ibShadowedObjectValues[1]" = "Item 2";
"jQC-12-UuK.ibShadowedObjectValues[2]" = "Item 3";
"lblDevZoneCandidateFont.title" = "該方法是 Apple Bug Report #FB10978412 的保守治療方案,用來僅針對 macOS 12 開始的系統,且僅對非 IMK 選字窗起作用。Apple 應該對 macOS 11 開始的系統修復這個 Bug。";
"lblDevZoneIMKCandidate.title" = "IMK 選字窗目前暫時無法正常使用選字鍵,併具其它未知故障。";
"lblDevZoneTitleDescription.title" = "警告:該頁面僅作未來功能測試所用。\n在此列出的功能並非處於完全可用之狀態。";
"lblUpperCaseLetterKeyBehavior.title" = "指定 Shift+字母鍵 的行為。";
"Parser11.title" = "國音二式+數字標調";
"Parser12.title" = "耶魯拼音+數字標調";
@ -78,6 +81,8 @@
"rVQ-Hx-cGi.title" = "和語";
"s7u-Fm-dVg.title" = "輪替頁面";
"shc-Nu-UsM.title" = "在選字窗內顯示翻頁按鈕";
"tglDevZoneCandidateFont.title" = "使用 .langIdentifier 來管理選字窗的預設介面字型";
"tglDevZoneIMKCandidate.title" = "啟用 IMK 選字窗(會自動重啟輸入法)";
"TXr-FF-ehw.title" = "繁體中文";
"ueU-Rz-a1C.title" = "指定 (Shift+)Tab 熱鍵在選字窗內的輪替操作對象。";
"VdT-fw-7pQ.title" = "偵錯模式";

View File

@ -3,9 +3,9 @@
<plist version="1.0">
<dict>
<key>CFBundleShortVersionString</key>
<string>1.9.1</string>
<string>1.9.2</string>
<key>CFBundleVersion</key>
<string>1991</string>
<string>1992</string>
<key>UpdateInfoEndpoint</key>
<string>https://gitee.com/vchewing/vChewing-macOS/raw/main/Update-Info.plist</string>
<key>UpdateInfoSite</key>

View File

@ -726,7 +726,7 @@
<key>USE_HFS+_COMPRESSION</key>
<false/>
<key>VERSION</key>
<string>1.9.1</string>
<string>1.9.2</string>
</dict>
<key>TYPE</key>
<integer>0</integer>

View File

@ -40,6 +40,7 @@
5B62A35327AE89C400A19448 /* InputSourceHelper.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5B62A33127AE792F00A19448 /* InputSourceHelper.swift */; };
5B73FB5E27B2BE1300E9BF49 /* InfoPlist.strings in Resources */ = {isa = PBXBuildFile; fileRef = 5B73FB6027B2BE1300E9BF49 /* InfoPlist.strings */; };
5B782EC4280C243C007276DE /* KeyHandler_HandleCandidate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5B782EC3280C243C007276DE /* KeyHandler_HandleCandidate.swift */; };
5B78EE0D28A562B4009456C1 /* suiPrefPaneDevZone.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5B78EE0C28A562B4009456C1 /* suiPrefPaneDevZone.swift */; };
5B7BC4B027AFFBE800F66C24 /* frmPrefWindow.xib in Resources */ = {isa = PBXBuildFile; fileRef = 5B7BC4AE27AFFBE800F66C24 /* frmPrefWindow.xib */; };
5B7F225D2808501000DDD3CB /* KeyHandler_HandleInput.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5B7F225C2808501000DDD3CB /* KeyHandler_HandleInput.swift */; };
5B84579E2871AD2200C93B01 /* convdict.plist in Resources */ = {isa = PBXBuildFile; fileRef = 5B84579C2871AD2200C93B01 /* convdict.plist */; };
@ -246,6 +247,7 @@
5B73FB5427B2BD6900E9BF49 /* PhraseEditor-Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; name = "PhraseEditor-Info.plist"; path = "UserPhraseEditor/PhraseEditor-Info.plist"; sourceTree = SOURCE_ROOT; };
5B73FB5F27B2BE1300E9BF49 /* en */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = en; path = en.lproj/InfoPlist.strings; sourceTree = "<group>"; };
5B782EC3280C243C007276DE /* KeyHandler_HandleCandidate.swift */ = {isa = PBXFileReference; explicitFileType = sourcecode.swift; fileEncoding = 4; indentWidth = 2; lineEnding = 0; path = KeyHandler_HandleCandidate.swift; sourceTree = "<group>"; tabWidth = 2; usesTabs = 0; };
5B78EE0C28A562B4009456C1 /* suiPrefPaneDevZone.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = suiPrefPaneDevZone.swift; sourceTree = "<group>"; };
5B7BC4AF27AFFBE800F66C24 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.xib; name = Base; path = Base.lproj/frmPrefWindow.xib; sourceTree = "<group>"; };
5B7BC4B227AFFC0B00F66C24 /* en */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = en; path = en.lproj/frmPrefWindow.strings; sourceTree = "<group>"; };
5B7F225C2808501000DDD3CB /* KeyHandler_HandleInput.swift */ = {isa = PBXFileReference; explicitFileType = sourcecode.swift; fileEncoding = 4; indentWidth = 2; lineEnding = 0; path = KeyHandler_HandleInput.swift; sourceTree = "<group>"; tabWidth = 2; usesTabs = 0; };
@ -652,6 +654,7 @@
isa = PBXGroup;
children = (
5BA9FD0C27FEDB6B002DE248 /* ctlPrefUI.swift */,
5B78EE0C28A562B4009456C1 /* suiPrefPaneDevZone.swift */,
5BA9FD0E27FEDB6B002DE248 /* suiPrefPaneDictionary.swift */,
5BA9FD0D27FEDB6B002DE248 /* suiPrefPaneExperience.swift */,
5BA9FD0A27FEDB6B002DE248 /* suiPrefPaneGeneral.swift */,
@ -1184,6 +1187,7 @@
5B3A87BC28597CDB0090E163 /* LMSymbolNode.swift in Sources */,
5BA9FD4327FEF3C8002DE248 /* Preferences.swift in Sources */,
5BA9FD4427FEF3C8002DE248 /* SegmentedControlStyleViewController.swift in Sources */,
5B78EE0D28A562B4009456C1 /* suiPrefPaneDevZone.swift in Sources */,
D47F7DCE278BFB57002F9DD7 /* ctlPrefWindow.swift in Sources */,
5BD0113D2818543900609769 /* KeyHandler_Core.swift in Sources */,
5B2170E4289FACAD00BE7304 /* 2_Walker.swift in Sources */,
@ -1413,7 +1417,7 @@
CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
CODE_SIGN_STYLE = Automatic;
CURRENT_PROJECT_VERSION = 1991;
CURRENT_PROJECT_VERSION = 1992;
GCC_C_LANGUAGE_STANDARD = gnu11;
GCC_DYNAMIC_NO_PIC = NO;
GCC_PREPROCESSOR_DEFINITIONS = (
@ -1423,7 +1427,7 @@
GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
GENERATE_INFOPLIST_FILE = YES;
MARKETING_VERSION = 1.9.1;
MARKETING_VERSION = 1.9.2;
MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE;
MTL_FAST_MATH = YES;
PRODUCT_BUNDLE_IDENTIFIER = org.atelierInmu.vChewingTests;
@ -1452,13 +1456,13 @@
CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
CODE_SIGN_STYLE = Automatic;
CURRENT_PROJECT_VERSION = 1991;
CURRENT_PROJECT_VERSION = 1992;
ENABLE_NS_ASSERTIONS = NO;
GCC_C_LANGUAGE_STANDARD = gnu11;
GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
GENERATE_INFOPLIST_FILE = YES;
MARKETING_VERSION = 1.9.1;
MARKETING_VERSION = 1.9.2;
MTL_ENABLE_DEBUG_INFO = NO;
MTL_FAST_MATH = YES;
PRODUCT_BUNDLE_IDENTIFIER = org.atelierInmu.vChewingTests;
@ -1489,7 +1493,7 @@
CODE_SIGN_IDENTITY = "-";
CODE_SIGN_STYLE = Automatic;
COMBINE_HIDPI_IMAGES = YES;
CURRENT_PROJECT_VERSION = 1991;
CURRENT_PROJECT_VERSION = 1992;
DEAD_CODE_STRIPPING = YES;
GCC_C_LANGUAGE_STANDARD = gnu11;
GCC_DYNAMIC_NO_PIC = NO;
@ -1510,7 +1514,7 @@
"$(inherited)",
"@executable_path/../Frameworks",
);
MARKETING_VERSION = 1.9.1;
MARKETING_VERSION = 1.9.2;
MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE;
MTL_FAST_MATH = YES;
PRODUCT_BUNDLE_IDENTIFIER = org.atelierInmu.vChewing.vChewingPhraseEditor;
@ -1539,7 +1543,7 @@
CODE_SIGN_IDENTITY = "-";
CODE_SIGN_STYLE = Automatic;
COMBINE_HIDPI_IMAGES = YES;
CURRENT_PROJECT_VERSION = 1991;
CURRENT_PROJECT_VERSION = 1992;
DEAD_CODE_STRIPPING = YES;
ENABLE_NS_ASSERTIONS = NO;
GCC_C_LANGUAGE_STANDARD = gnu11;
@ -1556,7 +1560,7 @@
"$(inherited)",
"@executable_path/../Frameworks",
);
MARKETING_VERSION = 1.9.1;
MARKETING_VERSION = 1.9.2;
MTL_ENABLE_DEBUG_INFO = NO;
MTL_FAST_MATH = YES;
PRODUCT_BUNDLE_IDENTIFIER = org.atelierInmu.vChewing.vChewingPhraseEditor;
@ -1670,7 +1674,7 @@
CODE_SIGN_IDENTITY = "-";
CODE_SIGN_STYLE = Automatic;
COMBINE_HIDPI_IMAGES = YES;
CURRENT_PROJECT_VERSION = 1991;
CURRENT_PROJECT_VERSION = 1992;
DEAD_CODE_STRIPPING = YES;
DEVELOPMENT_ASSET_PATHS = "";
DEVELOPMENT_TEAM = "";
@ -1698,7 +1702,7 @@
"$(inherited)",
"@executable_path/../Frameworks",
);
MARKETING_VERSION = 1.9.1;
MARKETING_VERSION = 1.9.2;
ONLY_ACTIVE_ARCH = YES;
PRODUCT_BUNDLE_IDENTIFIER = org.atelierInmu.inputmethod.vChewing;
PRODUCT_NAME = "$(TARGET_NAME)";
@ -1725,7 +1729,7 @@
CODE_SIGN_IDENTITY = "-";
CODE_SIGN_STYLE = Automatic;
COMBINE_HIDPI_IMAGES = YES;
CURRENT_PROJECT_VERSION = 1991;
CURRENT_PROJECT_VERSION = 1992;
DEAD_CODE_STRIPPING = YES;
DEVELOPMENT_ASSET_PATHS = "";
DEVELOPMENT_TEAM = "";
@ -1747,7 +1751,7 @@
"$(inherited)",
"@executable_path/../Frameworks",
);
MARKETING_VERSION = 1.9.1;
MARKETING_VERSION = 1.9.2;
PRODUCT_BUNDLE_IDENTIFIER = org.atelierInmu.inputmethod.vChewing;
PRODUCT_NAME = "$(TARGET_NAME)";
PROVISIONING_PROFILE_SPECIFIER = "";
@ -1769,7 +1773,7 @@
CODE_SIGN_IDENTITY = "-";
CODE_SIGN_STYLE = Automatic;
COMBINE_HIDPI_IMAGES = YES;
CURRENT_PROJECT_VERSION = 1991;
CURRENT_PROJECT_VERSION = 1992;
DEAD_CODE_STRIPPING = YES;
DEVELOPMENT_TEAM = "";
GCC_C_LANGUAGE_STANDARD = gnu99;
@ -1789,7 +1793,7 @@
"$(inherited)",
"@executable_path/../Frameworks",
);
MARKETING_VERSION = 1.9.1;
MARKETING_VERSION = 1.9.2;
ONLY_ACTIVE_ARCH = YES;
PRODUCT_BUNDLE_IDENTIFIER = "org.atelierInmu.vChewing.${PRODUCT_NAME:rfc1034identifier}";
PRODUCT_NAME = "$(TARGET_NAME)";
@ -1811,7 +1815,7 @@
CODE_SIGN_IDENTITY = "-";
CODE_SIGN_STYLE = Automatic;
COMBINE_HIDPI_IMAGES = YES;
CURRENT_PROJECT_VERSION = 1991;
CURRENT_PROJECT_VERSION = 1992;
DEAD_CODE_STRIPPING = YES;
DEVELOPMENT_TEAM = "";
GCC_C_LANGUAGE_STANDARD = gnu99;
@ -1825,7 +1829,7 @@
"$(inherited)",
"@executable_path/../Frameworks",
);
MARKETING_VERSION = 1.9.1;
MARKETING_VERSION = 1.9.2;
PRODUCT_BUNDLE_IDENTIFIER = "org.atelierInmu.vChewing.${PRODUCT_NAME:rfc1034identifier}";
PRODUCT_NAME = "$(TARGET_NAME)";
PROVISIONING_PROFILE_SPECIFIER = "";