コード例 #1
0
        private static string GeneratePropertyWrapperInitializers(
            PropertyTypeNode propertyType,
            string containerName,
            PropertyTypeNode.TypeTag containerTypeTag,
            string propertyWrapperTypeString,
            string propertyAccessorName,
            string propertyTypeString,
            Scope code
            )
        {
            var initializerParams = new List <string>();

            var accessors = GetPropertyWrapperAccessors(
                propertyType,
                containerName,
                containerTypeTag,
                propertyWrapperTypeString,
                propertyTypeString,
                propertyAccessorName);

            // @TODO shouldn't be done here, and be located in a cleaner place

#if ENABLE_CUSTOM_PROPERTY_PARTIALS
            if (propertyType.IsCustomProperty)
            {
                var containerAsAParemeterType =
                    containerTypeTag.HasFlag(PropertyTypeNode.TypeTag.Struct) ? $"ref {containerName}" : $"{containerName}";

                code.AddLine("");

                if (!string.IsNullOrEmpty(accessors.RefGetter))
                {
                    code.AddLine(
                        $"partial void {accessors.RefGetter}({containerAsAParemeterType} value, IPropertyVisitor visitor);");
                }

                code.AddLine($"partial void {accessors.ValueSetter}({containerAsAParemeterType} container, {propertyTypeString} value);");

                code.AddLine(
                    $"partial {propertyTypeString} {accessors.ValueGetter}({containerAsAParemeterType} container);");

                code.AddLine("");
            }
#endif

            initializerParams.Add($"nameof({propertyType.PropertyName})");
            initializerParams.Add(accessors.ValueGetter);
            initializerParams.Add(accessors.ValueSetter);

            if (!string.IsNullOrEmpty(accessors.RefGetter))
            {
                initializerParams.Add(accessors.RefGetter);
            }

            return($@"new { propertyWrapperTypeString }( {string.Join(", ", initializerParams)} )");
        }
コード例 #2
0
 public override void AddStringFragment()
 {
     if (!string.IsNullOrEmpty(Fragment))
     {
         Scope.AddLine(Fragment);
     }
 }
コード例 #3
0
        private static void GenerateClassPropertiesForPropertyAccessor(
            PropertyTypeNode.TypeTag containerTypeTag,
            PropertyTypeNode propertyType,
            Scope code
            )
        {
            var containerAsAParamTokens = new List <string> {
            };

            if (containerTypeTag.HasFlag(PropertyTypeNode.TypeTag.Struct))
            {
                containerAsAParamTokens.Add("ref");
            }
            containerAsAParamTokens.Add("this");

            var getSetValueCallContainerParam = string.Join(" ", containerAsAParamTokens);

            var propertyWrapperVariableName = GetPropertyWrapperVariableName(propertyType);

            var propertyTypeString = TypeDeclarationStringForProperty(propertyType);

            var isCompositeType = PropertyTypeNode.IsCompositeType(propertyType.Tag);

            var modifiers = string.Join(" ", ModifiersToStrings(AccessModifiers.Public));

            code.AddLine($"{modifiers} {propertyTypeString} {propertyType.PropertyName}");

            {
                code.AddLine("{");
                var accessorScope = new Scope(code);
                accessorScope.AddLine($"get {{ return {propertyWrapperVariableName}.GetValue({getSetValueCallContainerParam}); }}");
                if (!isCompositeType)
                {
                    accessorScope.AddLine($"set {{ {propertyWrapperVariableName}.SetValue({getSetValueCallContainerParam}, value); }}");
                }
                code.AddLine("}");
            }
        }
コード例 #4
0
        private void GeneratePropertyContainerFor(
            PropertyTypeNode c,
            Func <string, CSharpGenerationCache.CodeInfo> dependancyLookupFunc,
            StringBuffer gen)
        {
            var containerName = c.TypeName;

            var containerTypeTag = c.Tag;

            var baseClass = string.IsNullOrEmpty(c.OverrideDefaultBaseClass)
                ? "IPropertyContainer" : c.OverrideDefaultBaseClass;

            var rootScope = new Scope();

            var shouldGeneratePRopertyContainerImplementation = !c.NoDefaultImplementation;

            using (var d = new PropertyContainerDataTypeDecorator(c, rootScope.Code, new List <string> {
                baseClass
            }))
                using (var scope = new Scope(rootScope))
                {
                    if (shouldGeneratePRopertyContainerImplementation)
                    {
                        if (c.Properties.Count != 0)
                        {
                            foreach (var propertyType in c.Properties)
                            {
                                GenerateProperty(
                                    containerName,
                                    containerTypeTag,
                                    propertyType,
                                    scope
                                    );
                                scope.AddLine("");
                            }

                            scope.AddLine("");
                        }

                        GenerateUserHooksFor(c, scope);

                        // Add inherited properties if it applies

                        var propertyBagElementNames = PropertyBagItemNames;
                        if (!string.IsNullOrEmpty(c.OverrideDefaultBaseClass) && dependancyLookupFunc != null)
                        {
                            var cachedContainer = dependancyLookupFunc(c.OverrideDefaultBaseClass);
                            if (cachedContainer != null)
                            {
                                propertyBagElementNames = PropertyBagItemNames.Select(n => n).ToList();

                                propertyBagElementNames.AddRange(cachedContainer.GeneratedPropertyFieldNames);
                            }
                        }

                        GeneratePropertyBag(
                            c,
                            propertyBagElementNames,
                            scope);

                        GenerateConstructorFor(c, scope.Code);

                        GenerateStaticConstructorFor(c, scope.Code);

                        // @TODO Cleanup
                        // Recurse to collect nested container definitions

                        foreach (var nestedContainer in c.NestedContainers)
                        {
                            if (nestedContainer == null)
                            {
                                continue;
                            }

                            var g = new CSharpContainerGenerator()
                            {
                                DoGenerateNamespace = false
                            };
                            g.GeneratePropertyContainer(nestedContainer, dependancyLookupFunc);

                            if (!string.IsNullOrEmpty(g.Code.ToString()))
                            {
                                scope.AddLine(string.Empty);
                                scope.AddLine(string.Empty);

                                scope.AddLine(g.Code.ToString());

                                scope.AddLine(string.Empty);
                                scope.AddLine(string.Empty);
                            }
                        }

                        scope.AddLine("public IVersionStorage VersionStorage => DefaultVersionStorage.Instance;");
                        scope.AddLine(Environment.NewLine);
                    }
                }

            gen.Append(rootScope.Code);
        }
コード例 #5
0
        public void GenerateProperty(
            string containerName,
            PropertyTypeNode.TypeTag containerTypeTag,
            PropertyTypeNode propertyType,
            Scope code)
        {
            // Public C# Property & backing field

            GenerateClassPropertiesForPropertyAccessor(containerTypeTag, propertyType, code);

            var propertyWrapperTypeName = GetPropertyWrapperTypeFor(
                containerName,
                containerTypeTag,
                propertyType);

            code.AddLine(GeneratePropertyWrapperBackingVariable(
                             propertyWrapperTypeName, containerTypeTag, propertyType));

            // Backing field if any

            var propertyAccessorName = string.Empty;
            var backingField         = GeneratePropertyBackingField(
                propertyType.PropertyName,
                propertyType,
                out propertyAccessorName
                );

            if (!string.IsNullOrEmpty(backingField))
            {
                // If we have a class we delegate init to constructor otherwise we default construct here

                var initializer = GenerateInitializerFromProperty(containerTypeTag, propertyType);

                var initializerFragment = backingField;

                if (!string.IsNullOrEmpty(initializer) && !propertyType.DontInitializeBackingField)
                {
                    initializerFragment += $" = {initializer}";
                }

                initializerFragment += ";";

                code.AddLine(initializerFragment);
            }

            //      -> Add constructor initializer fragments for later stage for that property

            var propertyTypeString          = TypeDeclarationStringForProperty(propertyType);
            var propertyWrapperVariableName = GetPropertyWrapperVariableName(propertyType);

            {
                var initializer = GeneratePropertyWrapperInitializers(
                    propertyType,
                    containerName,
                    containerTypeTag,
                    propertyWrapperTypeName,
                    propertyAccessorName,
                    propertyTypeString,
                    code);

                AddStaticConstructorInStageFragment(
                    ConstructorStage.PropertyInitializationStage,
                    new CSharpGenerationFragmentContext()
                {
                    Scope    = code,
                    Fragment = $"{propertyWrapperVariableName} = {initializer};"
                });
            }

            PropertyBagItemNames.Add(propertyWrapperVariableName);
        }