Approved
Last Updated: 10 Sep 2019 20:55 by ADMIN
Pierre
Created on: 28 Mar 2019 09:46
Category: Entry
Type: Feature Request
2
Entry: Provide a way to override the behavior of the keyboard
I would need to control when the overlay keyboard will appear, for example, hide it when the Entry gets the focus.
3 comments
ADMIN
Lance | Principal TSE
Posted on: 10 Sep 2019 20:55

Hello dbnex,

Currently, Keyboard="None" is not available for the RadEntry (or any control implementing RadEntry). Thank you for providing this feedback, we'll use it in our feature planning for the RadEntry's keyboard features.

In the meantime, you can still interact with the native platform's keyboard APIs because Xamarin.Forms lets you directly use those APIs in simple Custom Renderer classes. "Custom renderer" might sound complicated at first, but it's really just a place that lets you insert your platform-specific code as the control is being created.

To better explain, I've included code below that hides the keyboard on all 3 platforms for the RadEntry.

Example Custom Renderers

On Android, you can hide the keyboard through the InputMethodManager:

using Android.Content;
using Android.Views.InputMethods;
using NumericHideKeyboard.Droid;
using Telerik.XamarinForms.Input;
using Xamarin.Forms;
using Xamarin.Forms.Platform.Android;

[assembly: ExportRenderer(typeof(RadEntry), typeof(CustomRadEntryRenderer))]
namespace NumericHideKeyboard.Droid
{
    public class CustomRadEntryRenderer : Telerik.XamarinForms.InputRenderer.Android.EntryRenderer
    {
        public CustomRadEntryRenderer(Context context)
            : base(context)
        {
        }

        protected override void OnElementChanged(ElementChangedEventArgs<RadEntry> e)
        {
            base.OnElementChanged(e);

            if (e.NewElement != null)
            {
                this.Control.ShowSoftInputOnFocus = false;
                this.Control.FocusChange += Control_FocusChange;
            }
        }

        private void Control_FocusChange(object sender, FocusChangeEventArgs e)
        {
            if (e.HasFocus)
            {
                // See https://docs.microsoft.com/en-us/dotnet/api/android.views.inputmethods.inputmethodmanager.hidesoftinputfromwindow?view=xamarin-android-sdk-9
                // and
                // https://developer.android.com/reference/android/view/inputmethod/InputMethodManager
                InputMethodManager imm = (InputMethodManager)this.Context.GetSystemService(Context.InputMethodService);
                imm.HideSoftInputFromWindow(this.Control.WindowToken, 0);
            }
        }
    }
}

 

On iOS, you can use ResignFirstResponder:

using NumericHideKeyboard.iOS;
using Telerik.XamarinForms.Input;
using Xamarin.Forms;
using Xamarin.Forms.Platform.iOS;

[assembly: ExportRenderer(typeof(RadEntry), typeof(CustomRadEntryRenderer))]
namespace NumericHideKeyboard.iOS
{
    public class CustomRadEntryRenderer : Telerik.XamarinForms.InputRenderer.iOS.EntryRenderer
    {
        protected override void OnElementChanged(ElementChangedEventArgs<RadEntry> e)
        {
            base.OnElementChanged(e);

            if (e.NewElement != null)
            {
                // See https://docs.microsoft.com/en-us/dotnet/api/uikit.uiresponder?view=xamarin-ios-sdk-12
                // and
                // https://forums.xamarin.com/discussion/5934/ios-newb-how-do-you-get-rid-of-the-keyboard
                this.Control.ResignFirstResponder();
            }
        }
    }
}

 

On UWP, you can use the InputPane

using System;
using System.Diagnostics;
using Windows.UI.ViewManagement;
using NumericHideKeyboard.UWP;
using Telerik.XamarinForms.Input;
using Xamarin.Forms.Platform.UWP;

[assembly: ExportRenderer(typeof(RadEntry), typeof(CustomRadEntryRenderer))]
namespace NumericHideKeyboard.UWP
{
    public class CustomRadEntryRenderer : Telerik.XamarinForms.InputRenderer.UWP.EntryRenderer
    {
        protected override void OnElementChanged(ElementChangedEventArgs<RadEntry> e)
        {
            base.OnElementChanged(e);

            if (e.NewElement != null)
            {
                this.Control.GotFocus += Tb_GotFocus;
            }
        }

        private void Tb_GotFocus(object sender, Windows.UI.Xaml.RoutedEventArgs e)
        {
            try
            {
                // See https://docs.microsoft.com/en-us/uwp/api/Windows.UI.ViewManagement.InputPane
                InputPane.GetForCurrentView().TryHide();
            }
            catch (Exception ex)
            {
                Debug.WriteLine($"Error getting InputPane - {ex.Message}");
            }
        }
    }
}

 

Keep in mind that these APIs are not something that we ship with the UI for Xamarin controls. Instead, the API is from the UWP, Xamarin.Android or Xamarin.iOS. you can learn more about any of them in the links I provide in the code.

Custom and Special Circumstances

If you have additional needs about when this should happen (i.e. different timing), then you can add the appropriate logic in the renderer using the native control. In the renderers, the this.Control property is the native control, you can access all of the control's properties, method and events there.

I hope this is useful to help you move forward until we have an official API option in Xamarin.Forms layer.

Regards,
Lance | Technical Support Engineer, Principal
Progress Telerik

Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Feedback Portal and vote to affect the priority of the items
dbnex
Posted on: 10 Sep 2019 15:50
... continuing on above comment, this should be supported by Xamarin.Forms, all 3 platforms Android, iOS and UWP.  UWP is important to us since lots of our customers use Windows
dbnex
Posted on: 10 Sep 2019 15:46

Yes, this is really missing in Xamarin.Forms.  We should have an Entry like view that will not show device keyboard when focused programatically on call to myEntry.Focus().

For example, some of us may use data-wedge type of barcode scanning where we dont want to use 3rd party SDK/EMDK for barcode scanners since we would have to support to many of these.  For simple barcode scanning, data wedge is fine and all we want is to be able to programatically focus on an Entry field (which could be visible or non-visible) and scan into it like so:

  1. I land on a view with this Entry field
  2. Code calls myEntry.Focus() to focus on it - no device keyboard should show up here
  3. I scan barcode
  4. Scanned barcode is processed
  5. I am back to step 2 above and can scan again next barcode - no device keyboard shows

Another scenario could be when we develop our own keyboard and dont want device keyboard to show up.  But this is less important to us than scenario with barcodes described above.

I have seen requests for this kind of Entry functionality dating from 2016 but Microsoft/Xamarin never looked into it.