Ejemplo n.º 1
0
        protected override void SolveInstance(IGH_DataAccess DA)
        {
            //CONTINUE HERE!!!!
            UpdateTask = new Task <int>(() => Update());

            FlexParams              param       = new FlexParams();
            FlexCollisionGeometry   geom        = new FlexCollisionGeometry();
            List <FlexForceField>   forceFields = new List <FlexForceField>();
            List <FlexScene>        scenes      = new List <FlexScene>();
            List <ConstraintSystem> constraints = new List <ConstraintSystem>();
            FlexSolverOptions       options     = new FlexSolverOptions();
            bool reset = false;

            bool go = false;

            DA.GetData(6, ref reset);
            DA.GetData(7, ref go);

            if (reset)
            {
                //reset everything related to time tracking
                counter           = 0;
                totalTimeMs       = 0;
                totalUpdateTimeMs = 0;
                sw.Stop();
                sw.Reset();

                outInfo = new List <string>();

                //retrieve relevant data
                DA.GetData(0, ref param);
                DA.GetData(1, ref geom);
                DA.GetDataList(2, forceFields);
                DA.GetDataList(3, scenes);
                DA.GetDataList(4, constraints);
                DA.GetData(5, ref options);

                sceneTimeStamps      = new List <int>();
                forceFieldTimeStamps = new List <int>();

                //destroy old Flex instance
                if (flex != null)
                {
                    flex.Destroy();
                }

                //Create new instance and assign everything
                flex = new Flex();

                flex.SetParams(param);
                flex.SetCollisionGeometry(geom);
                flex.SetForceFields(forceFields);
                foreach (FlexForceField f in forceFields)
                {
                    forceFieldTimeStamps.Add(f.TimeStamp);
                }
                FlexScene scene = new FlexScene();
                foreach (FlexScene s in scenes)
                {
                    scene.AppendScene(s);
                    sceneTimeStamps.Add(s.TimeStamp);
                }
                foreach (ConstraintSystem c in constraints)
                {
                    scene.RegisterCustomConstraints(c.AnchorIndices, c.ShapeMatchingIndices, c.ShapeStiffness, c.SpringPairIndices, c.SpringStiffnesses, c.SpringTargetLengths, c.TriangleIndices, c.TriangleNormals);
                    constraintTimeStamps.Add(c.TimeStamp);
                }
                flex.SetScene(scene);
                flex.SetSolverOptions(options);
            }
            else if (go && flex != null && flex.IsReady())
            {
                DA.GetData(5, ref options);
                if (options.TimeStamp != optionsTimeStamp)
                {
                    flex.SetSolverOptions(options);
                }

                if (options.SceneMode == 0 || options.SceneMode == 1)
                {
                    //update params if timestamp expired
                    DA.GetData(0, ref param);
                    if (param.TimeStamp != paramsTimeStamp)
                    {
                        flex.SetParams(param);
                        paramsTimeStamp = param.TimeStamp;
                    }

                    //update geom if timestamp expired
                    if (DA.GetData(1, ref geom))
                    {
                        if (geom.TimeStamp != geomTimeStamp)
                        {
                            flex.SetCollisionGeometry(geom);
                            geomTimeStamp = geom.TimeStamp;
                        }
                    }
                    else if (geom != null)
                    {
                        flex.SetCollisionGeometry(new FlexCollisionGeometry());
                    }

                    //update forcefields where timestamp expired
                    DA.GetDataList(2, forceFields);
                    bool needsUpdate = false;
                    for (int i = forceFieldTimeStamps.Count; i < forceFields.Count; i++)
                    {
                        forceFieldTimeStamps.Add(forceFields[i].TimeStamp);
                        needsUpdate = true;
                    }
                    for (int i = 0; i < forceFields.Count; i++)
                    {
                        if (forceFields[i].TimeStamp != forceFieldTimeStamps[i])
                        {
                            needsUpdate             = true;
                            forceFieldTimeStamps[i] = forceFields[i].TimeStamp;
                        }
                    }
                    if (needsUpdate)
                    {
                        flex.SetForceFields(forceFields);
                    }

                    //update scenes where timestamp expired
                    DA.GetDataList(3, scenes);
                    for (int i = sceneTimeStamps.Count; i < scenes.Count; i++)
                    {
                        sceneTimeStamps.Add(scenes[i].TimeStamp);
                    }
                    for (int i = 0; i < scenes.Count; i++)
                    {
                        if (scenes[i].TimeStamp != sceneTimeStamps[i])
                        {
                            if (options.SceneMode == 0)
                            {
                                flex.SetScene(flex.Scene.AlterScene(scenes[i], false));
                            }
                            else
                            {
                                flex.SetScene(flex.Scene.AppendScene(scenes[i]));
                            }
                            sceneTimeStamps[i] = scenes[i].TimeStamp;
                        }
                    }

                    DA.GetDataList(4, constraints);
                    for (int i = constraintTimeStamps.Count; i < constraints.Count; i++)
                    {
                        constraintTimeStamps.Add(constraints[i].TimeStamp);
                    }
                    for (int i = 0; i < constraints.Count; i++)
                    {
                        ConstraintSystem c = constraints[i];
                        if (c.TimeStamp != constraintTimeStamps[i])
                        {
                            if (!flex.Scene.RegisterCustomConstraints(c.AnchorIndices, c.ShapeMatchingIndices, c.ShapeStiffness, c.SpringPairIndices, c.SpringStiffnesses, c.SpringTargetLengths, c.TriangleIndices, c.TriangleNormals))
                            {
                                AddRuntimeMessage(GH_RuntimeMessageLevel.Warning, "Custom constraint indices exceeded particle count. No constraints applied!");
                            }
                            flex.SetScene(flex.Scene);
                            constraintTimeStamps[i] = constraints[i].TimeStamp;
                        }
                    }
                }

                //Add timing info
                outInfo = new List <string>();
                counter++;
                outInfo.Add(counter.ToString());
                long currentTickTimeMs = sw.ElapsedMilliseconds;
                sw.Restart();
                totalTimeMs += currentTickTimeMs;
                outInfo.Add(totalTimeMs.ToString());
                outInfo.Add(currentTickTimeMs.ToString());
                float avTotalTickTime = ((float)totalTimeMs / (float)counter);
                outInfo.Add(avTotalTickTime.ToString());

                //start update
                UpdateTask.Start();

                //Add solver timing info
                int tickTimeSolver = UpdateTask.Result;
                totalUpdateTimeMs += tickTimeSolver;
                float ratUpdateTime = ((float)totalUpdateTimeMs / (float)counter);
                outInfo.Add(tickTimeSolver.ToString());
                outInfo.Add(ratUpdateTime.ToString());
            }

            if (go && options.FixedTotalIterations < 1)
            {
                ExpireSolution(true);
            }

            else if (flex != null && UpdateTask.Status == TaskStatus.Running)
            {
                UpdateTask.Dispose();
            }

            if (flex != null)
            {
                DA.SetData(0, flex);
            }
            DA.SetDataList(1, outInfo);
        }