3

I have been trying out MAUI extensively lately and was trying to Create a Custom Control I guess and I ran into this weird problem, the CreatePlatform method was never getting called, at first I thought this was because I was using a MAUI class library and there was some issue with them, So instead I created another control in the same MAUI project instead of doing it through a CL and to my surprise even then it did not work.

My code is as follows:

Interface:

public interface IExtendedLabel : ILabel
{
    bool HasUnderline { get; }
    Color UnderlineColor { get; }
}

Label class:

public class ExtendedLabel : Label, IExtendedLabel
{
    public readonly BindableProperty HasUnderlineProperty = BindableProperty.Create(
        nameof(HasUnderline),
        typeof(bool),
        typeof(ExtendedLabel),
        true);

    public bool HasUnderline
    {
        get => (bool)GetValue(HasUnderlineProperty);
        set => SetValue(HasUnderlineProperty, value);
    }

    public readonly BindableProperty UnderlineColorProperty = BindableProperty.Create(
       nameof(UnderlineColor),
       typeof(Color),
       typeof(ExtendedLabel),
       Colors.Black);

    public Color UnderlineColor
    {
        get => (Color)GetValue(HasUnderlineProperty);
        set => SetValue(HasUnderlineProperty, value);
    }
}

My shared handler:

using System;
using MAUI.FreakyControls;
using Microsoft.Maui.Handlers;
#if ANDROID
using NativeView = AndroidX.AppCompat.Widget.AppCompatTextView;
#endif
#if IOS
using NativeView = UIKit.UILabel;
#endif
namespace Samples
{
    public partial class ExtendedLabelHandler : ViewHandler<IExtendedLabel,NativeView>
    {
        #region ctor 

        public static CommandMapper<IExtendedLabel, ExtendedLabelHandler> CommandMapper = new(ViewCommandMapper);


        public ExtendedLabelHandler() : base(FreakyEditorMapper)
        {

        }

        public ExtendedLabelHandler(IPropertyMapper mapper = null) : base(mapper ?? FreakyEditorMapper)
        {

        }

        #endregion

        #region Mappers

        public static IPropertyMapper<IExtendedLabel, ExtendedLabelHandler> FreakyEditorMapper = new PropertyMapper<IExtendedLabel, ExtendedLabelHandler>(ViewMapper)
        {
            [nameof(IExtendedLabel.HasUnderline)] = MapHasUnderlineWithColor,
            [nameof(IExtendedLabel.UnderlineColor)] = MapHasUnderlineWithColor
        };

        public static void MapHasUnderlineWithColor(ExtendedLabelHandler handler, IExtendedLabel entry)
        {

        }

        #endregion
    }
}

Handler Android:

public partial class ExtendedLabelHandler
    {
        protected override AppCompatTextView CreatePlatformView()
        {
            var nativeView = new AppCompatTextView(this.Context)
            {

            };
            return nativeView;
        }

        private void HandleNativeHasUnderline(bool hasUnderline, Color underlineColor)
        {
            if (hasUnderline)
            {
                var AndroidColor = underlineColor.ToNativeColor();
                var colorFilter = BlendModeColorFilterCompat.CreateBlendModeColorFilterCompat(
                    AndroidColor, BlendModeCompat.SrcIn);
                PlatformView.Background?.SetColorFilter(colorFilter);
            }
            else
            {
                PlatformView.Background?.ClearColorFilter();
            }
        }
    } 

My iOS handler:

public partial class ExtendedLabelHandler
    {
        CoreAnimation.CALayer bottomLine;

        protected override UILabel CreatePlatformView()
        {
            return new UILabel();
        }

        private void HandleNativeHasUnderline(bool hasUnderline, Color underlineColor)
        {
            if (hasUnderline)
            {
                var uiColor = underlineColor.ToNativeColor();
                bottomLine = BottomLineDrawer(uiColor);
                bottomLine.Frame = new CGRect(x: 0, y: PlatformView.Frame.Size.Height - 5,
                    width: PlatformView.Frame.Size.Width, height: 1);
                PlatformView.Layer.AddSublayer(bottomLine);
                PlatformView.Layer.MasksToBounds = true;
            }
            else
            {
                bottomLine?.RemoveFromSuperLayer();
            }
        }
    }

Adding the handler:

 handlers.AddHandler(typeof(IExtendedLabel), typeof(ExtendedLabelHandler));

Am I doing something wrong?

You can find the full code on my repo here which has a full working example of the method never getting called for some reason: https://github.com/FreakyAli/MAUI.FreakyControls/tree/r1-gh/feat/freakyeditor

Update

So I am not sure if this is a bug or not but I have raised one in GitHub anyway, which can be tracked here: https://github.com/dotnet/maui/issues/9720

halfer
  • 19,824
  • 17
  • 99
  • 186
FreakyAli
  • 13,349
  • 3
  • 23
  • 63
  • It seems there is something different from the steps of creating the custom controls in the official document, such as the control interface should be inherited from the IView. You can check the answer in [this link](https://stackoverflow.com/questions/68724240/what-will-happen-to-custom-controls-and-renderers-in-net-maui) and the [example](https://github.com/dotnet/maui/wiki/Porting-Custom-Renderers-to-Handlers#example) on the github. – Liyun Zhang - MSFT Aug 29 '22 at 09:42
  • That doesn't make sense though, if the control interface will only work if i inherit with IView, that just means that if i wanna take advantage of existing controls and build over them that won't work.... – FreakyAli Aug 29 '22 at 22:54
  • Did you try to create a custom control follow the steps in the link I provided? – Liyun Zhang - MSFT Aug 30 '22 at 09:27
  • @LiyunZhang-MSFT Apparently the issue was something totally different – FreakyAli Sep 01 '22 at 17:51

1 Answers1

4

So the issue was my registration, I was registering my interface instead of the class of my custom control:

 handlers.AddHandler(typeof(ExtendedLabel), typeof(ExtendedLabelHandler));
halfer
  • 19,824
  • 17
  • 99
  • 186
FreakyAli
  • 13,349
  • 3
  • 23
  • 63