public override ICodeBlock GenerateFields(ICodeBlock codeBlock,  SaveClasses.IElement element)
        {
            #region Get the ContentManager variable to use

            string contentManagerName = "ContentManagerName";

            if (element is ScreenSave)
            {
                contentManagerName = (element as ScreenSave).ContentManagerForCodeGeneration;
            }

            #endregion

            if (element is EntitySave)
            {
                codeBlock.Line("static object mLockObject = new object();");
                codeBlock.Line("static System.Collections.Generic.List<string> mRegisteredUnloads = new System.Collections.Generic.List<string>();");

                #region Keep track of whether we've already registered an unload method and if StaticContent has been loaded
                codeBlock.Line("static System.Collections.Generic.List<string> LoadedContentManagers = new System.Collections.Generic.List<string>();");
                #endregion
            }

            for (int i = 0; i < element.ReferencedFiles.Count; i++)
            {
                AppendFieldOrPropertyForReferencedFile(codeBlock,
                    element.ReferencedFiles[i], element.Name, element, contentManagerName);

                //stringBuilder.AppendLine(GetFieldForReferencedFile(mSaveObject.ReferencedFiles[i]));

            }

            return codeBlock;
        }
        public override void GenerateInitializeEnd(ICodeBlock codeBlock)
        {
            codeBlock.Line("#if DEBUG && WINDOWS");
            codeBlock.Line("InitializeFileWatch();");
            codeBlock.Line("#endif");

        }
        public override ICodeBlock GenerateAddToManagers(ICodeBlock codeBlock, IElement element)
        {
            if (ShouldGenerate)
            {
                foreach (var layer in GetObjectsForGumLayers(element))
                {
                    var rfs = GetScreenRfsIn(element);
                    if (rfs != null)
                    {

                        codeBlock.Line(layer.InstanceName + "Gum = RenderingLibrary.SystemManagers.Default.Renderer.AddLayer();");


                        codeBlock.Line(rfs.GetInstanceName() + ".AddGumLayerToFrbLayer(" + layer.InstanceName + "Gum, " + layer.InstanceName + ");");
                    }
                }
                // todo:  Need to register the layer here
                foreach (var item in element.AllNamedObjects.Where(item =>
                    GumPluginCodeGenerator.IsGue(item) &&
                    !string.IsNullOrEmpty(item.LayerOn) &&
                    NamedObjectSaveCodeGenerator.GetFieldCodeGenerationType(item) == CodeGenerationType.Full))
                {
                    codeBlock.Line(item.FieldName + ".MoveToLayer(" + item.LayerOn + "Gum);");
                }
            }
            return base.GenerateAddToManagers(codeBlock, element);
        }
        public override ICodeBlock GenerateFields(ICodeBlock codeBlock, SaveClasses.IElement element)
        {
            codeBlock.Line("#if DEBUG");
            codeBlock.Line("static bool HasBeenLoadedWithGlobalContentManager = false;");
            codeBlock.Line("#endif");

            return codeBlock;
        }
        public override ICodeBlock GenerateFields(ICodeBlock codeBlock, IElement element)
        {
            if (IsLoadingScreen(element))
            {
                codeBlock.Line("double mSavedTargetElapedTime;");

                codeBlock.Line("private static System.Action<FlatRedBall.Screens.Screen> nextCallback;");
            }
            return codeBlock;
        }
        public override void GenerateAdditionalMethods(ICodeBlock codeBlock)
        {
            codeBlock.Line("#if DEBUG && WINDOWS");

            codeBlock.Line("static System.IO.FileSystemWatcher watcher;");
            GenerateInitialize(codeBlock);

            GenerateHandleFileChanged(codeBlock);
            codeBlock.Line("#endif");

        }
        public override ICodeBlock GenerateInitialize(ICodeBlock codeBlock, IElement element)
        {
            if (element is EntitySave && ((EntitySave)element).ImplementsIWindow &&
                ((EntitySave)element).GetInheritsFromIWindow() == false)
            {
                codeBlock.Line("this.Click += CallLosePush;");
                codeBlock.Line("this.RollOff += CallLosePush;");

            }
            return codeBlock;
        }
        public override ICodeBlock GenerateAdditionalMethods(ICodeBlock codeBlock, IElement element)
        {
            if (element is EntitySave && ((EntitySave)element).ImplementsIDrawableBatch)
            {
                var entitySave = element as EntitySave;

                codeBlock.Line("void FlatRedBall.Graphics.IDrawableBatch.Update(){}");
                codeBlock.Line("void FlatRedBall.Graphics.IDrawableBatch.Destroy(){}");

            }

            return codeBlock;
        }
        public override ICodeBlock GenerateFields(ICodeBlock codeBlock, FlatRedBall.Glue.SaveClasses.IElement element)
        {
            if (element.SupportsAdvancedInterpolation())
            {
                foreach (var enumName in element.GetStateEnumNames())
                {
                    codeBlock.Line("FlatRedBall.Glue.StateInterpolation.Tweener " + TweenerNameFor(enumName) + ";");
                    codeBlock.Line(enumName + " mFrom" + enumName + "Tween;");
                    codeBlock.Line(enumName + " mTo" + enumName + "Tween;");
                }
            }

            return codeBlock;
        }
        private void GenerateInterpolateBetween(ElementSave elementSave, ICodeBlock currentBlock,
            string enumType, IEnumerable<StateSave> states)
        {
            // We used to only generate these if there was were any states in this category, but
            // since Gum generated code supports dynamic states, there could be states in a category
            // even if they're not defined in Gum.
            //if (states.Count() > 0)
            {
                currentBlock = currentBlock.Function("public void",
                    "InterpolateBetween", enumType + " firstState, " + enumType + " secondState, float interpolationValue");

                GenerateDebugCheckForInterpolationValueNaN(currentBlock);

                Dictionary<VariableSave, InterpolationCharacteristic> interpolationCharacteristics =
                   new Dictionary<VariableSave, InterpolationCharacteristic>();

                CreateStartingValueVariables(elementSave, states, currentBlock, interpolationCharacteristics);

                currentBlock = currentBlock.Switch("firstState");
                currentBlock = SetInterpolateBetweenValuesForStates(elementSave, enumType, states, currentBlock,
                    interpolationCharacteristics, FirstValue);
                currentBlock = currentBlock.End();

                currentBlock = currentBlock.Switch("secondState");
                currentBlock = SetInterpolateBetweenValuesForStates(elementSave, enumType, states, currentBlock,
                    interpolationCharacteristics, SecondValue);
                currentBlock = currentBlock.End();


                currentBlock = AssignValuesUsingStartingValues(elementSave, currentBlock, interpolationCharacteristics);

                currentBlock = currentBlock.If("interpolationValue < 1");

                string fieldToAssign;
                if (enumType == "VariableState")
                {
                    fieldToAssign = "mCurrentVariableState";
                }
                else
                {
                    fieldToAssign = "mCurrent" + enumType + "State";
                }

                currentBlock.Line(fieldToAssign + " = firstState;");
                currentBlock = currentBlock.End().Else();
                currentBlock.Line(fieldToAssign + " = secondState;");
                currentBlock = currentBlock.End();
            }
        }
        private void GenerateAnimateForCategory(ICodeBlock currentBlock, string categoryName, List<Gum.DataTypes.Variables.StateSave> states)
        {
            string propertyToAssign;
            if (categoryName == "VariableState")
            {
                propertyToAssign = "this.CurrentVariableState";
            }
            else
            {
                propertyToAssign = "this.Current" + categoryName + "State";
            }
            currentBlock = currentBlock.Function("public void", "Animate",
                "System.Collections.Generic.IEnumerable<FlatRedBall.Gum.Keyframe<" + categoryName + ">> keyframes");
            {
                currentBlock.Line("bool isFirst = true;");
                currentBlock.Line("FlatRedBall.Gum.Keyframe<" + categoryName + "> lastKeyframe = null;");

                var foreachBlock = currentBlock.ForEach("var frame in keyframes");
                {
                    var ifBlock = foreachBlock.If("isFirst");
                    {
                        ifBlock.Line("isFirst = false;");
                        ifBlock.Line(propertyToAssign + " = frame.State;");

                    }
                    var elseBlock = ifBlock.End().Else();
                    {
                        elseBlock.Line("float timeToTake = frame.Time - lastKeyframe.Time;");
                        elseBlock.Line("var fromState = lastKeyframe.State;");
                        elseBlock.Line("var toState = frame.State;");
                        elseBlock.Line("var interpolationType = lastKeyframe.InterpolationType;");
                        elseBlock.Line("var easing = lastKeyframe.Easing;");

                        elseBlock.Line(
                            "System.Action action = () => this.InterpolateTo(fromState, toState, timeToTake, interpolationType, easing, {});");

                        elseBlock.Line(
                            "FlatRedBall.Instructions.DelegateInstruction instruction = new FlatRedBall.Instructions.DelegateInstruction(action);");
                        elseBlock.Line("instruction.Target = this;");
                        elseBlock.Line("instruction.TimeToExecute = FlatRedBall.TimeManager.CurrentTime + lastKeyframe.Time;");

                        elseBlock.Line("FlatRedBall.Instructions.InstructionManager.Instructions.Add(instruction);");
                    }

                    foreachBlock.Line("lastKeyframe = frame;");
                }
            }
        }
        public override ICodeBlock GenerateFields(ICodeBlock codeBlock, IElement element)
        {
            foreach (EventResponseSave ers in element.Events)
            {
                bool isTunneling = ers.GetIsTunneling();
                bool isExposing = ers.GetIsExposing();

                bool shouldCreateMember =
                    isExposing || isTunneling;

                if (!shouldCreateMember)
                {
                    shouldCreateMember = !string.IsNullOrEmpty(ers.DelegateType);
                }

                if (shouldCreateMember)
                {
                    string delegateType = ers.GetEffectiveDelegateType(element);

                    codeBlock.Line("public event " + delegateType + " " + ers.EventName + ";");

                }
            }

            return codeBlock;
        }
        private void GenerateInitializeLevel(ICodeBlock codeBlock, IElement element)
        {
            #region /////////////////////////////////Early out////////////////////////////////
            bool shouldGenerate = GetIfShouldGenerate(element);

            if (!shouldGenerate)
            {
                return;
            }

            ///////////////////////////////End early out/////////////////////////////
            #endregion


            codeBlock.Line("FlatRedBall.TileGraphics.LayeredTileMap CurrentTileMap;");
            var function = codeBlock.Function("void", "InitializeLevel", "string levelName");

            GenerateInitializeLevelObjects(function);

            GenerateInitializeCamera(function);

            GenerateAddCollisionAndEntities(function);

            GenerateInitializeAnimations(function);
        }
 private static void TryGenerateRemoveShapeCollectionFromManagers(ICodeBlock codeBlock, IElement element)
 {
     if (element.IsICollidable())
     {
         codeBlock.Line("mGeneratedCollision.RemoveFromManagers(clearThis: false);");
     }
 }
 public static void GenerateTimedEmit(ICodeBlock codeBlock, NamedObjectSave nos)
 {
     if (!nos.IsDisabled && nos.AddToManagers && !nos.DefinedByBase && nos.IsEmitter())
     {
         codeBlock.Line(nos.InstanceName + ".TimedEmit();");
     }
 }
 public override ICodeBlock GenerateActivity(ICodeBlock codeBlock, IElement element)
 {
     if(IsLoadingScreen(element))
     {
         codeBlock.Line("AsyncActivity();");
     }
     return codeBlock;
 }
 public static void GenerateTimedEmit(ICodeBlock codeBlock, ReferencedFileSave rfs, IElement element)
 {
     if (rfs.LoadedAtRuntime && !rfs.LoadedOnlyWhenReferenced && (element is ScreenSave || rfs.IsSharedStatic == false)
         && !string.IsNullOrEmpty(rfs.Name) && FileManager.GetExtension(rfs.Name) == "emix")
     {
         codeBlock.Line(rfs.GetInstanceName() + ".TimedEmit();");
     }
 }
 public override ICodeBlock GenerateFields(ICodeBlock codeBlock, IElement element)
 {
     if (IsLoadingScreen(element))
     {
         codeBlock.Line("double mSavedTargetElapedTime;");
     }
     return codeBlock;
 }
        public override ICodeBlock GenerateAdditionalMethods(ICodeBlock codeBlock, FlatRedBall.Glue.SaveClasses.IElement element)
        {
            //////////////////////////EARLY OUT//////////////////////////////////////
            if (element is ScreenSave)
            {
                return codeBlock;
            }
            ///////////////////////END EARLY OUT/////////////////////////////////////

            codeBlock = codeBlock.Function("public void", "MoveToLayer", "Layer layerToMoveTo");

            foreach (NamedObjectSave nos in element.NamedObjects)
            {
                if (!nos.IsDisabled)
                {
                    if (nos.GetAssetTypeInfo() != null && !string.IsNullOrEmpty(nos.GetAssetTypeInfo().RemoveFromLayerMethod))
                    {
                        NamedObjectSaveCodeGenerator.AddIfConditionalSymbolIfNecesssary(codeBlock, nos);
                        bool shouldSkip = GetShouldSkip(nos);

                        if (!shouldSkip)
                        {
                            codeBlock.If("LayerProvidedByContainer != null")
                                .Line(nos.GetAssetTypeInfo().RemoveFromLayerMethod.Replace("this", nos.InstanceName).Replace("mLayer", "LayerProvidedByContainer") + ";")
                            .End();

                            codeBlock.Line(nos.GetAssetTypeInfo().LayeredAddToManagersMethod[0].Replace("this", nos.InstanceName).Replace("mLayer", "layerToMoveTo") + ";");
                        }
                        NamedObjectSaveCodeGenerator.AddEndIfIfNecessary(codeBlock, nos);
                    }
                    else if (nos.SourceType == SourceType.Entity && !string.IsNullOrEmpty(nos.SourceClassType))
                    {
                        NamedObjectSaveCodeGenerator.AddIfConditionalSymbolIfNecesssary(codeBlock, nos);
                        codeBlock.Line(nos.InstanceName + ".MoveToLayer(layerToMoveTo);");
                        NamedObjectSaveCodeGenerator.AddEndIfIfNecessary(codeBlock, nos);
                    }
                }
            }

            codeBlock.Line("LayerProvidedByContainer = layerToMoveTo;");

            codeBlock = codeBlock.End();

            return codeBlock;
        }
        public override void GenerateRemoveFromManagers(ICodeBlock codeBlock, IElement element)
        {
            if(ShouldGenerate(element))
            {
                codeBlock.Line(
                    "FlatRedBall.SpriteManager.RemoveDrawableBatch(this);");
            }

        }
        public override ICodeBlock GenerateActivity(ICodeBlock codeBlock, FlatRedBall.Glue.SaveClasses.IElement element)
        {
            if (Active)
            {
                codeBlock.Line("TimeManager.SumTimeSection(\"Throwaway\");");
            }

            return codeBlock;
        }
        public override ICodeBlock GenerateLoadStaticContent(ICodeBlock codeBlock, SaveClasses.IElement element)
        {
            #region For debugging record if we're using a global content manager

            codeBlock.Line("#if DEBUG");
            
            codeBlock.If("contentManagerName == FlatRedBall.FlatRedBallServices.GlobalContentManager")
                .Line("HasBeenLoadedWithGlobalContentManager = true;");
            
            codeBlock.ElseIf("HasBeenLoadedWithGlobalContentManager")
                .Line("throw new System.Exception(\"This type has been loaded with a Global content manager, then loaded with a non-global.  This can lead to a lot of bugs\");");

            codeBlock.Line("#endif");
            
            #endregion

            return codeBlock;
        }
        public static void GenerateFields(IElement saveObject, ICodeBlock codeBlock)
        {
            if (ObjectFinder.Self.GlueProject.PerformanceSettingsSave.RecordInitializeSegments &&
                saveObject is ScreenSave)
            {
                codeBlock.Line("FlatRedBall.Performance.Measurement.Section mSection;");
            }

        }
        public override ICodeBlock GenerateAddToManagers(ICodeBlock codeBlock, IElement element)
        {
            if (ShouldGenerate(element))
            {
                var entity = element as EntitySave;

                codeBlock.Line(
                    "FlatRedBall.SpriteManager.AddToLayer((FlatRedBall.Graphics.IDrawableBatch)this, layerToAddTo);");
            }
            return codeBlock;
        }
 public override ICodeBlock GenerateFields(ICodeBlock codeBlock, IElement element)
 {
     if (ShouldGenerate)
     {
         foreach (var layer in GetObjectsForGumLayers(element))
         {
             codeBlock.Line("global::RenderingLibrary.Graphics.Layer " + layer.InstanceName + "Gum;");
         }
     }
     return codeBlock;
 }
        private void GenerateInterface(ICodeBlock codeBlock, BehaviorSave behavior)
        {

            foreach (var category in behavior.Categories)
            {
                string propertyName = behavior.Name + category.Name;

                codeBlock.Line($"{propertyName} Current{propertyName}State {{set;}}");
            }

        }
        public override ICodeBlock GenerateActivity(ICodeBlock codeBlock, FlatRedBall.Glue.SaveClasses.IElement element)
        {
            if (element.SupportsAdvancedInterpolation())
            {
                foreach (var enumName in element.GetStateEnumNames())
                {
                    codeBlock.Line(TweenerNameFor(enumName) + ".Update(FlatRedBall.TimeManager.SecondDifference);");

                }
            }
            return codeBlock;
        }
        public override ICodeBlock GeneratePostInitialize(ICodeBlock codeBlock, IElement element)
        {
            if (element.IsICollidable())
            {
                codeBlock.Line("mGeneratedCollision = new FlatRedBall.Math.Geometry.ShapeCollection();");

                foreach (var item in element.NamedObjects.Where(item=>item.IncludeInICollidable))
                {
                    string addCall = item.GetAddToShapeCollection();

                    if (!string.IsNullOrEmpty(addCall))
                    { 
                        codeBlock.Line("mGeneratedCollision." + addCall + "(" + item.FieldName + ");");
                    }


                }
            }

            return codeBlock;
        }
        public static void HandleWriteInstanceVariableAssignment(NamedObjectSave instance, ICodeBlock code, InstructionSave variable)
        {
            var shouldHandle = variable.Member == "AtlasedTexture" && instance.SourceClassType == "Sprite";

            if(shouldHandle)
            {
                var memberName = instance.InstanceName;

                // The code should look something like:
                // 
                // SpriteInstance.AtlasedTexture = FlatRedBall.Graphics.Texture.AtlasLoader.LoadAtlasedTexture("asdf");
                //
                // But I still need to make the AtlasLoader keep track of all loaded assets, and I need to have a "priority" system

                code = code.Block();
                {
                    // eventually this might exist
                    //var atlas = instance.GetInstructionFromMember("");
                    // for now we assume that the texture packer project is in global content
                    var rfs = GlueState.Self.CurrentGlueProject.GlobalFiles.FirstOrDefault(item =>
                    {
                        var ati = item.GetAssetTypeInfo();
                        if(ati != null)
                        {
                            return ati == AtiManager.Self.TextureAtlasAti;
                        }

                        return false;
                    });

                    if (rfs != null)
                    {
                        var atlas = $"{GlueState.Self.ProjectNamespace}.GlobalContent.{rfs.GetInstanceName()}";
                        code.Line($"var atlas = {atlas};");

                        code.Line($"{memberName}.AtlasedTexture = atlas.Sprite(\"{variable.Value}\");");
                    }
                }
            }
        }
        public override ICodeBlock GenerateActivity(ICodeBlock codeBlock, IElement element)
        {
            var collection = ParentPlugin.GlueCommands.TreeNodeCommands.GetProperty<StateChainCollection>(element, StateChainsPlugin.PropertyName);

            if (collection == null) return codeBlock;

            if(collection.StateChains.Count > 0)
            {
                codeBlock.Line("ManageStateChains();");
            }

            return codeBlock;
        }
        // We need to make this be part of the function so that we can have everything be async
        //static List<string> mUsingStrings = new List<string>();
        internal static void GenerateUsingStatements(ICodeBlock codeBlock, IElement SaveObject)
        {
            List <string> usingStrings = new List <string>();

            if (SaveObject is EntitySave)
            {
                EntitySave asEntitySave = (EntitySave)SaveObject;

                bool hasScreensInProject = ProjectManager.GlueProjectSave.Screens.Count != 0;
                if (hasScreensInProject)
                {
                    usingStrings.Add(ProjectManager.ProjectNamespace + ".Screens");
                }

                // I don't think we need this anymore
                //mUsingStrings.Add("Matrix = Microsoft.Xna.Framework.Matrix");


                // Since Entities inherit are IDestroyable
                usingStrings.Add("FlatRedBall.Graphics");
                // And since we want a Visible property, we'll have extension methods for Lists of this
                usingStrings.Add("FlatRedBall.Math");


                if (asEntitySave.CreatedByOtherEntities)
                {
                    usingStrings.Add(ProjectManager.ProjectNamespace + ".Performance");
                }

                if (asEntitySave.ImplementsIClickable || asEntitySave.ImplementsIWindow)
                {
                    usingStrings.Add("FlatRedBall.Gui");
                }
            }

            // We are phasing this out:
            //mUsingStrings.Add("FlatRedBall.Broadcasting");



            #region Add the using PROJECT.Factories if necessary
            if (ProjectManager.GlueProjectSave.Entities.Count != 0)
            {
                // add their usings
                for (int i = 0; i < ProjectManager.GlueProjectSave.Entities.Count; i++)
                {
                    EntitySave entitySave = ProjectManager.GlueProjectSave.Entities[i];

                    string entityNamespace = FileManager.MakeRelative(FileManager.GetDirectory(entitySave.Name)).Replace('/', '.');
                    entityNamespace = ProjectManager.ProjectNamespace + "." + entityNamespace.Substring(0, entityNamespace.Length - 1);

                    if (!usingStrings.Contains(entityNamespace))
                    {
                        usingStrings.Add(entityNamespace);
                    }
                }



                for (int i = 0; i < ProjectManager.GlueProjectSave.Entities.Count; i++)
                {
                    if (ProjectManager.GlueProjectSave.Entities[i].CreatedByOtherEntities)
                    {
                        usingStrings.Add(ProjectManager.ProjectNamespace + ".Factories");
                        break;
                    }
                }
            }

            #endregion

            usingStrings.Add("FlatRedBall");
            usingStrings.Add("FlatRedBall.Screens");

            usingStrings.Add("System");
            usingStrings.Add("System.Collections.Generic");
            usingStrings.Add("System.Text");

            bool shouldAddUsingForDataTypes = false;

            for (int i = 0; i < SaveObject.ReferencedFiles.Count; i++)
            {
                if (FileManager.GetExtension(SaveObject.ReferencedFiles[i].Name) == "csv")
                {
                    shouldAddUsingForDataTypes = true;
                    break;
                }
            }

            if (shouldAddUsingForDataTypes)
            {
                usingStrings.Add(ProjectManager.ProjectNamespace + ".DataTypes");
                usingStrings.Add("FlatRedBall.IO.Csv");
            }

            NamedObjectSaveCodeGenerator.AddUsingsForNamedObjects(usingStrings, SaveObject);

            if (ObjectFinder.Self.GlueProject.UsesTranslation)
            {
                usingStrings.Add("FlatRedBall.Localization");
            }

            // Plugins don't generate using statements.
            // This is intentional so we don't get naming conflicts

            // Remove duplicates
            StringFunctions.RemoveDuplicates(usingStrings);

            foreach (string s in usingStrings.Distinct())
            {
                codeBlock.Line("using " + s + ";");
            }
        }
Exemple #32
0
        private void GenerateGetCurrentValuesOnStateForCategory(ICodeBlock currentBlock, ElementSave container, string categoryName, List <Gum.DataTypes.Variables.StateSave> states, bool addValues = false)
        {
            string methodName = "GetCurrentValuesOnState";

            if (addValues)
            {
                methodName = "AddToCurrentValuesWithState";
            }

            currentBlock = currentBlock.Function("private Gum.DataTypes.Variables.StateSave", methodName, categoryName + " state");

            currentBlock.Line("Gum.DataTypes.Variables.StateSave newState = new Gum.DataTypes.Variables.StateSave();");

            var switchBlock = currentBlock.Switch("state");

            {
                foreach (var state in states)
                {
                    var caseBlock = switchBlock.Case(categoryName + "." + state.MemberNameInCode());
                    {
                        foreach (var variable in state.Variables.Where(item => GetIfShouldGenerateStateVariable(item, container)))
                        {
                            string memberNameInCode = variable.MemberNameInCode(container, VariableNamesToReplaceForStates);

                            caseBlock.Line("newState.Variables.Add(new Gum.DataTypes.Variables.VariableSave()");
                            var instantiatorBlock = caseBlock.Block();
                            {
                                instantiatorBlock.Line("SetsValue = true,");

                                // Don't use memberNameInCode - states from the XML files will not, and we want this
                                // to behave the same so merging (used in interpolation) works properly
                                //instantiatorBlock.Line("Name = \"" + memberNameInCode + "\",");
                                instantiatorBlock.Line("Name = \"" + variable.Name + "\",");

                                instantiatorBlock.Line($"Type = \"{variable.Type}\",");

                                string valueString = "Value = " + memberNameInCode + "";


                                if (addValues && IsVariableNumeric(variable))
                                {
                                    string variableValue = variable.Value.ToString();
                                    bool   isEntireAssignment;
                                    GueDerivingClassCodeGenerator.Self.AdjustVariableValueIfNecessary(variable, container, ref variableValue, out isEntireAssignment);

                                    if (isEntireAssignment)
                                    {
                                        valueString = variableValue;
                                    }
                                    else
                                    {
                                        valueString += " + " + variableValue;
                                    }
                                }
                                instantiatorBlock.Line(valueString);
                            }
                            caseBlock.Line(");");
                        }
                    }
                }
            }

            currentBlock.Line("return newState;");
        }
Exemple #33
0
        private void GenerateBorderOutline(NamedObjectSave namedObjectSave, ICodeBlock codeBlock)
        {
            T Get <T>(string name)
            {
                return(namedObjectSave.Properties.GetValue <T>(name));
            }

            var tileSize       = Get <float>(nameof(TileShapeCollectionPropertiesViewModel.CollisionTileSize));
            var tileSizeString = tileSize.ToString(CultureInfo.InvariantCulture) + "f";

            var leftFill       = Get <float>(nameof(TileShapeCollectionPropertiesViewModel.CollisionFillLeft));
            var leftFillString = leftFill.ToString(CultureInfo.InvariantCulture) + "f";

            var topFill       = Get <float>(nameof(TileShapeCollectionPropertiesViewModel.CollisionFillTop));
            var topFillString = topFill.ToString(CultureInfo.InvariantCulture) + "f";

            var widthFill  = Get <int>(nameof(TileShapeCollectionPropertiesViewModel.CollisionFillWidth));
            var heightFill = Get <int>(nameof(TileShapeCollectionPropertiesViewModel.CollisionFillHeight));

            var remainderX = leftFill % tileSize;
            var remainderY = topFill % tileSize;

            var instanceName = namedObjectSave.FieldName;

            codeBlock.Line($"{instanceName}.GridSize = {tileSizeString};");
            //TileShapeCollectionInstance.GridSize = gridSize;

            codeBlock.Line($"{instanceName}.LeftSeedX = {remainderX.ToString(CultureInfo.InvariantCulture)};");
            codeBlock.Line($"{instanceName}.BottomSeedY = {remainderY.ToString(CultureInfo.InvariantCulture)};");

            codeBlock.Line($"{instanceName}.SortAxis = FlatRedBall.Math.Axis.X;");
            //TileShapeCollectionInstance.SortAxis = FlatRedBall.Math.Axis.X;

            var xFor = codeBlock.For($"int x = 0; x < {widthFill}; x++");
            //int(int x = 0; x < width; x++)
            //{
            var ifBlock = xFor.If($"x == 0 || x == {widthFill} - 1");
            var yFor    = ifBlock.For($"int y = 0; y < {heightFill}; y++");

            //    for (int y = 0; y < height; y++)
            //    {

            yFor.Line(
                $"{instanceName}.AddCollisionAtWorld(" +
                $"{leftFillString} + x * {tileSize} + {tileSize} / 2.0f," +
                $"{topFillString} - y * {tileSize} - {tileSize} / 2.0f);");
            //        TileShapeCollectionInstance.AddCollisionAtWorld(
            //            left + x * gridSize + gridSize / 2.0f,
            //            top - y * gridSize - gridSize / 2.0f);
            //    }
            //}
            var elseBlock = ifBlock.End().Else();

            elseBlock.Line(
                $"{instanceName}.AddCollisionAtWorld(" +
                $"{leftFillString} + x * {tileSize} + {tileSize} / 2.0f," +
                $"{topFillString} - {tileSize} / 2.0f);");

            elseBlock.Line(
                $"{instanceName}.AddCollisionAtWorld(" +
                $"{leftFillString} + x * {tileSize} + {tileSize} / 2.0f," +
                $"{topFillString} - {heightFill - 1} * {tileSize} - {tileSize} / 2.0f);");
        }
Exemple #34
0
        private void GenerateCodeFor(NamedObjectSave namedObjectSave, ICodeBlock codeBlock)
        {
            if (namedObjectSave.DefinedByBase == false)
            {
                // don't generate if it's defined by base, the base class defines the properties
                // for now. Maybe eventually derived classes can override or change the behavior?
                // Not sure, that definitely does not seem like standard behavior, so maybe we leave
                // it to codegen.

                var sourceName = namedObjectSave.SourceNameWithoutParenthesis;

                T Get <T>(string name)
                {
                    return(namedObjectSave.Properties.GetValue <T>(name));
                }

                var creationOptions = Get <CollisionCreationOptions>(
                    nameof(TileShapeCollectionPropertiesViewModel.CollisionCreationOptions));

                var sourceType = namedObjectSave.SourceType;

                if (sourceType == SourceType.File)
                {
                    codeBlock.Line($"//The NamedObject {namedObjectSave} has a SourceType of {sourceType}, so it may not instantiate " +
                                   $"properly. If you are experiencing a NullReferenceException, consider changing the" +
                                   $"SourceType to {SourceType.FlatRedBallType}");
                }

                var isVisible = namedObjectSave.GetCustomVariable("Visible")?.ValueAsBool == true;

                if (!isVisible)
                {
                    codeBlock.Line("// normally we wait to set variables until after the object is created, but in this case if the");
                    codeBlock.Line("// TileShapeCollection doesn't have its Visible set before creating the tiles, it can result in");
                    codeBlock.Line("// really bad performance issues, as shapes will be made visible, then invisible. Really bad perf!");
                    codeBlock.Line($"{namedObjectSave.InstanceName}.Visible = false;");
                }

                switch (creationOptions)
                {
                case CollisionCreationOptions.Empty:
                    // do nothing
                    break;

                case CollisionCreationOptions.FillCompletely:
                    GenerateFillCompletely(namedObjectSave, codeBlock);
                    break;

                case CollisionCreationOptions.BorderOutline:
                    GenerateBorderOutline(namedObjectSave, codeBlock);
                    break;

                case CollisionCreationOptions.FromLayer:
                    // not handled:
                    GenerateFromLayerCollision(namedObjectSave, codeBlock);
                    break;

                case CollisionCreationOptions.FromProperties:
                    GenerateFromProperties(namedObjectSave, codeBlock);
                    break;

                case CollisionCreationOptions.FromType:
                    GenerateFromTileType(namedObjectSave, codeBlock);
                    break;
                }
            }
        }
 private void GeneratePartialMethods(ElementSave elementSave, ICodeBlock currentBlock)
 {
     currentBlock.Line("partial void CustomInitialize();");
 }
        private void CreateInstructionForInterpolationRelative(StateCodeGeneratorContext context, ICodeBlock currentBlock, AnimatedStateSave previousState, AnimatedStateSave currentState)
        {
            if (previousState != null)
            {
                currentBlock.Line("var toReturn = new FlatRedBall.Instructions.DelegateInstruction(() =>");
                {
                    currentBlock = currentBlock.Block();

                    // Is the start clone necessary?
                    currentBlock.Line("var relativeStart = ElementSave.AllStates.FirstOrDefault(item => item.Name == \"" + previousState.StateName + "\").Clone();");
                    currentBlock.Line("var relativeEnd = ElementSave.AllStates.FirstOrDefault(item => item.Name == \"" + currentState.StateName + "\").Clone();");
                    currentBlock.Line("Gum.DataTypes.Variables.StateSaveExtensionMethods.SubtractFromThis(relativeEnd, relativeStart);");
                    currentBlock.Line("var difference = relativeEnd;");

                    string categoryName = "VariableState";
                    var    category     = context.Element.Categories.FirstOrDefault(item => item.States.Any(stateCandidate => stateCandidate.Name == currentState.StateName));

                    string enumValue = currentState.StateName;

                    if (currentState.StateName.Contains('/'))
                    {
                        var split = currentState.StateName.Split('/');

                        category  = context.Element.Categories.FirstOrDefault(item => item.Name == split[0]);
                        enumValue = split[1];
                    }

                    if (category != null)
                    {
                        categoryName = category.Name;
                    }
                    currentBlock.Line("Gum.DataTypes.Variables.StateSave first = GetCurrentValuesOnState(" + categoryName + "." + enumValue + ");");

                    currentBlock.Line("Gum.DataTypes.Variables.StateSave second = first.Clone();");
                    currentBlock.Line("Gum.DataTypes.Variables.StateSaveExtensionMethods.AddIntoThis(second, difference);");


                    string interpolationTime = ToFloatString(currentState.Time - previousState.Time);

                    string easing            = "FlatRedBall.Glue.StateInterpolation.Easing." + previousState.Easing;
                    string interpolationType = "FlatRedBall.Glue.StateInterpolation.InterpolationType." + previousState.InterpolationType;


                    currentBlock.Line(
                        string.Format("FlatRedBall.Glue.StateInterpolation.Tweener tweener = new FlatRedBall.Glue.StateInterpolation.Tweener(from: 0, to: 1, duration: {0}, type: {1}, easing: {2});",
                                      interpolationTime,
                                      interpolationType,
                                      easing));

                    currentBlock.Line("tweener.Owner = this;");

                    currentBlock.Line("tweener.PositionChanged = newPosition => this.InterpolateBetween(first, second, newPosition);");
                    currentBlock.Line("tweener.Start();");
                    currentBlock.Line("StateInterpolationPlugin.TweenerManager.Self.Add(tweener);");


                    currentBlock = currentBlock.End();
                }
                currentBlock.Line(");");
                string previousStateTime = ToFloatString(previousState.Time);

                currentBlock.Line("toReturn.TimeToExecute = FlatRedBall.TimeManager.CurrentTime + " + previousStateTime + ";");
                currentBlock.Line("toReturn.Target = target;");

                currentBlock.Line("yield return toReturn;");
            }
        }
        private void GenerateGetEnumerableFor(StateCodeGeneratorContext context, ICodeBlock currentBlock, AnimationSave animation, AbsoluteOrRelative absoluteOrRelative)
        {
            string animationType = "VariableState";

            string animationName = animation.PropertyNameInCode();

            if (absoluteOrRelative == AbsoluteOrRelative.Relative)
            {
                animationName += "Relative";
            }

            string propertyName = animationName + "Instructions";

            // Instructions used to be public - the user would grab them and add them to the InstructionManager,
            // but now everything is encased in an Animation object which handles stopping itself and provides a simple
            // Play method.

            const string signature = "private System.Collections.Generic.IEnumerable<FlatRedBall.Instructions.Instruction>";

            if (animation.States.Count == 0 && animation.Animations.Count == 0)
            {
                currentBlock = currentBlock.Function(signature, propertyName, "object target");

                currentBlock.Line("yield break;");
            }
            else if (absoluteOrRelative == AbsoluteOrRelative.Relative && animation.States.Count < 2 && animation.Animations.Count == 0)
            {
                currentBlock = currentBlock.Function(signature, propertyName, "object target");

                currentBlock.Line("yield break;");
            }
            else
            {
                if (animation.States.Count != 0)
                {
                    var firstState = context.Element.AllStates.FirstOrDefault(item => item.Name == animation.States.First().StateName);

                    var category = context.Element.Categories.FirstOrDefault(item => item.States.Contains(firstState));

                    if (category != null)
                    {
                        animationType = category.Name;
                    }
                }

                currentBlock = currentBlock.Function(signature, propertyName, "object target");

                GenerateOrderedStateAndSubAnimationCode(context, currentBlock, animation, animationType, absoluteOrRelative);

                if (animation.Loops)
                {
                    currentBlock = currentBlock.Block();

                    currentBlock.Line("var toReturn = new FlatRedBall.Instructions.DelegateInstruction(  " +
                                      "() => FlatRedBall.Instructions.InstructionManager.Instructions.AddRange(this." + propertyName + "(target)));");
                    string executionTime = "0.0f";

                    if (animation.States.Count != 0)
                    {
                        executionTime = ToFloatString(animation.States.Last().Time);
                    }

                    currentBlock.Line("toReturn.TimeToExecute = FlatRedBall.TimeManager.CurrentTime + " + executionTime + ";");
                    currentBlock.Line("toReturn.Target = target;");

                    currentBlock.Line("yield return toReturn;");
                    currentBlock = currentBlock.End();
                }
            }
        }
        private void CreateInstructionForInterpolationAbsolute(StateCodeGeneratorContext context, ICodeBlock currentBlock, string animationType, AnimatedStateSave previousState, AnimatedStateSave currentState, string animationName)
        {
            if (previousState == null)
            {
                string variableStateName = null;

                variableStateName = "CurrentVariableState";

                if (currentState.StateName.Contains("/"))
                {
                    var split = currentState.StateName.Split('/');
                    animationType = split[0];
                }

                if (animationType != "VariableState")
                {
                    variableStateName = "Current" + animationType + "State";
                }

                // todo:  Change this on categories
                //System.Action action = () => this.CurrentState = fromState;

                string enumValue = currentState.StateName;
                if (enumValue.Contains("/"))
                {
                    enumValue = enumValue.Split('/')[1];
                }

                currentBlock.Line("var toReturn = new FlatRedBall.Instructions.DelegateInstruction( ()=> this." + variableStateName + " = " +
                                  animationType + "." + enumValue + ");");
                currentBlock.Line("toReturn.TimeToExecute = FlatRedBall.TimeManager.CurrentTime;");
                currentBlock.Line("toReturn.Target = target;");
            }
            else
            {
                var previousCategory = context.Element.Categories.FirstOrDefault(item => item.States.Any(stateCandiate => stateCandiate.Name == previousState.StateName));
                var currentCategory  = context.Element.Categories.FirstOrDefault(item => item.States.Any(stateCandiate => stateCandiate.Name == currentState.StateName));

                // Now that we interpolateTo a single state, we don't
                // need to pass in the StateSave object:
                //bool differentCategories = previousCategory != currentCategory;

                // November 3, 2015
                // Gum uses a "cumulative
                // state" system, so that each
                // keyframe in an animation will
                // tween with variables both before
                // and after.
                // The code as of the time of the writing
                // of this comment does InterpolateBetween
                // two states, which does not consider the state
                // of the object and only tweens variables common
                // to the two states. This makes the runtime behave
                // different than Glue, and it also makes the runtime
                // behave in confusing ways as authors don't often think
                // about the individual variables that may be set in a state.
                // We can solve this by instead doing Interpolate to between the
                // current state of the instance and the state that we are interpolating
                // to. Going to accomplish this by getting rid of the "from" state:
                //string fromState = null;

                string toState = null;

                string enumValue = currentState.StateName;
                if (currentState.StateName.Contains("/"))
                {
                    currentCategory = context.Element.Categories.FirstOrDefault(item => item.Name == currentState.StateName.Split('/')[0]);
                    enumValue       = currentState.StateName.Split('/')[1];
                }


                //if (differentCategories)
                //{
                //fromState = "this.ElementSave.AllStates.FirstOrDefault(item => item.Name == \"" + previousState.StateName + "\")";
                //toState = "this.ElementSave.AllStates.FirstOrDefault(item => item.Name == \"" + currentState.StateName + "\")";
                //}
                //else
                //{
                //fromState = animationType + "." + previousState.StateName;
                if (currentCategory == null)
                {
                    toState = "VariableState." + enumValue;
                }
                else
                {
                    toState = currentCategory.Name + "." + enumValue;
                }
                //}

                string previousStateTime = ToFloatString(previousState.Time);

                string interpolationTime = ToFloatString(currentState.Time - previousState.Time);

                string easing            = "FlatRedBall.Glue.StateInterpolation.Easing." + previousState.Easing;
                string interpolationType = "FlatRedBall.Glue.StateInterpolation.InterpolationType." + previousState.InterpolationType;

                var line = "var toReturn = new FlatRedBall.Instructions.DelegateInstruction(  () => this.InterpolateTo(" +
                           string.Format("{0}, {1}, {2}, {3}, {4}));", toState, interpolationTime, interpolationType, easing, animationName);

                currentBlock.Line(line);
                currentBlock.Line("toReturn.Target = target;");
                currentBlock.Line("toReturn.TimeToExecute = FlatRedBall.TimeManager.CurrentTime + " + previousStateTime + ";");
            }
            currentBlock.Line("yield return toReturn;");
            //System.Action action = () => this.InterpolateTo(fromState, toState, timeToTake, interpolationType, easing);
        }
        private void GenerateAnimationMember(StateCodeGeneratorContext context, ICodeBlock currentBlock, AnimationSave animation, AbsoluteOrRelative absoluteOrRelative)
        {
            string propertyName = animation.PropertyNameInCode();

            if (absoluteOrRelative == AbsoluteOrRelative.Relative)
            {
                propertyName += "Relative";
            }
            string referencedInstructionProperty = propertyName + "Instructions";
            // Force the property to be upper-case, since the field is lower-case:



            // We want to generate something like:
            //private FlatRedBall.Gum.Animation.GumAnimation uncategorizedAnimation;
            //public FlatRedBall.Gum.Animation.GumAnimation UncategorizedAnimation
            //{
            //    get
            //    {
            //        if (uncategorizedAnimation == null)
            //        {
            //            uncategorizedAnimation = new FlatRedBall.Gum.Animation.GumAnimation(1, () => UncategorizedAnimationInstructions);
            //            uncategorizedAnimation.AddEvent("Event1", 3.0f);
            //        }
            //        return uncategorizedAnimation;
            //    }
            //}

            var firstCharacterLower = propertyName.Substring(0, 1).ToLowerInvariant();
            var fieldName           = firstCharacterLower + propertyName.Substring(1);


            currentBlock.Line($"private FlatRedBall.Gum.Animation.GumAnimation {fieldName};");

            currentBlock = currentBlock.Property("public FlatRedBall.Gum.Animation.GumAnimation", propertyName).Get();



            float length = GetAnimationLength(context.Element, animation);

            string lengthAsString = ToFloatString(length);

            var ifBlock = currentBlock.If($"{fieldName} == null");

            {
                ifBlock.Line(
                    $"{fieldName} = new FlatRedBall.Gum.Animation.GumAnimation({lengthAsString}, {referencedInstructionProperty});");

                foreach (var namedEvent in animation.Events)
                {
                    string timeAsString = ToFloatString(namedEvent.Time);
                    ifBlock.Line(
                        $"{fieldName}.AddEvent(\"{namedEvent.Name}\", {timeAsString});");
                }
                foreach (var subAnimation in animation.Animations)
                {
                    if (string.IsNullOrEmpty(subAnimation.SourceObject) == false)
                    {
                        ifBlock.Line($"{fieldName}.SubAnimations.Add({subAnimation.PropertyNameInCode()});");
                    }
                }
            }

            currentBlock.Line($"return {fieldName};");
        }
Exemple #40
0
        private static bool GenerateLoadAsyncCode(ICodeBlock classLevelBlock, ICodeBlock initializeBlock)
        {
            bool loadAsync = ProjectManager.GlueProjectSave.GlobalContentSettingsSave.LoadAsynchronously;

            if (loadAsync)
            {
                GenerateInitializeAsync(initializeBlock);
            }

            loadAsync = ProjectManager.GlueProjectSave.GlobalContentSettingsSave.LoadAsynchronously;
            if (loadAsync)
            {
                classLevelBlock._();


                classLevelBlock.Line("#if !REQUIRES_PRIMARY_THREAD_LOADING");

                classLevelBlock
                .Function("static void", "RequestContentLoad", "string contentName")
                .Lock("LoadMethodList")
                .Line("int index = -1;")
                .For("int i = 0; i < LoadMethodList.Count; i++")
                .If("LoadMethodList[i].Name == contentName")
                .Line("index = i;")
                .Line("break;")
                .End()
                .End()
                .If("index != -1")
                .Line("NamedDelegate delegateToShuffle = LoadMethodList[index];")
                .Line("LoadMethodList.RemoveAt(index);")
                .Line("LoadMethodList.Insert(0, delegateToShuffle);")
                .End()
                .End()
                .End();
                classLevelBlock.Line("#endif");

                classLevelBlock._();

                classLevelBlock.Line("#if !REQUIRES_PRIMARY_THREAD_LOADING");
                classLevelBlock
                .Function("static void", "AsyncInitialize", "")

                .Line("#if XBOX360")
                .Line("// We can not use threads 0 or 2")
                .Line("// Async screen loading uses thread 4, so we'll use 3 here")
                .Line("Thread.CurrentThread.SetProcessorAffinity(3);")
                .Line("#endif")

                .Line("bool shouldLoop = LoadMethodList.Count != 0;")

                .While("shouldLoop")
                .Line("System.Action action = null;")
                .Lock("LoadMethodList")

                .Line("action = LoadMethodList[0].LoadMethod;")
                .Line("LoadMethodList.RemoveAt(0);")
                .Line("shouldLoop = LoadMethodList.Count != 0 && !ShouldStopLoading;")

                .End()
                .Line("action();")
                .End()
                .Line("IsInitialized = true;")
                ._()
                .End();
                classLevelBlock.Line("#endif");

                //stringBuilder.AppendLine("\t\t\tstring ContentManagerName = \"Global\";");
            }

            return(loadAsync);
        }
        private static ICodeBlock GenerateCurrentStateProperty(IElement element, ICodeBlock codeBlock, string enumType, List <StateSave> states)
        {
            var createField = false;

            if (enumType == "VariableState" && !DoesBaseHaveUncategorizedStates(element))  //Uncategorized and not base
            {
                createField = true;
            }
            else if (enumType != "VariableState")    //Check if this state category exists in a parent entity
            {
                if (element.BaseElement != null)
                {
                    var categories = GetAllStateCategoryNames(ObjectFinder.Self.GetIElement(element.BaseElement), true);

                    if (!categories.Any(category => category == enumType))
                    {
                        createField = true;
                    }
                }
                else
                {
                    createField = true;
                }
            }

            string variableNameModifier = enumType;

            if (enumType == "VariableState")
            {
                variableNameModifier = "";
            }

            string qualifiedEnumType = element.Name.Replace("\\", ".").Replace("/", ".") + "." + enumType;

            if (states.Count != 0)
            {
                string         variableToLookFor = "Current" + variableNameModifier + "State";
                CustomVariable customVariable    = element.GetCustomVariable(variableToLookFor);
                bool           hasEvent          = customVariable != null && customVariable.CreatesEvent;


                #region Header and Getter stuff - simple stuff with no logic

                if (createField)
                {
                    codeBlock
                    .Line(string.Format("protected int mCurrent{0}State = 0;", variableNameModifier));
                }

                string publicWithOptionalNew = "public";
                if (ShouldUseNewKeyword(element, enumType))
                {
                    publicWithOptionalNew += " new";
                }
                var setBlock = codeBlock
                               .Property(publicWithOptionalNew + " " + qualifiedEnumType, "Current" + variableNameModifier + "State")
                               .Get()
                               .If(string.Format("System.Enum.IsDefined(typeof({0}), mCurrent{1}State)", enumType, variableNameModifier))
                               .Line(string.Format("return ({0})mCurrent{1}State;", enumType, variableNameModifier))
                               .End()
                               .Else()
                               .Line(string.Format("return {0}.Unknown;", enumType))
                               .End()
                               .End()
                               .Set();

                #endregion

                #region Set the state value and call an event if necessary

                bool stillNeedsToAssignValue = true;

                if (element is EntitySave)
                {
                    EntitySave asEntitySave = element as EntitySave;

                    //if (!string.IsNullOrEmpty(asEntitySave.CurrentStateChange))
                    //{
                    //    setBlock
                    //        .If("value != mCurrent" + variableNameModifier + "State")
                    //            .Line("mCurrent" + variableNameModifier + "State = value;")
                    //            .Line(asEntitySave.CurrentStateChange + "(this, null);");

                    //    stillNeedsToAssignValue = false;
                    //}
                }

                if (hasEvent)
                {
                    EventCodeGenerator.GenerateEventRaisingCode(setBlock, BeforeOrAfter.Before, variableToLookFor, element);
                }

                if (stillNeedsToAssignValue)
                {
                    setBlock.Line("mCurrent" + variableNameModifier + "State = (int)value;");
                }

                #endregion

                var switchBlock = setBlock.Switch("Current" + variableNameModifier + "State");

                switchBlock.Case(enumType + ".Uninitialized");
                switchBlock.Case(enumType + ".Unknown");

                foreach (StateSave stateSave in states)
                {
                    GenerateCurrentStateCodeForIndividualState(element, switchBlock, stateSave, enumType);
                }

                if ((enumType == "VariableState" && DoesBaseHaveUncategorizedStates(element)) ||
                    (!string.IsNullOrEmpty(element.BaseElement) && GetAllStateCategoryNames(ObjectFinder.Self.GetIElement(element.BaseElement), true).Any(category => category == enumType)))
                {
                    switchBlock.Default()
                    .Line("base.Current" + variableNameModifier + "State = base.Current" + variableNameModifier + "State;");
                }

                if (hasEvent)
                {
                    EventCodeGenerator.GenerateEventRaisingCode(setBlock, BeforeOrAfter.After, variableToLookFor, element);
                }
            }
            return(codeBlock);
        }
 private void GenerateSpriteVariableUpdateDependenciesFor(ICodeBlock codeBlock, string name, List <string> managementValues)
 {
     // Even if the sprite is performing its attachments it needs to be manually updated
     codeBlock.Line($"FlatRedBall.SpriteManager.ManualUpdate({name});");
 }
Exemple #43
0
        private static void GenerateInitializeAsync(ICodeBlock currentBlock)
        {
            currentBlock.Line("#if !REQUIRES_PRIMARY_THREAD_LOADING");
            currentBlock.Line("NamedDelegate namedDelegate = new NamedDelegate();");

            foreach (ReferencedFileSave rfs in ProjectManager.GlueProjectSave.GlobalFiles)
            {
                if (!IsRfsHighPriority(rfs) && !rfs.LoadedOnlyWhenReferenced && rfs.LoadedAtRuntime)
                {
                    currentBlock.Line("namedDelegate.Name = \"" + rfs.Name + "\";");
                    currentBlock.Line("namedDelegate.LoadMethod = Load" + rfs.Name.Replace("/", "_").Replace(".", "_") + ";");
                    currentBlock.Line("LoadMethodList.Add( namedDelegate );");
                }
            }

            currentBlock._();

            currentBlock.Line("#if WINDOWS_8");
            currentBlock.Line("System.Threading.Tasks.Task.Run((System.Action)AsyncInitialize);");
            currentBlock.Line("#else");

            currentBlock.Line("ThreadStart threadStart = new ThreadStart(AsyncInitialize);");
            currentBlock.Line("Thread thread = new Thread(threadStart);");
            currentBlock.Line("thread.Name = \"GlobalContent Async load\";");
            currentBlock.Line("thread.Start();");
            currentBlock.Line("#endif");
            currentBlock.Line("#endif");
        }
        public override ICodeBlock GenerateAdditionalMethods(ICodeBlock codeBlock, IElement element)
        {
            ///////////////////Early Out///////////////////////////////
            if (!GetIfIsTopDown(element))
            {
                return(codeBlock);
            }
            /////////////////End Early Out/////////////////////////////

            codeBlock.Line(
                @"
        #region Top-Down Methods
        /// <summary>
        /// Sets the MovementInput to either the keyboard or 
        /// Xbox360GamePad index 0. This can be overridden by base classes to default
        /// to different input devices.
        /// </summary>
        protected virtual void InitializeInput()
        {
            if (FlatRedBall.Input.InputManager.Xbox360GamePads[0].IsConnected)
            {
                InitializeTopDownInput(FlatRedBall.Input.InputManager.Xbox360GamePads[0]);
            }
            else
            {
                InitializeTopDownInput(FlatRedBall.Input.InputManager.Keyboard);
            }
        
            InputEnabled = true;
        }
        

        public void InitializeTopDownInput(FlatRedBall.Input.IInputDevice inputDevice)
        {
            this.MovementInput = inputDevice.Default2DInput;
            this.InputDevice = inputDevice;
            InputEnabled = true;

            CustomInitializeTopDownInput();
        }

        partial void CustomInitializeTopDownInput();

        private void ApplyMovementInput()
        {
            ////////early out/////////
            if(mCurrentMovement == null)
            {
                return;
            }
            //////end early out

            var velocity = this.Velocity;

            var desiredVelocity = Microsoft.Xna.Framework.Vector3.Zero;

            if(InputEnabled)
            {
                desiredVelocity = new Microsoft.Xna.Framework.Vector3(MovementInput.X, MovementInput.Y, velocity.Z) * 
                    mCurrentMovement.MaxSpeed * TopDownSpeedMultiplier;
            }

            var difference = desiredVelocity - velocity;

            Acceleration = Microsoft.Xna.Framework.Vector3.Zero;

            var differenceLength = difference.Length();

            const float differenceEpsilon = .1f;

            if (differenceLength > differenceEpsilon)
            {
                var isMoving = velocity.X != 0 || velocity.Y != 0;
                var isDesiredVelocityNonZero = desiredVelocity.X != 0 || desiredVelocity.Y != 0;

                // A 0 to 1 ratio of acceleration to deceleration, where 1 means the player is accelerating completely,
                // and 0 means decelerating completely. This value will often be between 0 and 1 because the player may
                // set desired velocity perpendicular to the current velocity
                float accelerationRatio = 1;
                if(isMoving && isDesiredVelocityNonZero == false)
                {
                    // slowing down completely
                    accelerationRatio = 0;
                }
                else if(isMoving == false && isDesiredVelocityNonZero)
                {
                    accelerationRatio = 1;
                }
                else
                {
                    // both is moving and has a non-zero desired value
                    var movementAngle = (float)Math.Atan2(velocity.Y, velocity.X);
                    var desiredAngle = (float)Math.Atan2(difference.Y, difference.X);

                    accelerationRatio = 1-
                        Math.Abs(FlatRedBall.Math.MathFunctions.AngleToAngle(movementAngle, desiredAngle)) / (float)Math.PI;

                }

                var secondsToTake = Microsoft.Xna.Framework.MathHelper.Lerp(
                    mCurrentMovement.DecelerationTime,
                    mCurrentMovement.AccelerationTime,
                    accelerationRatio);

                if(secondsToTake == 0)
                {
                    this.Acceleration = Microsoft.Xna.Framework.Vector3.Zero;
                    this.Velocity = desiredVelocity;
                }
                else
                {
                    var accelerationMagnitude = TopDownSpeedMultiplier * mCurrentMovement.MaxSpeed / secondsToTake;
                
                    var nonNormalizedDifference = difference;
                
                    difference.Normalize();
                
                    var accelerationToSet = accelerationMagnitude * difference;
                    var expectedVelocityToAdd = accelerationToSet * TimeManager.SecondDifference;
                
                    if(expectedVelocityToAdd.Length() > nonNormalizedDifference.Length())
                    {
                        // we will overshoot it, so let's adjust the acceleration accordingly:
                        var ratioOfToAdd = nonNormalizedDifference.Length() / expectedVelocityToAdd.Length();
                        this.Acceleration = accelerationToSet * ratioOfToAdd;
                    }
                    else
                    {
                        this.Acceleration = accelerationToSet;
                    }
                }

                const float velocityEpsilon = .1f;
                var shouldAssignDirection = this.Velocity.Length() > velocityEpsilon || difference.Length() > 0;
                // player stopped moving, don't apply direction
                if(this.Velocity.LengthSquared() == 0)
                {
                    shouldAssignDirection = false;
                }

                if (shouldAssignDirection && mCurrentMovement.UpdateDirectionFromVelocity)
                {
                    mDirectionFacing = TopDownDirectionExtensions.FromDirection(XVelocity, YVelocity, PossibleDirections);
                }
            }
            else
            {
                Velocity = desiredVelocity;
                Acceleration = Microsoft.Xna.Framework.Vector3.Zero;
            }

        }

        #endregion

");

            return(codeBlock);
        }
Exemple #45
0
        public override ICodeBlock GenerateAdditionalMethods(ICodeBlock codeBlock, IElement element)
        {
            if (IsLoadingScreen(element))
            {
                codeBlock
                .Line("static string mNextScreenToLoad;")
                .Property("public static string", "NextScreenToLoad")
                .Get()
                .Line("return mNextScreenToLoad;")
                .End()
                .Set()
                .Line("mNextScreenToLoad = value;")
                .End()
                .End();


                string screenName =
                    FileManager.RemovePath(element.Name);



                codeBlock
                .Function("public static void", "TransitionToScreen", "System.Type screenType, System.Action<FlatRedBall.Screens.Screen> screenCreatedCallback = null")
                .Line("TransitionToScreen(screenType.FullName, screenCreatedCallback);")
                .End();


                codeBlock
                .Function("public static void", "TransitionToScreen", "string screenName, System.Action<FlatRedBall.Screens.Screen> screenCreatedCallback = null")
                .Line("Screen currentScreen = ScreenManager.CurrentScreen;")
                .Line("currentScreen.IsActivityFinished = true;")
                .Line("currentScreen.NextScreen = typeof(" + screenName + ").FullName;")
                .Line("mNextScreenToLoad = screenName;")
                .Line("nextCallback = screenCreatedCallback;")
                .End();


                codeBlock
                .Function("void", "AsyncActivity", "")
                .Switch("AsyncLoadingState")
                .Case("FlatRedBall.Screens.AsyncLoadingState.NotStarted")
                .If("!string.IsNullOrEmpty(mNextScreenToLoad)")
                .Line("#if REQUIRES_PRIMARY_THREAD_LOADING")
                .If("HasDrawBeenCalled")
                .Line("MoveToScreen(mNextScreenToLoad);")
                .End()
                .Line("#else")
                .Line("StartAsyncLoad(mNextScreenToLoad);")
                .Line("#endif")
                .End()
                .End()
                .Case("FlatRedBall.Screens.AsyncLoadingState.LoadingScreen")
                .End()
                .Case("FlatRedBall.Screens.AsyncLoadingState.Done")
                // The loading screen can be used to rehydrate.
                .Line("FlatRedBall.Screens.ScreenManager.ShouldActivateScreen = false;")

                .Line("FlatRedBall.Screens.ScreenManager.MoveToScreen(mNextScreenToLoad, nextCallback);")
                .End()
                .End()
                .End();
            }

            return(codeBlock);
        }
        public override ICodeBlock GenerateFields(ICodeBlock codeBlock, IElement element)
        {
            /////////////////Early Out//////////////////////
            if (GetIfIsTopDown(element) == false)
            {
                return(codeBlock);
            }
            //////////////End Early Out//////////////////////
            ///
            codeBlock.Line("#region Top Down Fields");


            codeBlock.Line("DataTypes.TopDownValues mCurrentMovement;");
            codeBlock.Line("public float TopDownSpeedMultiplier { get; set; } = 1;");

            codeBlock.Line("/// <summary>");
            codeBlock.Line("/// The current movement variables used when applying input.");
            codeBlock.Line("/// </summary>");
            codeBlock.Property("public DataTypes.TopDownValues", "CurrentMovement")
            .Get()
            .Line("return mCurrentMovement;");

            codeBlock.Property("public FlatRedBall.Input.IInputDevice", "InputDevice")
            .Line("get;")
            .Line("private set;");

            codeBlock.Line("TopDownDirection mDirectionFacing;");

            codeBlock.Line("/// <summary>");
            codeBlock.Line("/// Which direciton the character is facing.");
            codeBlock.Line("/// </summary>");
            codeBlock.Property("protected TopDownDirection", "DirectionFacing")
            .Get()
            .Line("return mDirectionFacing;");

            codeBlock.Property("public PossibleDirections", "PossibleDirections")
            .AutoGet().End()
            .AutoSet();

            codeBlock.Line("/// <summary>");
            codeBlock.Line("/// The input object which controls the horizontal movement of the character.");
            codeBlock.Line("/// Common examples include a d-pad, analog stick, or keyboard keys.");
            codeBlock.Line("/// </summary>");
            codeBlock.AutoProperty("public FlatRedBall.Input.I2DInput", "MovementInput");

            codeBlock.Line("/// <summary>");
            codeBlock.Line("/// Whether input is read to control the movement of the character.");
            codeBlock.Line("/// This can be turned off if the player should not be able to control");
            codeBlock.Line("/// the character.");
            codeBlock.Line("/// </summary>");
            codeBlock.AutoProperty("public bool", "InputEnabled");

            codeBlock.Line("#endregion");

            return(codeBlock);
        }