Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[#371] Add functionality for new keyboard expanded layout #373

Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 9 additions & 0 deletions Keyboards/InterfaceConstants.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
//
// Scribe
//

struct SpecialKeys {

static let indent = "indent"
static let capsLock = "capslock"
}
13 changes: 10 additions & 3 deletions Keyboards/KeyboardsBase/InterfaceVariables.swift
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ var keyboard = [[String]]()
var usingExpandedKeyboard = false
var allKeys = [String]()
let specialKeys = [
"shift", "delete", "ABC", "АБВ", "123", "#+=", "selectKeyboard", "space", "return", ".?123", "hideKeyboard",
SpecialKeys.indent, SpecialKeys.capsLock, "shift", "delete", "ABC", "АБВ", "123", "#+=", "selectKeyboard", "space", "return", ".?123", "hideKeyboard",
]
var allNonSpecialKeys = [String]()
var keyboardHeight: CGFloat!
Expand Down Expand Up @@ -51,11 +51,17 @@ enum KeyboardState {
/// What the keyboard state is in regards to the shift key.
/// - normal: not capitalized
/// - shift: capitalized
/// - caps: caps-lock
enum ShiftButtonState {
case normal
case shift
case caps
}

/// What the keyboard state is in regards to the all caps key.
/// - normal: not capitalized
/// - locked: caps-lock
enum CapsLockButtonState {
case normal
case locked
}

/// States of the keyboard corresponding to which commands the user is executing.
Expand Down Expand Up @@ -89,6 +95,7 @@ enum ConjViewShiftButtonsState {
// Baseline state variables.
var keyboardState: KeyboardState = .letters
var shiftButtonState: ShiftButtonState = .normal
var capsLockButtonState: CapsLockButtonState = .normal
var commandState: CommandState = .idle
var autoActionState: AutoActionState = .suggest
var conjViewShiftButtonsState: ConjViewShiftButtonsState = .bothInactive
Expand Down
4 changes: 2 additions & 2 deletions Keyboards/KeyboardsBase/KeyAnimation.swift
Original file line number Diff line number Diff line change
Expand Up @@ -319,7 +319,7 @@ func setPhoneKeyPopCharSize(char: String) {
keyPopChar.font = .systemFont(ofSize: letterKeyWidth / 1.15)
keyHoldPopChar.font = .systemFont(ofSize: letterKeyWidth / 1.15)
}
} else if shiftButtonState == .shift || shiftButtonState == .caps {
} else if shiftButtonState == .shift || capsLockButtonState == .locked {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Very intuitive :)

if isLandscapeView {
keyPopChar.font = .systemFont(ofSize: letterKeyWidth / 2.15)
keyHoldPopChar.font = .systemFont(ofSize: letterKeyWidth / 2.15)
Expand Down Expand Up @@ -351,7 +351,7 @@ func setPadKeyPopCharSize(char: String) {
keyPopChar.font = .systemFont(ofSize: letterKeyWidth / 2.5)
keyHoldPopChar.font = .systemFont(ofSize: letterKeyWidth / 2.5)
}
} else if keyboardState == .letters, shiftButtonState == .shift || shiftButtonState == .caps {
} else if keyboardState == .letters, shiftButtonState == .shift || capsLockButtonState == .locked {
if isLandscapeView {
keyPopChar.font = .systemFont(ofSize: letterKeyWidth / 2.5)
keyHoldPopChar.font = .systemFont(ofSize: letterKeyWidth / 2.5)
Expand Down
61 changes: 37 additions & 24 deletions Keyboards/KeyboardsBase/KeyboardKeys.swift
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ class KeyboardKey: UIButton {
} else {
capsKey = key
}
let keyToDisplay = shiftButtonState == .normal ? key : capsKey
let keyToDisplay = shiftButtonState == .shift || capsLockButtonState == .locked ? capsKey : key
setTitleColor(keyCharColor, for: .normal)
layer.setValue(key, forKey: "original")
layer.setValue(keyToDisplay, forKey: "keyToDisplay")
Expand Down Expand Up @@ -256,22 +256,14 @@ class KeyboardKey: UIButton {
if key == "ABC" || key == "АБВ" {
layer.setValue(true, forKey: "isSpecial")
widthAnchor.constraint(equalToConstant: numSymKeyWidth * 1).isActive = true
} else if key == "delete"
|| key == "#+="
|| key == "shift"
|| key == "selectKeyboard"
{
} else if ["delete", "#+=", "shift", "selectKeyboard", SpecialKeys.indent, SpecialKeys.capsLock].contains(key) {
layer.setValue(true, forKey: "isSpecial")
widthAnchor.constraint(equalToConstant: numSymKeyWidth * 1).isActive = true
} else if key == "123"
|| key == ".?123"
|| key == "return"
|| key == "hideKeyboard"
{
} else if ["123", ".?123", "return", "hideKeyboard"].contains(key) {
Copy link
Member

@andrewtavis andrewtavis Oct 30, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Appreciate you fixing these formatting/logic errors! 🙏

if key == "return"
&& (controllerLanguage == "Portuguese" || controllerLanguage == "Italian" || commandState == .translate)
&& row == 1
&& DeviceType.isPad
&& (controllerLanguage == "Portuguese" || controllerLanguage == "Italian" || commandState == .translate)
&& row == 1
&& DeviceType.isPad
{
layer.setValue(true, forKey: "isSpecial")
widthAnchor.constraint(equalToConstant: numSymKeyWidth * 1.5).isActive = true
Expand All @@ -291,25 +283,46 @@ class KeyboardKey: UIButton {
} else if DeviceType.isPad {
adjustPadKeyWidth()
}
}

/// Adjusts the style of the button based on different states
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Minor nit that I'm noting here is that we'd like this to be a complete sentence with a period :) I can get it though!

func adjustButtonStyle() {
guard let isSpecial = layer.value(forKey: "isSpecial") as? Bool else { return }

if key == "shift" {
// Switch the shift key icon given its state.
switch key {
case SpecialKeys.indent:
backgroundColor = specialKeyColor

case SpecialKeys.capsLock:
switch capsLockButtonState {

case .normal:
backgroundColor = specialKeyColor
styleIconBtn(btn: self, color: UIColor.label, iconName: "capslock")

case .locked:
backgroundColor = keyPressedColor
styleIconBtn(btn: self, color: UIColor.label, iconName: "capslock.fill")
}

case "shift":
if shiftButtonState == .shift {
backgroundColor = keyPressedColor
styleIconBtn(btn: self, color: UIColor.label, iconName: "shift.fill")
} else if shiftButtonState == .caps {
backgroundColor = keyPressedColor
styleIconBtn(btn: self, color: UIColor.label, iconName: "capslock.fill")
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Losing this line is disabling an indication that we're in caps lock on iPhones :)

} else {
backgroundColor = specialKeyColor
}
} else if key == "return" && [.translate, .conjugate, .plural].contains(commandState) {
// Color the return key depending on if it's being used as enter for commands.
backgroundColor = commandKeyColor
} else if isSpecial {
backgroundColor = specialKeyColor

case "return":
if [.translate, .conjugate, .plural].contains(commandState) {
// Color the return key depending on if it's being used as enter for commands.
backgroundColor = commandKeyColor
}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We need the else back here for one bug I'm about to mention such that we get backgroundColor = specialKeyColor.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There's a default case which should handle the elsebut I'll do a review of my code to see if it's not missing some cases.


default:
if isSpecial {
backgroundColor = specialKeyColor
}
}
}
}
Expand Down
2 changes: 2 additions & 0 deletions Keyboards/KeyboardsBase/KeyboardStyling.swift
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,9 @@ var keysThatAreSlightlyLarger = [
"chevron.right",
"shift",
"shift.fill",
"capslock",
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Again the dedication here is amazing. Looking into and finding keysThatAreSlightlyLarger is great, but also has me worried about the state of some of the code that we're using so many random variables everywhere.

A basic ask would be if you had ideas for how we can improve the code base, it'd be great if you could open some issues. Anything that you've seen that might be some solid refactoring would be very welcome!

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good point 🤔 I'll do a quick sweep over the codebase and open a few issues for code quality ^^

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks so much, @damien-rivet! Always looking for some good first issues for new folks to work on 😊

"capslock.fill",
"arrow.forward.to.line",
"arrowtriangle.right.fill",
]

Expand Down
56 changes: 46 additions & 10 deletions Keyboards/KeyboardsBase/KeyboardViewController.swift
Original file line number Diff line number Diff line change
Expand Up @@ -406,7 +406,9 @@ class KeyboardViewController: UIInputViewController {
var i = 0
if completionOptions.count <= 3 {
while i < completionOptions.count {
if shiftButtonState == .caps {
if shiftButtonState == .shift {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Interesting, we were missing shift?? Great catch :)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yup, suggestions were not handled properly for capitalised first-letter but it will be history after the merge.

completionWords[i] = completionOptions[i].capitalize()
} else if capsLockButtonState == .locked {
completionWords[i] = completionOptions[i].uppercased()
} else if currentPrefix.isCapitalized {
if completionOptions[i].isUppercase {
Expand All @@ -421,7 +423,9 @@ class KeyboardViewController: UIInputViewController {
}
} else {
while i < 3 {
if shiftButtonState == .caps {
if shiftButtonState == .shift {
completionWords[i] = completionOptions[i].capitalize()
} else if capsLockButtonState == .locked {
completionWords[i] = completionOptions[i].uppercased()
} else if currentPrefix.isCapitalized {
if completionOptions[i].isUppercase {
Expand Down Expand Up @@ -472,7 +476,7 @@ class KeyboardViewController: UIInputViewController {
}
if shiftButtonState == .shift {
completionWords.append(suggestion.capitalize())
} else if shiftButtonState == .caps {
} else if capsLockButtonState == .locked {
completionWords.append(suggestion.uppercased())
} else {
completionWords.append(suggestion)
Expand All @@ -492,7 +496,7 @@ class KeyboardViewController: UIInputViewController {
while i < 3 {
if shiftButtonState == .shift {
completionWords.append(baseAutosuggestions[i].capitalize())
} else if shiftButtonState == .caps {
} else if capsLockButtonState == .locked {
completionWords.append(baseAutosuggestions[i].uppercased())
} else {
completionWords.append(baseAutosuggestions[i])
Expand Down Expand Up @@ -547,7 +551,7 @@ class KeyboardViewController: UIInputViewController {
while i < 3 {
if shiftButtonState == .shift {
completionWords.append(suggestionsLowerCasePrefix[i].capitalize())
} else if shiftButtonState == .caps {
} else if capsLockButtonState == .locked {
completionWords.append(suggestionsLowerCasePrefix[i].uppercased())
} else {
let nounGenderQuery = "SELECT * FROM nouns WHERE noun = ?"
Expand All @@ -574,7 +578,7 @@ class KeyboardViewController: UIInputViewController {
while i < 3 {
if shiftButtonState == .shift {
completionWords.append(suggestionsCapitalizedPrefix[i].capitalize())
} else if shiftButtonState == .caps {
} else if capsLockButtonState == .locked {
completionWords.append(suggestionsCapitalizedPrefix[i].uppercased())
} else {
completionWords.append(suggestionsCapitalizedPrefix[i])
Expand Down Expand Up @@ -1875,6 +1879,14 @@ class KeyboardViewController: UIInputViewController {
styleIconBtn(btn: btn, color: keyCharColor, iconName: "keyboard.chevron.compact.down")
}

if key == SpecialKeys.indent {
styleIconBtn(btn: btn, color: keyCharColor, iconName: "arrow.forward.to.line")
}

if key == SpecialKeys.capsLock {
styleIconBtn(btn: btn, color: keyCharColor, iconName: "capslock")
}

if key == "shift" {
styleIconBtn(btn: btn, color: keyCharColor, iconName: "shift")
}
Expand Down Expand Up @@ -1925,6 +1937,10 @@ class KeyboardViewController: UIInputViewController {

// Set the width of the key given device and the given key.
btn.adjustKeyWidth()

// Update the button style
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Noting the comment for myself.

btn.adjustButtonStyle()

if key == "return" && proxy.keyboardType == .webSearch && ![.translate, .conjugate, .plural].contains(commandState) {
// Override background color from adjustKeyWidth for "search" blue for web searches.
styleIconBtn(btn: btn, color: .white.withAlphaComponent(0.9), iconName: "arrow.turn.down.left")
Expand Down Expand Up @@ -2482,7 +2498,14 @@ class KeyboardViewController: UIInputViewController {
}

case "shift":
shiftButtonState = shiftButtonState == .normal ? .shift : .normal
if capsLockButtonState == .locked {
// Return capitalization to default
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nice as well as we now have both states to account for :)

capsLockButtonState = .normal
shiftButtonState = .normal
} else {
shiftButtonState = shiftButtonState == .normal ? .shift : .normal
}

loadKeys()
capsLockPossible = true

Expand All @@ -2496,6 +2519,12 @@ class KeyboardViewController: UIInputViewController {
changeKeyboardToLetterKeys()
autoCapAtStartOfProxy()

case SpecialKeys.capsLock:
switchToFullCaps()

case SpecialKeys.indent:
proxy.insertText("\t")

case "selectKeyboard":
advanceToNextInputMode()

Expand Down Expand Up @@ -2612,9 +2641,7 @@ class KeyboardViewController: UIInputViewController {

// Caps lock given two taps of shift.
if touch.tapCount == 2 && originalKey == "shift" && capsLockPossible {
shiftButtonState = .caps
loadKeys()
conditionallySetAutoActionBtns()
switchToFullCaps()
}

// To make sure that the user can still use the double space period shortcut after numbers and symbols.
Expand Down Expand Up @@ -2657,6 +2684,15 @@ class KeyboardViewController: UIInputViewController {
}
}

private func switchToFullCaps() {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Another thing that we've been dealing with is that not enough of the code base is split into functions. I do some rounds from time to time and break some things out, but if you came across some parts where we can extract some code then by all means let me know or open an issue!

// Return SHIFT button to normal state as the ALLCAPS button will be enabled
shiftButtonState = .normal
capsLockButtonState = capsLockButtonState == .normal ? .locked : .normal

loadKeys()
conditionallySetAutoActionBtns()
}

/// Defines the criteria under which delete is long pressed.
///
/// - Parameters
Expand Down
8 changes: 4 additions & 4 deletions Keyboards/LanguageKeyboards/Danish/DAInterfaceVariables.swift
Original file line number Diff line number Diff line change
Expand Up @@ -55,16 +55,16 @@ public enum DanishKeyboardConstants {
// Expanded iPad keyboard layouts for wider devices.
static let letterKeysPadExpanded = [
["$", "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", "+", "'", "delete"],
["indent", "q", "w", "e", "r", "t", "y", "u", "i", "o", "p", "å", "@", "*"],
["uppercase", "a", "s", "d", "f", "g", "h", "j", "k", "l", "æ", "ø", "'", "return"],
[SpecialKeys.indent, "q", "w", "e", "r", "t", "y", "u", "i", "o", "p", "å", "@", "*"],
[SpecialKeys.capsLock, "a", "s", "d", "f", "g", "h", "j", "k", "l", "æ", "ø", "'", "return"],
["shift", "<", "z", "x", "c", "v", "b", "n", "m", ",", ".", "-", "shift"],
["selectKeyboard", ".?123", "space", ".?123", "hideKeyboard"], // "microphone", "scribble"
]

static let symbolKeysPadExpanded = [
["`", "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", "<", ">", "delete"],
["indent", "[", "]", "{", "}", "#", "%", "^", "*", "+", "=", "\"", "|"],
["uppercase", "-", "/", ":", ";", "(", ")", "$", "&", "@", "£", "¥", "~", "return"], // "undo"
[SpecialKeys.indent, "[", "]", "{", "}", "#", "%", "^", "*", "+", "=", "\"", "|"],
[SpecialKeys.capsLock, "-", "/", ":", ";", "(", ")", "$", "&", "@", "£", "¥", "~", "return"], // "undo"
["shift", "...", ".", ",", "?", "!", "'", "\"", "_", "€"], // "redo"
["selectKeyboard", "ABC", "space", "ABC", "hideKeyboard"], // "microphone", "scribble"
]
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -55,16 +55,16 @@ public enum EnglishKeyboardConstants {
// Expanded iPad keyboard layouts for wider devices.
static let letterKeysPadExpanded = [
["`", "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", "-", "=", "delete"],
["indent", "q", "w", "e", "r", "t", "y", "u", "i", "o", "p", "[", "]", "\\"],
["uppercase", "a", "s", "d", "f", "g", "h", "j", "k", "l", ";", "'", "return"],
[SpecialKeys.indent, "q", "w", "e", "r", "t", "y", "u", "i", "o", "p", "[", "]", "\\"],
[SpecialKeys.capsLock, "a", "s", "d", "f", "g", "h", "j", "k", "l", ";", "'", "return"],
["shift", "z", "x", "c", "v", "b", "n", "m", ",", ".", "/", "shift"],
["selectKeyboard", ".?123", "space", ".?123", "hideKeyboard"], // "microphone", "scribble"
]

static let symbolKeysPadExpanded = [
["`", "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", "<", ">", "delete"],
["indent", "[", "]", "{", "}", "#", "%", "^", "*", "+", "=", "\"", "~"],
["uppercase", "-", "/", ":", ";", "(", ")", "$", "&", "@", "£", "¥", "return"], // "undo"
[SpecialKeys.indent, "[", "]", "{", "}", "#", "%", "^", "*", "+", "=", "\"", "~"],
[SpecialKeys.capsLock, "-", "/", ":", ";", "(", ")", "$", "&", "@", "£", "¥", "return"], // "undo"
["shift", "...", ".", ",", "?", "!", "'", "\"", "_", "€"], // "redo"
["selectKeyboard", "ABC", "space", "ABC", "hideKeyboard"], // "microphone", "scribble"
]
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -55,16 +55,16 @@ public enum FrenchKeyboardConstants {
// Expanded iPad keyboard layouts for wider devices.
static let letterKeysPadExpanded = [
["@", "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", "°", "–", "delete"],
["indent", "a", "z", "e", "r", "t", "y", "u", "i", "o", "p", "^", "$", "*"],
["uppercase", "q", "s", "d", "f", "g", "h", "j", "k", "l", "m", "€", "%", "return"],
[SpecialKeys.indent, "a", "z", "e", "r", "t", "y", "u", "i", "o", "p", "^", "$", "*"],
[SpecialKeys.capsLock, "q", "s", "d", "f", "g", "h", "j", "k", "l", "m", "€", "%", "return"],
["shift", "/", "w", "x", "c", "v", "b", "n", ",", ".", "<", ">", "shift"],
["selectKeyboard", ".?123", "space", ".?123", "hideKeyboard"], // "microphone", "scribble"
]

static let symbolKeysPadExpanded = [
["`", "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", "<", ">", "delete"],
["indent", "[", "]", "{", "}", "#", "%", "^", "*", "+", "=", "\"", "|", "§"],
["uppercase", "-", "/", ":", ";", "(", ")", "$", "&", "@", "£", "¥", "~", "return"], // "undo"
[SpecialKeys.indent, "[", "]", "{", "}", "#", "%", "^", "*", "+", "=", "\"", "|", "§"],
[SpecialKeys.capsLock, "-", "/", ":", ";", "(", ")", "$", "&", "@", "£", "¥", "~", "return"], // "undo"
["shift", "...", ".", ",", "?", "!", "'", "\"", "_", "€"], // "redo"
["selectKeyboard", "ABC", "space", "ABC", "hideKeyboard"], // "microphone", "scribble"
]
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -53,16 +53,16 @@ public enum FrenchQWERTYKeyboardConstants {
// Expanded iPad keyboard layouts for wider devices.
static let letterKeysPadExpanded = [
["/", "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", "-", "=", "delete"],
["indent", "q", "w", "e", "r", "t", "y", "u", "i", "o", "p", "^", "ç", ":"],
["uppercase", "a", "s", "d", "f", "g", "h", "j", "k", "l", ";", "è", "à", "return"],
[SpecialKeys.indent, "q", "w", "e", "r", "t", "y", "u", "i", "o", "p", "^", "ç", ":"],
[SpecialKeys.capsLock, "a", "s", "d", "f", "g", "h", "j", "k", "l", ";", "è", "à", "return"],
["shift", "ù", "z", "x", "c", "v", "b", "n", "m", ",", ".", "é", "shift"],
["selectKeyboard", ".?123", "space", ".?123", "hideKeyboard"], // "microphone", "scribble"
]

static let symbolKeysPadExpanded = [
["`", "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", "<", ">", "delete"],
["indent", "[", "]", "{", "}", "#", "%", "^", "*", "+", "=", "\"", "|", "~"],
["uppercase", "-", "/", ":", ";", "(", ")", "$", "&", "@", "£", "¥", "~", "return"], // "undo"
[SpecialKeys.indent, "[", "]", "{", "}", "#", "%", "^", "*", "+", "=", "\"", "|", "~"],
[SpecialKeys.capsLock, "-", "/", ":", ";", "(", ")", "$", "&", "@", "£", "¥", "~", "return"], // "undo"
["shift", "...", ".", ",", "?", "!", "'", "\"", "_", "€"], // "redo"
["selectKeyboard", "ABC", "space", "ABC", "hideKeyboard"], // "microphone", "scribble"
]
Expand Down
Loading