Selectable Label on Xamarin.Forms
The Xamarin.Forms Label doesn't have something as basic as being able to select text, so we are going to implement it using ViewRenderer: UITextView in iOS and TextView in Android.
iOS behavior:
Android behavior:
Here you can see the iOS Renderer using UITextview
Here you can see the Android Renderer using Textview:
Finally this is the custom control with some properties that we are going to use in our pages:
You can see the complete Renderers code and the use of SelectableLabel control in this Github repository.
If you need a better understanding of the native properties that make the text selectable, I recommend reading this post by Anna.
I hope this has been helpful for someone :)
iOS behavior:

Android behavior:

Here you can see the iOS Renderer using UITextview
public class SelectableLabelRenderer : ViewRenderer
{
UITextView uiTextView;
protected override void OnElementChanged(ElementChangedEventArgs e)
{
base.OnElementChanged(e);
var label = (SelectableLabel)Element;
if (label == null)
return;
if (Control == null)
{
uiTextView = new UITextView();
}
uiTextView.Selectable = true;
uiTextView.Editable = false;
uiTextView.ScrollEnabled = false;
uiTextView.TextContainerInset = UIEdgeInsets.Zero;
uiTextView.TextContainer.LineFragmentPadding = 0;
uiTextView.BackgroundColor = UIColor.Clear;
// Initial properties Set
uiTextView.Text = label.Text;
uiTextView.TextColor = label.TextColor.ToUIColor();
switch (label.FontAttributes)
{
case FontAttributes.None:
uiTextView.Font = UIFont.SystemFontOfSize(new nfloat(label.FontSize));
break;
case FontAttributes.Bold:
uiTextView.Font = UIFont.BoldSystemFontOfSize(new nfloat(label.FontSize));
break;
case FontAttributes.Italic:
uiTextView.Font = UIFont.ItalicSystemFontOfSize(new nfloat(label.FontSize));
break;
default:
uiTextView.Font = UIFont.BoldSystemFontOfSize(new nfloat(label.FontSize));
break;
}
SetNativeControl(uiTextView);
}
}
Here you can see the Android Renderer using Textview:
public class SelectableLabelRenderer : ViewRenderer
{
TextView textView;
public SelectableLabelRenderer(Context context) : base(context)
{
}
protected override void OnElementChanged(ElementChangedEventArgs e)
{
base.OnElementChanged(e);
var label = (SelectableLabel)Element;
if (label == null)
return;
if (Control == null)
{
textView = new TextView(this.Context);
}
textView.Enabled = true;
textView.Focusable = true;
textView.LongClickable = true;
textView.SetTextIsSelectable(true);
// Initial properties Set
textView.Text = label.Text;
textView.SetTextColor(label.TextColor.ToAndroid());
switch (label.FontAttributes)
{
case FontAttributes.None:
textView.SetTypeface(null, Android.Graphics.TypefaceStyle.Normal);
break;
case FontAttributes.Bold:
textView.SetTypeface(null, Android.Graphics.TypefaceStyle.Bold);
break;
case FontAttributes.Italic:
textView.SetTypeface(null, Android.Graphics.TypefaceStyle.Italic);
break;
default:
textView.SetTypeface(null, Android.Graphics.TypefaceStyle.Normal);
break;
}
textView.TextSize = (float)label.FontSize;
SetNativeControl(textView);
}
}
Finally this is the custom control with some properties that we are going to use in our pages:
public class SelectableLabel : View
{
public static readonly BindableProperty TextProperty = BindableProperty.Create(nameof(Text), typeof(string), typeof(SelectableLabel), default(string));
public static readonly BindableProperty TextColorProperty = BindableProperty.Create(nameof(TextColor), typeof(Color), typeof(SelectableLabel), Color.Black);
public static readonly BindableProperty FontAttributesProperty = BindableProperty.Create(nameof(FontAttributes), typeof(FontAttributes), typeof(SelectableLabel), FontAttributes.None);
public static readonly BindableProperty FontSizeProperty = BindableProperty.Create(nameof(FontSize), typeof(double), typeof(SelectableLabel), -1.0);
public string Text
{
get { return (string)GetValue(TextProperty); }
set { SetValue(TextProperty, value); }
}
public Color TextColor
{
get { return (Color)GetValue(TextColorProperty); }
set { SetValue(TextColorProperty, value); }
}
public FontAttributes FontAttributes
{
get { return (FontAttributes)GetValue(FontAttributesProperty); }
set { SetValue(FontAttributesProperty, value); }
}
[TypeConverter(typeof(FontSizeConverter))]
public double FontSize
{
get { return (double)GetValue(FontSizeProperty); }
set { SetValue(FontSizeProperty, value); }
}
}
You can see the complete Renderers code and the use of SelectableLabel control in this Github repository.
If you need a better understanding of the native properties that make the text selectable, I recommend reading this post by Anna.
I hope this has been helpful for someone :)
Comments
Post a Comment