[NUI] Support implicit value in Xaml (#1784)
authorAdunFang <30402408+AdunFang@users.noreply.github.com>
Thu, 2 Jul 2020 07:03:31 +0000 (15:03 +0800)
committerGitHub <noreply@github.com>
Thu, 2 Jul 2020 07:03:31 +0000 (16:03 +0900)
Co-authored-by: Fang Xiaohui <xiaohui fang>
src/Tizen.NUI/src/internal/Xaml/ApplyPropertiesVisitor.cs
src/Tizen.NUI/src/internal/Xaml/CreateValuesVisitor.cs

index e4db39f..5b43fd2 100755 (executable)
@@ -540,14 +540,58 @@ namespace Tizen.NUI.Xaml
             if (serviceProvider != null && serviceProvider.IProvideValueTarget != null)
                 ((XamlValueTargetProvider)serviceProvider.IProvideValueTarget).TargetProperty = propertyInfo;
 
-            object convertedValue = value.ConvertTo(propertyInfo.PropertyType, () => propertyInfo, serviceProvider);
-            if (convertedValue != null && !propertyInfo.PropertyType.IsInstanceOfType(convertedValue))
+            object convertedValue = GetConvertedValue(propertyInfo.PropertyType, value, () => propertyInfo, serviceProvider);
+
+            if (null == convertedValue)
+            {
+                var methods = propertyInfo.PropertyType.GetMethods().Where(a => a.Name == "op_Implicit");
+
+                foreach (var method in methods)
+                {
+                    var paramType = method.GetParameters()[0].ParameterType;
+                    convertedValue = GetConvertedValue(paramType, value, () => propertyInfo, serviceProvider);
+
+                    if (null != convertedValue)
+                    {
+                        var realValue = Activator.CreateInstance(propertyInfo.PropertyType);
+                        convertedValue = method.Invoke(realValue, new object[] { convertedValue });
+
+                        if (null != convertedValue)
+                        {
+                            break;
+                        }
+                    }
+                }
+            }
+
+            if (null == convertedValue)
+            {
                 return false;
+            }
 
-            setter.Invoke(element, new object [] { convertedValue });
+            setter.Invoke(element, new object[] { convertedValue });
             return true;
         }
 
+        static private object GetConvertedValue(Type valueType, object value, Func<MemberInfo> minfoRetriever, XamlServiceProvider serviceProvider)
+        {
+            try
+            {
+                object convertedValue = value.ConvertTo(valueType, minfoRetriever, serviceProvider);
+
+                if (convertedValue != null && !valueType.IsInstanceOfType(convertedValue))
+                {
+                    return null;
+                }
+
+                return convertedValue;
+            }
+            catch
+            {
+                return null;
+            }
+        }
+
         static bool TryGetProperty(object element, string localName, out object value, IXmlLineInfo lineInfo, HydrationContext context, out Exception exception, out object targetProperty)
         {
             exception = null;
index e6ab251..150b200 100755 (executable)
@@ -279,6 +279,12 @@ namespace Tizen.NUI.Xaml
             {
                 var array = new object[1];
                 array[0] = Values[elementNode];
+
+                if (array[0].GetType().IsClass)
+                {
+                    elementNode.Accept(new ApplyPropertiesVisitor(Context, true), null);
+                }
+
                 return array;
             }