public ICompletable <TurtleCompletionResult> CompileStringToTransformsWithMeshIds(
            DependencyTracker <SymbolString <float> > symbols,
            Mesh targetMesh,
            Matrix4x4 localToWorldTransform)
        {
            if (IsDisposed)
            {
                throw new ObjectDisposedException("Turtle has been disposed and cannot be used");
            }

            RefreshVolumetricWriters();
            var volumeWorldReferences = new TurtleVolumeWorldReferences
            {
                world                = volumetricWorld,
                durabilityWriter     = durabilityWriterHandle,
                universalLayerWriter = commandBufferWriter,
                damageFlags          = damageCapFlags,
            };

            return(new TurtleStringReadingCompletable(
                       targetMesh,
                       submeshMaterials.Length,
                       symbols,
                       nativeDataTracker,
                       branchStartChar,
                       branchEndChar,
                       defaultState,
                       customSymbols,
                       volumeWorldReferences,
                       localToWorldTransform
                       ));
        }
Exemple #2
0
        public HelloWorldViewModel()
        {
            firstName = Factory.Backing(nameof(FirstName), "Anton", NotNullOrWhitespace.Then(NotEqual("Foo")));

            lastName = Factory.Backing(
                nameof(LastName),
                "Tcholakov",
                NotNullOrWhitespace.Then(NotEqual("Bar")).Then(x => x.Length < 10, "Length cannot exceed 10 characters"));

            sayHello = Factory.CommandAsyncChecked(
                Greet,
                () => this.IsValid && !this.OperationExecuting,
                cts.Token,
                exn => MessageBox.Show("Sorry I was too slow :-(."),
                nameof(IsValid),
                nameof(OperationExecuting));

            cancelCommand = Factory.CommandSyncChecked(
                () => this.cts?.Cancel(),
                () => this.OperationExecuting,
                nameof(OperationExecuting));

            DependencyTracker.AddPropertyDependencies(nameof(ReadyToGreet), nameof(OperationExecuting));
            DependencyTracker.AddPropertyDependencies(nameof(FullName), nameof(FirstName), nameof(LastName));
            DependencyTracker.AddPropertyDependencies(nameof(Greeting), nameof(FullName));
        }
Exemple #3
0
        public T Get <T>(string key)
        {
            key = key.Replace('/', '.');
            if (cache.TryGetValue(key, out var cachedValue))
            {
                if (cachedValue is T tCachedValue)
                {
                    return(tCachedValue);
                }

                throw new InvalidOperationException($"Value '{key}' is not compatible with the requested type.");
            }

            var valueProvider = TryFindValue(key);

            if (valueProvider == null)
            {
                throw new KeyNotFoundException();
            }

            var tracker = new DependencyTracker(this, key);
            var result  = valueProvider.Get(tracker);

            dependencyMap[key] = tracker.Dependencies;
            if (result is T t)
            {
                cache[key] = t;
                return(t);
            }

            throw new InvalidOperationException($"Value '{key}' is not compatible with the requested type.");
        }
Exemple #4
0
    private void AssertRuleDoesNotMatchCondtitional(
        string ruleText,
        int[] sourceSymbols        = null,
        float[][] sourceParameters = null,
        string axiom = null,
        int ruleParamMemoryStartIndex = 0,
        int matchIndex            = 0,
        int paramTempMemorySize   = 0,
        float[] globalParams      = null,
        string[] globalParamNames = null,
        string includedSymbols    = "[]ABCDE"
        )
    {
        var totalIncluded = new HashSet <int>(includedSymbols.Select(x => (int)x));

        globalParamNames  = globalParamNames ?? new string[0];
        using var symbols = new DependencyTracker <SymbolString <float> >(
                  axiom == null ?
                  new SymbolString <float>(sourceSymbols, sourceParameters)
            : SymbolString <float> .FromString(axiom, Allocator.Persistent)
                  );
        var ruleFromString = new BasicRule(
            RuleParser.ParseToRule(ruleText, x => x, globalParameters: globalParamNames),
            '[', ']');

        using var ruleNativeData = new SystemLevelRuleNativeData(new[] { ruleFromString });
        var nativeWriter = new SymbolSeriesMatcherNativeDataWriter();

        ruleFromString.WriteDataIntoMemory(ruleNativeData, nativeWriter);

        globalParams           = globalParams ?? new float[0];
        using var globalNative = new NativeArray <float>(globalParams, Allocator.Persistent);

        using var paramMemory = new NativeArray <float>(paramTempMemorySize, Allocator.Persistent);
        using var branchCache = new SymbolStringBranchingCache('[', ']', new[] { totalIncluded }, ruleNativeData);
        branchCache.BuildJumpIndexesFromSymbols(symbols);
        var random          = new Unity.Mathematics.Random();
        var matchSingleData = new LSystemSingleSymbolMatchData
        {
            isTrivial = false,
            tmpParameterMemorySpace = JaggedIndexing.GetWithNoLength(ruleParamMemoryStartIndex)
        };

        var potentialMatch = ruleFromString.AsBlittable().PreMatchCapturedParametersWithoutConditional(
            branchCache,
            symbols.Data,
            matchIndex,
            paramMemory,
            matchSingleData.tmpParameterMemorySpace.index,
            ref matchSingleData,
            new TmpNativeStack <SymbolStringBranchingCache.BranchEventData>(5),
            globalNative,
            ruleNativeData.dynamicOperatorMemory,
            ref random,
            ruleNativeData.ruleOutcomeMemorySpace
            );

        Assert.IsFalse(potentialMatch);
    }
 public void FindsBranchForwardLinksCorrectlyWhenBranchingAtSameIndexAsCharacterCodeForBranchingSymbol()
 {
     using var targetString   = new DependencyTracker <SymbolString <float> >(SymbolString <float> .FromString("[&E][&&E]&EEEE[&[EE]E][&&[EE]E]&EEEE[&[EEEE]EE][&&[EEEE]EE]&EEEA[&[EEEEEE]E[E]E[E]][&&[EEEEEE]E[E]E[E]]"));
     using var branchingCache = new SymbolStringBranchingCache('[', ']', new SystemLevelRuleNativeData());
     branchingCache.BuildJumpIndexesFromSymbols(targetString);
     Assert.AreEqual(64, branchingCache.FindOpeningBranchIndexReadonly(82));
     Assert.AreEqual(86, branchingCache.FindOpeningBranchIndexReadonly(93));
 }
Exemple #6
0
        public LSystemStepper(
            IEnumerable <BasicRule> rules,
            SystemLevelRuleNativeData nativeRuleData,
            CustomRuleSymbols customSymbols,
            int expectedGlobalParameters = 0,
            ISet <int>[] includedContextualCharactersByRuleIndex = null)
        {
            GlobalParameters = expectedGlobalParameters;

            this.customSymbols = customSymbols;

            includedCharacters = includedContextualCharactersByRuleIndex == null ? new HashSet <int> [0] : includedContextualCharactersByRuleIndex;

            rulesByTargetSymbol = new Dictionary <int, IList <BasicRule> >();
            foreach (var rule in rules)
            {
                var targetSymbols = rule.TargetSymbol;
                if (!rulesByTargetSymbol.TryGetValue(targetSymbols, out var ruleList))
                {
                    rulesByTargetSymbol[targetSymbols] = ruleList = new List <BasicRule>();
                }
                ruleList.Add(rule);
            }

            var maxMemoryRequirementsPerSymbol = new NativeHashMap <int, MaxMatchMemoryRequirements>(rulesByTargetSymbol.Keys.Count(), Allocator.Persistent);

            foreach (var symbol in rulesByTargetSymbol.Keys.ToList())
            {
                rulesByTargetSymbol[symbol] = rulesByTargetSymbol[symbol]
                                              .OrderByDescending(x =>
                                                                 (x.ContextPrefix.IsValid ? x.ContextPrefix.graphNodeMemSpace.length : 0) +
                                                                 (x.ContextSuffix.IsCreated ? x.ContextSuffix.graphNodeMemSpace.length : 0))
                                              .ToList();

                var maxParamCapturedByAnyRule = rulesByTargetSymbol[symbol]
                                                .Select(x => x.CapturedLocalParameterCount)
                                                .DefaultIfEmpty().Max();
                // Greedy estimate for maximum possible parameter match.
                //  there need to be enough space for any rule's parameters to fit, since we don't know which ones will match.
                var maximumPossibleParameterMatch = maxParamCapturedByAnyRule;
                if (maximumPossibleParameterMatch > ushort.MaxValue)
                {
                    throw new LSystemRuntimeException($"Rules with more than {ushort.MaxValue} captured local parameters over all conditional options");
                }
                maxMemoryRequirementsPerSymbol[symbol] = new MaxMatchMemoryRequirements
                {
                    maxParameters = maximumPossibleParameterMatch
                };
            }

            nativeRuleData.blittableRulesByTargetSymbol = NativeOrderedMultiDictionary <BasicRule.Blittable> .WithMapFunction(
                rulesByTargetSymbol,
                rule => rule.AsBlittable(),
                Allocator.Persistent);

            nativeRuleData.maxParameterMemoryRequirementsPerSymbol = maxMemoryRequirementsPerSymbol;
            this.nativeRuleData = new DependencyTracker <SystemLevelRuleNativeData>(nativeRuleData);
        }
Exemple #7
0
        // The special constructor is used to deserialize values.
        private LSystemState(SerializationInfo info, StreamingContext context)
        {
            currentSymbols = info.GetValue <DependencyTracker <SymbolString <T> > >("currentSymbols");
            randomProvider = new Unity.Mathematics.Random(info.GetUInt32("randomSeed"));

            firstUniqueOrganId = info.GetUInt32("firstUniqueOrganId");
            maxUniqueOrganIds  = info.GetUInt32("maxUniqueOrganIds");
            hasImmatureSymbols = info.GetBoolean("hasImmatureSymbols");
        }
 public void FindsClosingBranchLinks()
 {
     using var targetString   = new DependencyTracker <SymbolString <float> >(SymbolString <float> .FromString("A[AA]AAA[A[AAA[A]]]A"));
     using var branchingCache = new SymbolStringBranchingCache('[', ']', new SystemLevelRuleNativeData());
     branchingCache.BuildJumpIndexesFromSymbols(targetString);
     Assert.AreEqual(4, branchingCache.FindClosingBranchIndexReadonly(1));
     Assert.AreEqual(17, branchingCache.FindClosingBranchIndexReadonly(10));
     Assert.AreEqual(18, branchingCache.FindClosingBranchIndexReadonly(8));
 }
Exemple #9
0
 static OptionsPageViewModel()
 {
     tracker = DependencyTracker.Create <OptionsPageViewModel>(configurator =>
     {
         configurator
         .RaiseProperty(model => model.IsDirty)
         .CalculatedBy(model => true)
         .WhenPropertyChanged(model => model.Delay);
     });
 }
    private void AssertBackwardsMatch(
        string target,
        string matcher,
        bool shouldMatch,
        string includeSymbols              = "[]ABCDEFJ",
        int parameterMemorySize            = 10,
        float[] expectedCapturedParameters = null,
        int indexInTarget = -1)
    {
        var includedSymbolSet = includeSymbols.Select(x => (int)x);

        var prefixBuilder = SymbolSeriesPrefixBuilder.Parse(matcher);

        using var nativeData = new SystemLevelRuleNativeData(new RuleDataRequirements
        {
            prefixNodes = prefixBuilder.RequiredNodeMemorySpace
        });
        var writer = new SymbolSeriesMatcherNativeDataWriter();

        var seriesMatcher = prefixBuilder.BuildIntoManagedMemory(nativeData, writer);

        using var targetString   = new DependencyTracker <SymbolString <float> >(SymbolString <float> .FromString(target));
        using var branchingCache = new SymbolStringBranchingCache(
                  '[', ']',
                  includedSymbolSet == null ? new HashSet <int> [0] : new[] { new HashSet <int>(includedSymbolSet) },
                  nativeData);
        branchingCache.BuildJumpIndexesFromSymbols(targetString);
        using var parameterMemory = new NativeArray <float>(parameterMemorySize, Allocator.Persistent);


        var realIndex  = indexInTarget < 0 ? indexInTarget + targetString.Data.Length : indexInTarget;
        var hasMatched = branchingCache.MatchesBackwards(
            branchingCache.includeSymbols[0],
            realIndex,
            seriesMatcher,
            targetString.Data,
            0,
            parameterMemory,
            out var copiedParams);

        if (shouldMatch != hasMatched)
        {
            Assert.Fail($"Expected '{matcher}' to {(shouldMatch ? "" : "not ")}match backwards from {indexInTarget} in '{target}'");
        }
        if (shouldMatch && expectedCapturedParameters != null)
        {
            Assert.AreEqual(expectedCapturedParameters.Length, copiedParams);
            for (int i = 0; i < expectedCapturedParameters.Length; i++)
            {
                Assert.AreEqual(expectedCapturedParameters[i], parameterMemory[i]);
            }
        }
    }
Exemple #11
0
        static void AssertDependencyExists(DependencyTracker tracker, int key, GameObject dependent)
        {
            var dependents = tracker.GetAllDependents(key);
            int id         = dependent.GetInstanceID();

            while (dependents.MoveNext())
            {
                if (id == dependents.Current)
                {
                    return;
                }
            }
            Assert.Fail("The dependent wasn't registered to the key of the dependency.");
        }
Exemple #12
0
        public LSystemParameterSizeCountingCompletable(
            LSystemState <float> systemState,
            DependencyTracker <SystemLevelRuleNativeData> lSystemNativeData,
            float[] globalParameters,
            ISet <int>[] includedCharactersByRuleIndex,
            CustomRuleSymbols customSymbols,
            JobHandle parameterModificationJobDependency)
        {
            currentJobHandle = default;

            this.globalParameters            = globalParameters;
            this.paramModificationDependency = parameterModificationJobDependency;

            this.systemState   = systemState;
            this.customSymbols = customSymbols;
            nativeData         = lSystemNativeData;

            // 1.
            UnityEngine.Profiling.Profiler.BeginSample("Paramter counts");

            UnityEngine.Profiling.Profiler.BeginSample("allocating");
            matchSingletonData = new NativeArray <LSystemSingleSymbolMatchData>(systemState.currentSymbols.Data.Length, Allocator.Persistent, NativeArrayOptions.UninitializedMemory);
            parameterTotalSum  = new NativeArray <int>(1, Allocator.TempJob);
            UnityEngine.Profiling.Profiler.EndSample();

            var memorySizeJob = new SymbolStringMemoryRequirementsJob
            {
                matchSingletonData          = matchSingletonData,
                memoryRequirementsPerSymbol = nativeData.Data.maxParameterMemoryRequirementsPerSymbol,
                parameterTotalSum           = parameterTotalSum,
                sourceSymbolString          = systemState.currentSymbols.Data
            };

            currentJobHandle = memorySizeJob.Schedule();
            systemState.currentSymbols.RegisterDependencyOnData(currentJobHandle);
            nativeData.RegisterDependencyOnData(currentJobHandle);


            UnityEngine.Profiling.Profiler.EndSample();

            // 2.1
            UnityEngine.Profiling.Profiler.BeginSample("branch cache");
            branchingCache = new SymbolStringBranchingCache(
                customSymbols.branchOpenSymbol,
                customSymbols.branchCloseSymbol,
                includedCharactersByRuleIndex,
                nativeData.Data);
            branchingCache.BuildJumpIndexesFromSymbols(systemState.currentSymbols);
            UnityEngine.Profiling.Profiler.EndSample();
        }
Exemple #13
0
        public void BuildJumpIndexesFromSymbols(DependencyTracker <SymbolString <float> > symbols)
        {
            var tmpBranchingJumpIndexes = new Dictionary <int, int>();

            CacheAllBranchJumpIndexes(symbols.Data.symbols, tmpBranchingJumpIndexes);

            UnityEngine.Profiling.Profiler.BeginSample("allocating");
            branchingJumpIndexes = new NativeHashMap <int, int>(tmpBranchingJumpIndexes.Count, Allocator.Persistent);
            UnityEngine.Profiling.Profiler.EndSample();

            foreach (var kvp in tmpBranchingJumpIndexes)
            {
                branchingJumpIndexes[kvp.Key] = kvp.Value;
            }
        }
        public TurtleMeshBuildingCompletable(
            Mesh targetMesh,
            NativeArray <TurtleMeshAllocationCounter> resultMeshSizeBySubmesh,
            DependencyTracker <NativeTurtleData> nativeData,
            NativeList <TurtleOrganInstance> organInstances)
        {
            if (nativeData.IsDisposed)
            {
                throw new InvalidOperationException("turtle data has been disposed before completable could finish.");
            }

            this.targetMesh = targetMesh;
            targetMesh.MarkDynamic();
            this.resultMeshSizeBySubmesh = resultMeshSizeBySubmesh;
            UnityEngine.Profiling.Profiler.BeginSample("mesh data building job");

            UnityEngine.Profiling.Profiler.BeginSample("allocating");
            var lastSubmeshSize = resultMeshSizeBySubmesh[resultMeshSizeBySubmesh.Length - 1];

            meshData = new MyMeshData
            {
                indices    = new NativeArray <uint>(lastSubmeshSize.indexInTriangles + lastSubmeshSize.totalTriangleIndexes, Allocator.TempJob), // TODO: does this have to be persistent? or can it be tempjob since it'll be handed to the mesh?
                vertexData = new NativeArray <MeshVertexLayout>(lastSubmeshSize.indexInVertexes + lastSubmeshSize.totalVertexes, Allocator.TempJob),
                meshBounds = new NativeArray <Bounds>(1, Allocator.TempJob)
            };

            var turtleEntitySpawnJob = new TurtleMeshBuildingJob
            {
                templateVertexData   = nativeData.Data.vertexData,
                templateTriangleData = nativeData.Data.triangleData,
                templateOrganData    = nativeData.Data.allOrganData,
                submeshSizes         = resultMeshSizeBySubmesh,

                organInstances = organInstances,

                targetMesh = meshData
            };

            UnityEngine.Profiling.Profiler.EndSample();

            UnityEngine.Profiling.Profiler.BeginSample("scheduling");
            currentJobHandle = turtleEntitySpawnJob.Schedule();
            nativeData.RegisterDependencyOnData(currentJobHandle);

            currentJobHandle = organInstances.Dispose(currentJobHandle);
            UnityEngine.Profiling.Profiler.EndSample();
            UnityEngine.Profiling.Profiler.EndSample();
        }
    private void AssertForwardsMatch(
        string target,
        string matcher,
        bool shouldMatch                   = true,
        int indexInTarget                  = 0,
        int parameterMemorySize            = 10,
        float[] expectedCapturedParameters = null,
        string message        = null,
        string includeSymbols = "[]ABCDEFGJKZ")
    {
        var seriesMatcher = SymbolSeriesGraphTests.GenerateSingleMatcher(matcher, out var nativeData);

        using var nativeDataDisposable = nativeData;
        using var targetString         = new DependencyTracker <SymbolString <float> >(SymbolString <float> .FromString(target));
        using var branchingCache       = new SymbolStringBranchingCache(
                  '[', ']',
                  includeSymbols == null ? new HashSet <int> [0] : new[] { new HashSet <int>(includeSymbols.Select(x => (int)x)) },
                  nativeDataDisposable);
        branchingCache.BuildJumpIndexesFromSymbols(targetString);
        using var parameterMemory = new NativeArray <float>(parameterMemorySize, Allocator.Persistent);

        var matches = branchingCache.MatchesForward(
            branchingCache.includeSymbols[0],
            indexInTarget,
            seriesMatcher,
            targetString.Data,
            0,
            parameterMemory,
            out var copiedParams,
            new TmpNativeStack <SymbolStringBranchingCache.BranchEventData>(5));

        if (shouldMatch != matches)
        {
            Assert.Fail($"Expected '{matcher}' to {(shouldMatch ? "" : "not ")}match forwards retaining order from {indexInTarget} in '{target}'{(message == null ? "" : '\n' + message)}");
        }
        if (shouldMatch && expectedCapturedParameters != null)
        {
            Assert.AreEqual(expectedCapturedParameters.Length, copiedParams, "captured parameter length mismatch");
            for (int i = 0; i < expectedCapturedParameters.Length; i++)
            {
                Assert.AreEqual(expectedCapturedParameters[i], parameterMemory[i]);
            }
        }
    }
        public TurtleInterpretor(
            List <TurtleOperationSet> operationSets,
            TurtleState defaultState,
            LinkedFileSet linkedFiles,
            CustomRuleSymbols customSymbols,
            OrganVolumetricWorld volumetricWorld,
            VoxelCapReachedTimestampEffect damageCapFlags,
            char startChar = '[', char endChar = ']')
        {
            foreach (var operationSet in operationSets)
            {
                operationSet.InternalCacheOperations();
            }

            var totalRequirements = operationSets.Select(x => x.DataReqs).Aggregate(new TurtleDataRequirements(), (agg, req) => agg + req);
            var nativeData        = new NativeTurtleData(totalRequirements);
            var nativeWriter      = new TurtleNativeDataWriter();

            foreach (var operationSet in operationSets)
            {
                operationSet.WriteIntoNativeData(nativeData, nativeWriter);
            }

            submeshMaterials = nativeWriter.materialsInOrder.ToArray();

            nativeData.operationsByKey = new NativeHashMap <int, TurtleOperation>(nativeWriter.operators.Count(), Allocator.Persistent);
            foreach (var ops in nativeWriter.operators)
            {
                var realSymbol = linkedFiles.GetSymbolFromRoot(ops.characterInRootFile);
                nativeData.operationsByKey[realSymbol] = ops.operation;
            }

            branchStartChar    = linkedFiles.GetSymbolFromRoot(startChar);
            branchEndChar      = linkedFiles.GetSymbolFromRoot(endChar);
            this.customSymbols = customSymbols;


            nativeDataTracker = new DependencyTracker <NativeTurtleData>(nativeData);
            this.defaultState = defaultState;

            this.volumetricWorld = volumetricWorld;
            this.damageCapFlags  = damageCapFlags;
            RefreshVolumetricWriters();
        }
Exemple #17
0
        internal ConversionDependencies(bool isLiveLink)
        {
            _isLiveLink = isLiveLink;
            if (_isLiveLink)
            {
                GameObjectDependencyTracker       = new DependencyTracker(Allocator.Persistent);
                _componentDependenciesByTypeIndex = new NativeHashMap <int, DependencyTracker>(0, Allocator.Persistent);
                _unresolvedComponentInstanceIds   = new NativeHashSet <int>(0, Allocator.Persistent);
            }
            else
            {
                GameObjectDependencyTracker       = default;
                _componentDependenciesByTypeIndex = default;
                _unresolvedComponentInstanceIds   = default;
            }
#if UNITY_EDITOR
            AssetDependencyTracker = new DependencyTracker(Allocator.Persistent);
#endif
        }
        /// <summary>
        /// iterate through <paramref name="symbols"/> and assign the generated mesh to the attached meshFilter
        /// </summary>
        /// <param name="symbols"></param>
        public ICompletable <TurtleCompletionResult> InterpretSymbols(DependencyTracker <SymbolString <float> > symbols)
        {
            UnityEngine.Profiling.Profiler.BeginSample("Turtle compilation");

            //var createNewOrgansCommandBuffer = World.DefaultGameObjectInjectionWorld.GetOrCreateSystem<EndSimulationEntityCommandBufferSystem>();

            var meshFilter   = GetComponent <MeshFilter>();
            var meshRenderer = GetComponent <MeshRenderer>();
            var dep          = turtle.CompileStringToTransformsWithMeshIds(
                symbols,
                meshFilter.mesh,
                meshFilter.transform.localToWorldMatrix);

            // TOODO: do this oon startup?
            meshRenderer.materials = turtle.submeshMaterials;

            UnityEngine.Profiling.Profiler.EndSample();
            return(dep);
        }
Exemple #19
0
        public bool TryGet <T>(string key, out T result)
        {
            key = key.Replace('/', '.');
            if (cache.TryGetValue(key, out var cachedValue))
            {
                if (cachedValue is T tCachedValue)
                {
                    result = tCachedValue;
                    return(true);
                }

                result = default;
                return(false);
            }

            var valueProvider = TryFindValue(key);

            if (valueProvider == null)
            {
                result = default;
                return(false);
            }

            var tracker = new DependencyTracker(this, key);
            var value   = valueProvider.Get(tracker);

            dependencyMap[key] = tracker.Dependencies;
            if (value is T t)
            {
                cache[key] = value;
                result     = t;
                return(true);
            }

            result = default;
            return(false);
        }
Exemple #20
0
    public void BasicRuleRejectsApplicationIfAnyParameters()
    {
        var ruleFromString = new BasicRule(
            RuleParser.ParseToRule("A -> AB", x => x),
            '[', ']');
        var totalIncluded = new HashSet <int>("[]AB".Select(x => (int)x));

        using var ruleNativeData = new SystemLevelRuleNativeData(new[] { ruleFromString });
        var nativeWriter = new SymbolSeriesMatcherNativeDataWriter();

        ruleFromString.WriteDataIntoMemory(ruleNativeData, nativeWriter);

        var symbols = new DependencyTracker <SymbolString <float> >(
            new SymbolString <float>(new int[] { 'A' }, new float[][] { new float[0] })
            );

        try
        {
            var globalParams = new float[0];
            using var globalNative = new NativeArray <float>(globalParams, Allocator.Persistent);
            using var paramMemory  = new NativeArray <float>(0, Allocator.Persistent);
            using var branchCache  = new SymbolStringBranchingCache('[', ']', new[] { totalIncluded }, ruleNativeData);
            branchCache.BuildJumpIndexesFromSymbols(symbols);
            var random          = new Unity.Mathematics.Random();
            var matchSingleData = new LSystemSingleSymbolMatchData
            {
                isTrivial = false,
                tmpParameterMemorySpace = JaggedIndexing.GetWithNoLength(0)
            };

            var preMatchSuccess = ruleFromString.AsBlittable().PreMatchCapturedParametersWithoutConditional(
                branchCache,
                symbols.Data,
                0,
                paramMemory,
                matchSingleData.tmpParameterMemorySpace.index,
                ref matchSingleData,
                new TmpNativeStack <SymbolStringBranchingCache.BranchEventData>(5),
                globalNative,
                ruleNativeData.dynamicOperatorMemory,
                ref random,
                ruleNativeData.ruleOutcomeMemorySpace
                );
            Assert.IsTrue(preMatchSuccess);
            Assert.AreEqual(0, matchSingleData.selectedReplacementPattern);
            Assert.AreEqual(0, matchSingleData.tmpParameterMemorySpace.length);
            Assert.AreEqual(2, matchSingleData.replacementSymbolIndexing.length);
            Assert.AreEqual(0, matchSingleData.replacementParameterIndexing.length);

            var symbolRawData = symbols.Data;
            symbolRawData.parameters[0] = new JaggedIndexing
            {
                index  = 0,
                length = 1
            };

            matchSingleData = new LSystemSingleSymbolMatchData
            {
                isTrivial = false,
                tmpParameterMemorySpace = JaggedIndexing.GetWithNoLength(0)
            };
            preMatchSuccess = ruleFromString.AsBlittable().PreMatchCapturedParametersWithoutConditional(
                branchCache,
                symbols.Data,
                0,
                paramMemory,
                matchSingleData.tmpParameterMemorySpace.index,
                ref matchSingleData,
                new TmpNativeStack <SymbolStringBranchingCache.BranchEventData>(5),
                globalNative,
                ruleNativeData.dynamicOperatorMemory,
                ref random,
                ruleNativeData.ruleOutcomeMemorySpace
                );
            Assert.IsFalse(preMatchSuccess);
        }
        finally
        {
            symbols.Dispose();
        }
    }
Exemple #21
0
 internal bool TryGetComponentDependencyTracker <T>(out DependencyTracker tracker)
 => _componentDependenciesByTypeIndex.TryGetValue(TypeManager.GetTypeIndex <T>(), out tracker);
Exemple #22
0
 internal bool TryGetComponentDependencyTracker(int typeIndex, out DependencyTracker tracker)
 => _componentDependenciesByTypeIndex.TryGetValue(typeIndex, out tracker);
Exemple #23
0
        public LSystemSymbolReplacementCompletable(
            Unity.Mathematics.Random randResult,
            LSystemState <float> lastSystemState,
            int totalNewSymbolSize,
            int totalNewParamSize,
            NativeArray <float> globalParamNative,
            NativeArray <float> tmpParameterMemory,
            NativeArray <LSystemSingleSymbolMatchData> matchSingletonData,
            DependencyTracker <SystemLevelRuleNativeData> nativeData,
            SymbolStringBranchingCache branchingCache,
            CustomRuleSymbols customSymbols)
        {
            this.lastSystemState    = lastSystemState;
            this.matchSingletonData = matchSingletonData;
            this.branchingCache     = branchingCache;
            UnityEngine.Profiling.Profiler.BeginSample("allocating");
            target = new SymbolString <float>(totalNewSymbolSize, totalNewParamSize, Allocator.Persistent);
            UnityEngine.Profiling.Profiler.EndSample();

            this.randResult = randResult;

            this.nativeData = nativeData;

            // 5
            UnityEngine.Profiling.Profiler.BeginSample("generating replacements");

            var replacementJob = new RuleReplacementJob
            {
                globalParametersArray = globalParamNative,

                parameterMatchMemory = tmpParameterMemory,
                matchSingletonData   = matchSingletonData,

                sourceData            = lastSystemState.currentSymbols.Data,
                structExpressionSpace = nativeData.Data.structExpressionMemorySpace,
                globalOperatorData    = nativeData.Data.dynamicOperatorMemory,
                replacementSymbolData = nativeData.Data.replacementsSymbolMemorySpace,
                outcomeData           = nativeData.Data.ruleOutcomeMemorySpace,

                targetData = target,
                blittableRulesByTargetSymbol = nativeData.Data.blittableRulesByTargetSymbol,
                branchingCache = branchingCache,
                customSymbols  = customSymbols
            };

            currentJobHandle = replacementJob.Schedule(
                matchSingletonData.Length,
                100
                );

            if (customSymbols.hasDiffusion && !customSymbols.independentDiffusionUpdate)
            {
                diffusionHelper = new DiffusionWorkingDataPack(10, 5, 2, customSymbols, Allocator.TempJob);
                var diffusionJob = new ParallelDiffusionReplacementJob
                {
                    matchSingletonData = matchSingletonData,
                    sourceData         = lastSystemState.currentSymbols.Data,
                    targetData         = target,
                    customSymbols      = customSymbols,
                    working            = diffusionHelper
                };
                currentJobHandle = JobHandle.CombineDependencies(
                    currentJobHandle,
                    diffusionJob.Schedule()
                    );
            }
            // only parameter modifications beyond this point
            lastSystemState.currentSymbols.RegisterDependencyOnData(currentJobHandle);
            nativeData.RegisterDependencyOnData(currentJobHandle);

            currentJobHandle = JobHandle.CombineDependencies(
                JobHandle.CombineDependencies(
                    ScheduleIdAssignmentJob(currentJobHandle, customSymbols, lastSystemState),
                    ScheduleIndependentDiffusion(currentJobHandle, customSymbols)
                    ),
                JobHandle.CombineDependencies(
                    ScheduleAutophagyJob(currentJobHandle, customSymbols),
                    ScheduleImmaturityJob(currentJobHandle)
                    ));

            UnityEngine.Profiling.Profiler.EndSample();
        }
        public TurtleStringReadingCompletable(
            Mesh targetMesh,
            int totalSubmeshes,
            DependencyTracker <SymbolString <float> > symbols,
            DependencyTracker <NativeTurtleData> nativeData,
            int branchStartChar,
            int branchEndChar,
            TurtleState defaultState,
            CustomRuleSymbols customSymbols,
            TurtleVolumeWorldReferences volumetrics,
            Matrix4x4 localToWorldTransform)
        {
            this.targetMesh = targetMesh;
            this.nativeData = nativeData;

            UnityEngine.Profiling.Profiler.BeginSample("turtling job");

            JobHandleWrapper volumetricJobHandle = currentJobHandle;
            var volumetricHandles = new TurtleVolumetricHandles
            {
                durabilityWriter = volumetrics.durabilityWriter.GetNextNativeWritableHandle(localToWorldTransform, ref volumetricJobHandle),
                universalWriter  = volumetrics.universalLayerWriter.GetNextNativeWritableHandle(localToWorldTransform),
                volumetricData   = volumetrics.world.NativeVolumeData.openReadData.AsReadOnly()
            };

            currentJobHandle = volumetricJobHandle;


            UnityEngine.Profiling.Profiler.BeginSample("allocating");
            var tmpHelperStack = new TmpNativeStack <TurtleState>(50, Allocator.TempJob);

            organInstances       = new NativeList <TurtleOrganInstance>(100, Allocator.TempJob);
            newMeshSizeBySubmesh = new NativeArray <TurtleMeshAllocationCounter>(totalSubmeshes, Allocator.TempJob);
            UnityEngine.Profiling.Profiler.EndSample();

            NativeArray <float> destructionCommandTimestamps;

            if (volumetrics.damageFlags != null)
            {
                destructionCommandTimestamps = volumetrics.damageFlags.GetDestructionCommandTimestampsReadOnly();
            }
            else
            {
                destructionCommandTimestamps = new NativeArray <float>(0, Allocator.TempJob);
            }

            var entitySpawningSystem = World.DefaultGameObjectInjectionWorld.GetOrCreateSystem <BeginSimulationEntityCommandBufferSystem>();
            var entitySpawnBuffer    = entitySpawningSystem.CreateCommandBuffer();


            var turtleCompileJob = new TurtleCompilationJob
            {
                symbols         = symbols.Data,
                operationsByKey = nativeData.Data.operationsByKey,
                organData       = nativeData.Data.allOrganData,

                organInstances       = organInstances,
                newMeshSizeBySubmesh = newMeshSizeBySubmesh,
                spawnEntityBuffer    = entitySpawnBuffer,

                nativeTurtleStack = tmpHelperStack,

                branchStartChar = branchStartChar,
                branchEndChar   = branchEndChar,

                currentState = defaultState,

                customRules = customSymbols,

                volumetricHandles               = volumetricHandles,
                hasVolumetricDestruction        = volumetrics.damageFlags != null,
                volumetricDestructionTimestamps = destructionCommandTimestamps,
                earliestValidDestructionCommand = volumetrics.damageFlags != null ? Time.time - volumetrics.damageFlags.timeCommandStaysActive : -1
            };

            currentJobHandle = turtleCompileJob.Schedule(currentJobHandle);
            volumetrics.world.NativeVolumeData.RegisterReadingDependency(currentJobHandle);
            entitySpawningSystem.AddJobHandleForProducer(currentJobHandle);
            volumetrics.damageFlags?.RegisterReaderOfDestructionFlags(currentJobHandle);
            volumetrics.durabilityWriter.RegisterWriteDependency(currentJobHandle);
            volumetrics.universalLayerWriter.RegisterWriteDependency(currentJobHandle);

            nativeData.RegisterDependencyOnData(currentJobHandle);
            symbols.RegisterDependencyOnData(currentJobHandle);

            currentJobHandle = tmpHelperStack.Dispose(currentJobHandle);
            if (volumetrics.damageFlags == null)
            {
                currentJobHandle = destructionCommandTimestamps.Dispose(currentJobHandle);
            }
            UnityEngine.Profiling.Profiler.EndSample();
        }
        /// <summary>
        ///
        /// </summary>
        /// <param name="lastSystemState"></param>
        /// <param name="lSystemNativeData"></param>
        /// <param name="globalParameters"></param>
        /// <param name="maxMemoryRequirementsPerSymbol"></param>
        /// <param name="branchOpenSymbol"></param>
        /// <param name="branchCloseSymbol"></param>
        /// <param name="includedCharactersByRuleIndex"></param>
        /// <param name="customSymbols"></param>
        /// <param name="parameterModificationJobDependency">A dependency on a job which only makes changes to the parameters of the source symbol string.
        ///     the symbols themselves must be constant</param>
        public LSystemRuleMatchCompletable(
            NativeArray <LSystemSingleSymbolMatchData> matchSingletonData,
            int parameterTotalSum,
            SymbolStringBranchingCache branchingCache,
            LSystemState <float> lastSystemState,
            DependencyTracker <SystemLevelRuleNativeData> lSystemNativeData,
            float[] globalParameters,
            CustomRuleSymbols customSymbols,
            JobHandle parameterModificationJobDependency)
        {
            this.customSymbols   = customSymbols;
            this.lastSystemState = lastSystemState;
            randResult           = lastSystemState.randomProvider;
            nativeData           = lSystemNativeData;

            this.matchSingletonData = matchSingletonData;
            this.branchingCache     = branchingCache;

            // 1.
            UnityEngine.Profiling.Profiler.BeginSample("allocating");
            tmpParameterMemory = new NativeArray <float>(parameterTotalSum, Allocator.Persistent, NativeArrayOptions.UninitializedMemory);
            globalParamNative  = new NativeArray <float>(globalParameters, Allocator.Persistent);
            UnityEngine.Profiling.Profiler.EndSample();

            // 2.
            UnityEngine.Profiling.Profiler.BeginSample("matching");


            var prematchJob = new RuleCompleteMatchJob
            {
                matchSingletonData = matchSingletonData,

                sourceData         = lastSystemState.currentSymbols.Data,
                tmpParameterMemory = tmpParameterMemory,

                globalOperatorData = nativeData.Data.dynamicOperatorMemory,
                outcomes           = nativeData.Data.ruleOutcomeMemorySpace,
                globalParams       = globalParamNative,

                blittableRulesByTargetSymbol = nativeData.Data.blittableRulesByTargetSymbol,
                branchingCache = branchingCache,
                seed           = randResult.NextUInt()
            };

            var matchingJobHandle = prematchJob.ScheduleBatch(
                matchSingletonData.Length,
                100,
                parameterModificationJobDependency);


            UnityEngine.Profiling.Profiler.EndSample();

            // 4.
            UnityEngine.Profiling.Profiler.BeginSample("replacement counting");

            UnityEngine.Profiling.Profiler.BeginSample("allocating");
            totalSymbolCount          = new NativeArray <int>(1, Allocator.Persistent);
            totalSymbolParameterCount = new NativeArray <int>(1, Allocator.Persistent);
            UnityEngine.Profiling.Profiler.EndSample();

            var totalSymbolLengthJob = new RuleReplacementSizeJob
            {
                matchSingletonData        = matchSingletonData,
                totalResultSymbolCount    = totalSymbolCount,
                totalResultParameterCount = totalSymbolParameterCount,
                sourceData    = lastSystemState.currentSymbols.Data,
                customSymbols = customSymbols
            };

            currentJobHandle = totalSymbolLengthJob.Schedule(matchingJobHandle);
            lastSystemState.currentSymbols.RegisterDependencyOnData(currentJobHandle);
            nativeData.RegisterDependencyOnData(currentJobHandle);

            UnityEngine.Profiling.Profiler.EndSample();
        }
Exemple #26
0
 public TLogWriter(DependencyTracker t)
 {
     tracker = t;
 }
Exemple #27
0
 public DefaultLSystemState(SymbolString <float> axiom, uint seed)
 {
     currentSymbols = new DependencyTracker <SymbolString <float> >(axiom);
     randomProvider = new Unity.Mathematics.Random(seed);
 }