ctlIME // Add "lineHeightRect" and simplify display process.
This commit is contained in:
parent
ba0e47ad61
commit
d52678c959
|
@ -13,19 +13,31 @@ import Cocoa
|
||||||
// MARK: - Tooltip Display and Candidate Display Methods
|
// MARK: - Tooltip Display and Candidate Display Methods
|
||||||
|
|
||||||
extension ctlInputMethod {
|
extension ctlInputMethod {
|
||||||
func show(tooltip: String, displayedText: String, u16Cursor: Int) {
|
func lineHeightRect(zeroCursor: Bool = false) -> NSRect {
|
||||||
guard let client = client() else { return }
|
var lineHeightRect = NSRect.seniorTheBeast
|
||||||
var lineHeightRect = NSRect(x: 0.0, y: 0.0, width: 16.0, height: 16.0)
|
guard let client = client() else {
|
||||||
var cursor = u16Cursor
|
return lineHeightRect
|
||||||
if cursor == displayedText.utf16.count, cursor != 0 {
|
|
||||||
cursor -= 1
|
|
||||||
}
|
}
|
||||||
while lineHeightRect.origin.x == 0, lineHeightRect.origin.y == 0, cursor >= 0 {
|
var u16Cursor: Int = {
|
||||||
|
// iMessage 在 cursor == 0 時的計算會有一些偏差,所以例外處理。
|
||||||
|
if clientBundleIdentifier == "com.apple.MobileSMS" { return state.data.u16Cursor }
|
||||||
|
if state.data.marker >= state.data.cursor { return state.data.u16Cursor }
|
||||||
|
return state.data.u16Marker // 這樣可以讓工具提示視窗始終盡量往書寫方向的後方顯示。
|
||||||
|
}()
|
||||||
|
u16Cursor = max(min(state.data.displayedTextConverted.utf16.count, u16Cursor), 0)
|
||||||
|
if zeroCursor { u16Cursor = 0 }
|
||||||
|
while lineHeightRect.origin.x == 0, lineHeightRect.origin.y == 0, u16Cursor >= 0 {
|
||||||
client.attributes(
|
client.attributes(
|
||||||
forCharacterIndex: cursor, lineHeightRectangle: &lineHeightRect
|
forCharacterIndex: u16Cursor, lineHeightRectangle: &lineHeightRect
|
||||||
)
|
)
|
||||||
cursor -= 1
|
u16Cursor -= 1
|
||||||
}
|
}
|
||||||
|
return lineHeightRect
|
||||||
|
}
|
||||||
|
|
||||||
|
func show(tooltip: String) {
|
||||||
|
guard client() != nil else { return }
|
||||||
|
let lineHeightRect = lineHeightRect()
|
||||||
var finalOrigin: NSPoint = lineHeightRect.origin
|
var finalOrigin: NSPoint = lineHeightRect.origin
|
||||||
let delta: CGFloat = lineHeightRect.size.height + 4.0 // bottomOutOfScreenAdjustmentHeight
|
let delta: CGFloat = lineHeightRect.size.height + 4.0 // bottomOutOfScreenAdjustmentHeight
|
||||||
if isVerticalTyping {
|
if isVerticalTyping {
|
||||||
|
@ -120,34 +132,17 @@ extension ctlInputMethod {
|
||||||
|
|
||||||
ctlInputMethod.ctlCandidateCurrent.visible = true
|
ctlInputMethod.ctlCandidateCurrent.visible = true
|
||||||
|
|
||||||
var lineHeightRect = NSRect(x: 0.0, y: 0.0, width: 16.0, height: 16.0)
|
|
||||||
var cursor = 0
|
|
||||||
|
|
||||||
if [.ofCandidates, .ofSymbolTable].contains(state.type) {
|
|
||||||
cursor = state.data.u16Cursor
|
|
||||||
if cursor == state.displayedText.utf16.count, cursor != 0 {
|
|
||||||
cursor -= 1
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
while lineHeightRect.origin.x == 0, lineHeightRect.origin.y == 0, cursor >= 0 {
|
|
||||||
client.attributes(
|
|
||||||
forCharacterIndex: cursor, lineHeightRectangle: &lineHeightRect
|
|
||||||
)
|
|
||||||
cursor -= 1
|
|
||||||
}
|
|
||||||
|
|
||||||
if isVerticalTyping {
|
if isVerticalTyping {
|
||||||
ctlInputMethod.ctlCandidateCurrent.set(
|
ctlInputMethod.ctlCandidateCurrent.set(
|
||||||
windowTopLeftPoint: NSPoint(
|
windowTopLeftPoint: NSPoint(
|
||||||
x: lineHeightRect.origin.x + lineHeightRect.size.width + 4.0, y: lineHeightRect.origin.y - 4.0
|
x: lineHeightRect().origin.x + lineHeightRect().size.width + 4.0, y: lineHeightRect().origin.y - 4.0
|
||||||
),
|
),
|
||||||
bottomOutOfScreenAdjustmentHeight: lineHeightRect.size.height + 4.0
|
bottomOutOfScreenAdjustmentHeight: lineHeightRect().size.height + 4.0
|
||||||
)
|
)
|
||||||
} else {
|
} else {
|
||||||
ctlInputMethod.ctlCandidateCurrent.set(
|
ctlInputMethod.ctlCandidateCurrent.set(
|
||||||
windowTopLeftPoint: NSPoint(x: lineHeightRect.origin.x, y: lineHeightRect.origin.y - 4.0),
|
windowTopLeftPoint: NSPoint(x: lineHeightRect().origin.x, y: lineHeightRect().origin.y - 4.0),
|
||||||
bottomOutOfScreenAdjustmentHeight: lineHeightRect.size.height + 4.0
|
bottomOutOfScreenAdjustmentHeight: lineHeightRect().size.height + 4.0
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -65,10 +65,8 @@ extension ctlInputMethod {
|
||||||
if !textToCommit.isEmpty { commit(text: textToCommit) }
|
if !textToCommit.isEmpty { commit(text: textToCommit) }
|
||||||
setInlineDisplayWithCursor()
|
setInlineDisplayWithCursor()
|
||||||
if !state.tooltip.isEmpty {
|
if !state.tooltip.isEmpty {
|
||||||
show(
|
show(tooltip: state.tooltip)
|
||||||
tooltip: state.tooltip, displayedText: state.displayedText,
|
}
|
||||||
u16Cursor: state.data.u16Cursor
|
|
||||||
)
|
|
||||||
}
|
}
|
||||||
case .ofMarking:
|
case .ofMarking:
|
||||||
ctlInputMethod.ctlCandidateCurrent.visible = false
|
ctlInputMethod.ctlCandidateCurrent.visible = false
|
||||||
|
@ -76,14 +74,7 @@ extension ctlInputMethod {
|
||||||
if state.tooltip.isEmpty {
|
if state.tooltip.isEmpty {
|
||||||
ctlInputMethod.tooltipInstance.hide()
|
ctlInputMethod.tooltipInstance.hide()
|
||||||
} else {
|
} else {
|
||||||
let cursorReference: Int = {
|
show(tooltip: state.tooltip)
|
||||||
if state.data.marker >= state.data.cursor { return state.data.u16Cursor }
|
|
||||||
return state.data.u16Marker // 這樣可以讓工具提示視窗始終盡量往書寫方向的後方顯示。
|
|
||||||
}()
|
|
||||||
show(
|
|
||||||
tooltip: state.tooltip, displayedText: state.displayedText,
|
|
||||||
u16Cursor: cursorReference
|
|
||||||
)
|
|
||||||
}
|
}
|
||||||
case .ofCandidates, .ofAssociates, .ofSymbolTable:
|
case .ofCandidates, .ofAssociates, .ofSymbolTable:
|
||||||
ctlInputMethod.tooltipInstance.hide()
|
ctlInputMethod.tooltipInstance.hide()
|
||||||
|
|
Loading…
Reference in New Issue