//Initialize UI Keyboard from VirtualKeyboard private VBox InitVirtualKeyboard(VirtualKeyBoard pVirtualKeyboard) { List <VirtualKey> currentKeyboardRow; VirtualKey currentKey; //Virtual Key KeyboardPadKey keyboardPadKey; //UI GTK Key //Init Lists List <HBox> hboxKeyBoard = new List <HBox>(); List <HBox> hboxNumPad = new List <HBox>(); //Init VBoxs to strore Rows _vboxKeyboardRows = new VBox(true, 0); _vboxNumPadRows = new VBox(true, 0); //loop rows for (int i = 0; i < pVirtualKeyboard.KeyBoard.Count; i++) { //Get current VirtualKeyboard Row to Work currentKeyboardRow = pVirtualKeyboard.KeyBoard[i]; //add new Hbox to hboxKeyBoard/hboxNumPad rows List hboxKeyBoard.Add(new HBox(false, 0)); hboxNumPad.Add(new HBox(false, 0)); //loop columns in a row for (int j = 0; j < currentKeyboardRow.Count; j++) { //Debug //_log.Debug(string.Format("InitVirtualKeyboard(): tmpKey{0}:{1}:{2}", i, j, currentKey.L1.Glyph)); currentKey = currentKeyboardRow[j]; //Create UI Key keyboardPadKey = new KeyboardPadKey(currentKey); keyboardPadKey.Clicked += keyboardPadKey_Clicked; //Assign its UI reference to VirtualKey, usefull to have access to UI in VirtualKeyboard.VirtualKey currentKey.UIKey = keyboardPadKey; //If is a IsNumPad L1 key add to IsNumPad if (currentKey.L1.IsNumPad) { hboxNumPad[i].PackStart(keyboardPadKey, false, false, 0); } //Else Add to KeyBoard else { hboxKeyBoard[i].PackStart(keyboardPadKey, false, false, 0); }; } //In the end add row to Vbox _vboxKeyboardRows.PackStart(hboxKeyBoard[i]); _vboxNumPadRows.PackStart(hboxNumPad[i]); } //Pack KeyBoard and NumberPad into hboxResultReyboard HBox hboxResultReyboard = new HBox(false, 0); hboxResultReyboard.Spacing = _spacing; hboxResultReyboard.PackStart(_vboxKeyboardRows, false, false, 0); hboxResultReyboard.PackStart(_vboxNumPadRows, false, false, 0); //Init _textEntry Pango.FontDescription fontDescriptiontextEntry = Pango.FontDescription.FromString(_fontKeyboardPadTextEntry); _textEntry = new EntryValidation(); _textEntry.ModifyFont(fontDescriptiontextEntry); //Change Selected Text, when looses entry focus _textEntry.ModifyBase(StateType.Active, Utils.ColorToGdkColor(Color.Gray)); //Final Pack KeyBoard + TextEntry VBox vboxResult = new VBox(false, _spacing); vboxResult.PackStart(_textEntry); vboxResult.PackStart(hboxResultReyboard); //Events this.KeyReleaseEvent += KeyBoardPad_KeyReleaseEvent; //Add Space arround Keyboards return(vboxResult); }
//Process Keyboard Inputs private void keyboardPadKey_Clicked(object sender, EventArgs e) { KeyboardPadKey vKey = (KeyboardPadKey)sender; VirtualKeyProperties vKeyProperties = null; Char _unicodeChar; bool _requireUpdate = false; bool _skipInsert = false; int _tempCursorPosition; String _stringChar; int selectionStart, selectionEnd; _textEntry.GetSelectionBounds(out selectionStart, out selectionEnd); if (selectionStart > 0 || selectionEnd > 0) { _textEntry.DeleteSelection(); } //Get Level and Assign Level Properties to current vKeyProperties switch (_activeModifierKey) { case ModifierKeys.Shift: vKeyProperties = vKey.Properties.L2; break; case ModifierKeys.Alt: vKeyProperties = vKey.Properties.L3; break; default: vKeyProperties = vKey.Properties.L1; break; } //DeadKey if (vKeyProperties != null && vKeyProperties.IsDeadKey) { _requireUpdate = true; _skipInsert = true; _activeDiacritical = vKeyProperties.Diacritical; } ; //Process Keys, Modifiers switch (vKey.Properties.Type) { //Sticky Caps Lock case "caps": _requireUpdate = true; if (_isCapsEnabled == false) { _isCapsEnabled = true; } else { _isCapsEnabled = false; } break; //Modifier Shift case "shift": _requireUpdate = true; if (_activeModifierKey == ModifierKeys.Shift) { _activeModifierKey = ModifierKeys.None; } else { _activeModifierKey = ModifierKeys.Shift; }; break; //Modifier Alt case "alt": _requireUpdate = true; if (_activeModifierKey == ModifierKeys.Alt) { _activeModifierKey = ModifierKeys.None; } else { _activeModifierKey = ModifierKeys.Alt; }; break; //Modifier Shift case "ctrl": _requireUpdate = true; if (_activeModifierKey == ModifierKeys.Ctrl) { _activeModifierKey = ModifierKeys.None; } else { _activeModifierKey = ModifierKeys.Ctrl; }; break; //Modal Cancel case "esc": ParentDialog.Respond(ResponseType.Cancel); break; //Modal Confirm case "enter": if (_textEntry.Validated) { // This Will Crash only in Debug, if Run Outside it Wont Crash (Simply disappear without log error) try { ParentDialog.Respond(ResponseType.Ok); } catch (Exception ex) { _log.Error(ex.Message, ex); } } else { Utils.ShowMessageTouch(ParentDialog, DialogFlags.Modal, MessageType.Error, ButtonsType.Ok, Resx.global_error, Resx.dialog_message_field_validation_error_keyboardpad); }; break; //Show/Hide Number Lock case "tab": if (_activeKeyboardMode == KeyboardMode.AlfaNumeric) { if (_vboxNumPadRows.Visible) { ParentDialog.WidthRequest -= _vboxNumPadRows.Allocation.Width + _spacing; _vboxNumPadRows.HideAll(); } else { ParentDialog.WidthRequest += _vboxNumPadRows.Allocation.Width + _spacing; _vboxNumPadRows.ShowAll(); }; } break; //Enable/Disable Internal Keyboard case "ekey": break; //Delete case "back": _textEntry.DeleteText(_textEntry.Position - 1, _textEntry.Position); break; //Cursor Move to Start case "home": _textEntry.Position = 0; break; //Cursor Move to End case "end": _textEntry.Position = _textEntry.Text.Length; break; //Does Nothing case "up": break; //Does Nothing case "down": break; //Move Cursor to Left case "left": if (_textEntry.Position > 0) { _textEntry.Position -= 1; } break; //Move Cursor to Right case "right": if (_textEntry.Position < _textEntry.Text.Length) { _textEntry.Position += 1; } break; //All Other Keys default: //NumberPad always work only with L1 if (vKey.Properties.L1.IsNumPad == true || vKey.Properties.Type == "space") { vKeyProperties = vKey.Properties.L1; } //If Caps enabled and is Letter, change to Level 2 (Uppercase) else if (_isCapsEnabled && Utils.IsLetter(Utils.UnicodeHexadecimalStringToChar(vKeyProperties.UnicodeId))) { vKeyProperties = vKey.Properties.L2; } ; //Get unicodeChar from UnicodeId after Caps _unicodeChar = Utils.UnicodeHexadecimalStringToChar(vKeyProperties.UnicodeId); //Modifie _unicodeChar Keys ex Culture Decimal Separator . with , [3,15 = Key NumberPad .] //if (vKey.Properties.RowIndex == 3 && vKey.Properties.ColIndex == 15) _unicodeChar = (char) GlobalFramework.CurrentCulture.NumberFormat.NumberDecimalSeparator[0]; //Always Disable Modifiers Keys After Use if (_activeModifierKey != ModifierKeys.None) { _requireUpdate = true; //Process Modifiers aBefore Disable Modifier switch (_activeModifierKey) { case ModifierKeys.Ctrl: switch (Convert.ToString(_unicodeChar).ToUpper()) { case "X": _textEntry.CutClipboard(); _skipInsert = true; break; case "C": _textEntry.CopyClipboard(); _skipInsert = true; break; case "V": _textEntry.PasteClipboard(); _skipInsert = true; break; } break; default: break; } //After Process Modifiers, restore default Non Modifiers State _activeModifierKey = ModifierKeys.None; } ; //Debug //_log.Debug(string.Format("keyboardKey_Clicked(): L1.Glyph:[{1}] L1.UnicodeId:[{2}] L1.CharacterName:[{3}] unicodeChar[{4}]", vKey.Properties.Type, vKeyProperties.Glyph, vKeyProperties.UnicodeId, vKeyProperties.CharacterName, _unicodeChar)); //Add to TextEntry _tempCursorPosition = _textEntry.Position; if (!_skipInsert) { _stringChar = Convert.ToString(_unicodeChar); //Diacritical if (_activeDiacritical != null) { _stringChar += Convert.ToString(Utils.UnicodeHexadecimalStringToChar(_activeDiacritical)); //Convert Diacritial chars to ISO chars to work with Validations and Peristence Database _stringChar = ReplaceDiacritial(_stringChar); //Reset activeDiacritical _activeDiacritical = null; } _textEntry.InsertText(_stringChar, ref _tempCursorPosition); _textEntry.Text.Normalize(); } ; _textEntry.Position = _tempCursorPosition; break; } //HACK: to Activate TextEntry and place Cursor _tempCursorPosition = _textEntry.Position; _textEntry.GrabFocus(); _textEntry.Position = _tempCursorPosition; //Update Keyboard if ModifierKey has Changed if (_requireUpdate) { UpdateKeyboard(); } }