/// <summary>
        /// Extension method to resolve supplied resource from a resource dictionary.
        /// </summary>
        /// <typeparam name="T">Expected type of requested resource.</typeparam>
        /// <param name="resources">ResourceDictionary from where to resolve resource.</param>
        /// <param name="resource">Resource to resolve.</param>
        /// <param name="defaultValue">Default value of expected type.</param>
        /// <returns>Resolved resource in expected type or supplied default value of expected type.</returns>
        /// <remarks>Recursion is used to resolve resources from within other resources.</remarks>
        static T GetResource <T>(this ResourceDictionary resources, object?resource, T defaultValue)
        {
            //Init
            var comparer = EqualityComparer <T> .Default;

            //Check resource type
            switch (resource)
            {
            case OnPlatform <T> value:
                //Get platform specific resource
                var platformValue = value.Platforms?.FirstOrDefault(p => p.Platform.Contains(Device.RuntimePlatform))?.Value;
                return(resources.GetResource <T>(platformValue, comparer.Equals(value.Default, default(T) ?? defaultValue) ? defaultValue : value.Default ?? defaultValue));

            case OnIdiom <T> value:
            {
                //Get idiom specific resource
                return(Device.Idiom switch
                    {
                        TargetIdiom.Phone => value.Phone,
                        TargetIdiom.Tablet => value.Tablet,
                        TargetIdiom.Desktop => value.Desktop,
                        TargetIdiom.TV => value.TV,
                        TargetIdiom.Watch => value.Watch,
                        _ => comparer.Equals(value.Default, default(T) ?? defaultValue) ? defaultValue : value.Default ?? defaultValue,
                    });
            }
        /// <summary>
        /// Gets or creates the material resource for the given VertexStructure object.
        /// </summary>
        internal static MaterialResource GetOrCreateMaterialResource(this ResourceDictionary resourceDict, VertexStructureSurface targetSurface)
        {
            NamedOrGenericKey materialKey = targetSurface.Material;
            NamedOrGenericKey textureKey  = targetSurface.TextureKey;

            // Get the material if it is already created
            if ((!materialKey.IsEmpty) && (resourceDict.ContainsResource(materialKey)))
            {
                return(resourceDict.GetResource <MaterialResource>(materialKey));
            }

            // Generate a dynamic material key
            if (materialKey.IsEmpty)
            {
                materialKey = new NamedOrGenericKey(targetSurface.MaterialProperties.GetDynamicResourceKey());
            }

            // Get the material if it is already created
            if (resourceDict.ContainsResource(materialKey))
            {
                return(resourceDict.GetResource <MaterialResource>(materialKey));
            }

            if (textureKey.IsEmpty)
            {
                // Create a default material without any texture
                SimpleColoredMaterialResource result = resourceDict.AddResource <SimpleColoredMaterialResource>(materialKey, new SimpleColoredMaterialResource());
                result.MaterialDiffuseColor = targetSurface.MaterialProperties.DiffuseColor;
                return(result);
            }
            else
            {
                // Create texture resource if needed
                try
                {
                    if ((!resourceDict.ContainsResource(textureKey)) &&
                        (!string.IsNullOrEmpty(textureKey.NameKey)))
                    {
                        // Try to find and create the texture resource by its name
                        if (targetSurface.ResourceLink != null)
                        {
                            var textureResourceLink = targetSurface.ResourceLink.GetForAnotherFile(textureKey.NameKey);

                            resourceDict.AddResource <StandardTextureResource>(
                                textureKey,
                                new StandardTextureResource(
                                    targetSurface.ResourceLink.GetForAnotherFile(textureKey.NameKey)));
                        }
                        else if (targetSurface.ResourceSourceAssembly != null)
                        {
                            var textureResourceLink = new AssemblyResourceLink(
                                targetSurface.ResourceSourceAssembly,
                                targetSurface.ResourceSourceAssembly.GetName().Name + ".Resources.Textures",
                                textureKey.NameKey);
                            if (textureResourceLink.IsValid())
                            {
                                resourceDict.AddResource <StandardTextureResource>(
                                    textureKey,
                                    new StandardTextureResource(textureResourceLink));
                            }
                            else
                            {
                                // Unable to resolve texture
                                textureKey = NamedOrGenericKey.Empty;
                            }
                        }
                        else
                        {
                            // Unable to resolve texture
                            textureKey = NamedOrGenericKey.Empty;
                        }
                    }
                }
                catch { }

                // Create a default textured material
                if (!textureKey.IsEmpty)
                {
                    SimpleColoredMaterialResource result = resourceDict.AddResource <SimpleColoredMaterialResource>(
                        materialKey,
                        new SimpleColoredMaterialResource(textureKey));
                    result.MaterialDiffuseColor = targetSurface.MaterialProperties.DiffuseColor;
                    return(result);
                }
                else
                {
                    SimpleColoredMaterialResource result = resourceDict.AddResource <SimpleColoredMaterialResource>(
                        materialKey,
                        new SimpleColoredMaterialResource());
                    result.MaterialDiffuseColor = targetSurface.MaterialProperties.DiffuseColor;
                    return(result);
                }
            }
        }