public async Task SupportsTwoWayBindingForTextareas()
        {
            // Arrange/Act
            var component = CompileToComponent(
                @"<textarea bind=""MyValue"" ></textarea>
                @functions {
                    public string MyValue { get; set; } = ""Initial value"";
                }");
            var myValueProperty = component.GetType().GetProperty("MyValue");

            var renderer = new TestRenderer();

            // Assert
            EventCallback setter = default;
            var           frames = GetRenderTree(renderer, component);

            Assert.Collection(frames,
                              frame => AssertFrame.Element(frame, "textarea", 3, 0),
                              frame => AssertFrame.Attribute(frame, "value", "Initial value", 1),
                              frame =>
            {
                AssertFrame.Attribute(frame, "onchange", 2);
                setter = Assert.IsType <EventCallback>(frame.AttributeValue);
            });

            // Trigger the change event to show it updates the property
            //
            // This should always complete synchronously.
            var task = renderer.InvokeAsync(() => setter.InvokeAsync(new UIChangeEventArgs {
                Value = "Modified value",
            }));

            Assert.Equal(TaskStatus.RanToCompletion, task.Status);
            await task;

            Assert.Equal("Modified value", myValueProperty.GetValue(component));
        }
Esempio n. 2
0
        public async Task RespondsToValidationStateChangeNotifications()
        {
            // Arrange
            var model         = new TestModel();
            var rootComponent = new TestInputHostComponent <string, TestInputComponent <string> >
            {
                EditContext     = new EditContext(model),
                ValueExpression = () => model.StringProperty
            };
            var fieldIdentifier = FieldIdentifier.Create(() => model.StringProperty);
            var renderer        = new TestRenderer();
            var rootComponentId = renderer.AssignRootComponentId(rootComponent);
            await renderer.RenderRootComponentAsync(rootComponentId);

            // Initally, it rendered one batch and is valid
            var batch1           = renderer.Batches.Single();
            var componentFrame1  = batch1.GetComponentFrames <TestInputComponent <string> >().Single();
            var inputComponentId = componentFrame1.ComponentId;
            var component        = (TestInputComponent <string>)componentFrame1.Component;

            Assert.Equal("valid", component.CssClass);
            Assert.Null(component.AdditionalAttributes);

            // Act: update the field state in the EditContext and notify
            var messageStore = new ValidationMessageStore(rootComponent.EditContext);

            messageStore.Add(fieldIdentifier, "Some message");
            await renderer.Dispatcher.InvokeAsync(rootComponent.EditContext.NotifyValidationStateChanged);

            // Assert: The input component rendered itself again and now has the new class
            var batch2 = renderer.Batches.Skip(1).Single();

            Assert.Equal(inputComponentId, batch2.DiffsByComponentId.Keys.Single());
            Assert.Equal("invalid", component.CssClass);
            Assert.NotNull(component.AdditionalAttributes);
            Assert.True(component.AdditionalAttributes.ContainsKey("aria-invalid"));
        }
    public void RespondsToNotificationsFromAuthenticationStateProvider()
    {
        // Arrange: Service
        var services          = new ServiceCollection();
        var authStateProvider = new TestAuthenticationStateProvider()
        {
            CurrentAuthStateTask = Task.FromResult(CreateAuthenticationState(null))
        };

        services.AddSingleton <AuthenticationStateProvider>(authStateProvider);

        // Arrange: Renderer and component, initially rendered
        var renderer  = new TestRenderer(services.BuildServiceProvider());
        var component = new UseCascadingAuthenticationStateComponent();

        renderer.AssignRootComponentId(component);
        component.TriggerRender();
        var receiveAuthStateId = renderer.Batches.Single()
                                 .GetComponentFrames <ReceiveAuthStateComponent>().Single().ComponentId;

        // Act 2: AuthenticationStateProvider issues notification
        authStateProvider.TriggerAuthenticationStateChanged(
            Task.FromResult(CreateAuthenticationState("Bert")));

        // Assert 2: Re-renders content
        Assert.Equal(2, renderer.Batches.Count);
        var batch = renderer.Batches.Last();
        var receiveAuthStateDiff = batch.DiffsByComponentId[receiveAuthStateId].Single();

        Assert.Collection(receiveAuthStateDiff.Edits, edit =>
        {
            Assert.Equal(RenderTreeEditType.UpdateText, edit.Type);
            AssertFrame.Text(
                batch.ReferenceFrames[edit.ReferenceFrameIndex],
                "Authenticated: True; Name: Bert; Pending: False; Renders: 2");
        });
    }
Esempio n. 4
0
        public void DoesNotNotifyDescendantsIfCascadingParameterValuesAreImmutableAndUnchanged()
        {
            // Arrange
            var renderer  = new TestRenderer();
            var component = new TestComponent(builder =>
            {
                builder.OpenComponent <CascadingValue <string> >(0);
                builder.AddAttribute(1, "Value", "Unchanging value");
                builder.AddAttribute(2, RenderTreeBuilder.ChildContent, new RenderFragment(childBuilder =>
                {
                    childBuilder.OpenComponent <CascadingParameterConsumerComponent <string> >(0);
                    childBuilder.AddAttribute(1, "RegularParameter", "Goodbye");
                    childBuilder.CloseComponent();
                }));
                builder.CloseComponent();
            });

            // Act 1: Initial render
            var componentId = renderer.AssignRootComponentId(component);

            component.TriggerRender();
            var firstBatch      = renderer.Batches.Single();
            var nestedComponent = FindComponent <CascadingParameterConsumerComponent <string> >(firstBatch, out _);

            Assert.Equal(3, firstBatch.DiffsByComponentId.Count); // Root + CascadingValue + nested
            Assert.Equal(1, nestedComponent.NumRenders);

            // Act/Assert: Re-render the CascadingValue; observe nested component wasn't re-rendered
            component.TriggerRender();

            // Assert: We did not re-render CascadingParameterConsumerComponent
            Assert.Equal(2, renderer.Batches.Count);
            var secondBatch = renderer.Batches[1];

            Assert.Equal(2, secondBatch.DiffsByComponentId.Count); // Root + CascadingValue, but not nested one
            Assert.Equal(1, nestedComponent.NumRenders);
        }
Esempio n. 5
0
        public void RunsOnParametersSetAsyncWhenRendered()
        {
            // Arrange
            var renderer  = new TestRenderer();
            var component = new TestComponent();

            int onParametersSetAsyncRuns = 0;

            component.RunsBaseOnParametersSetAsync = false;
            component.OnParametersSetAsyncLogic    = c =>
            {
                onParametersSetAsyncRuns++;
                return(Task.CompletedTask);
            };

            // Act
            var componentId = renderer.AssignRootComponentId(component);

            renderer.RenderRootComponent(componentId);

            // Assert
            Assert.Equal(1, onParametersSetAsyncRuns);
            Assert.Single(renderer.Batches);
        }
        public void OmitsAttributeIfNotFoundButValueIsOmissible()
        {
            // Arrange
            var valuePropName = "testprop";
            var renderer      = new TestRenderer();
            var builder       = new RenderTreeBuilder();

            builder.OpenElement(0, "elem");
            builder.AddAttribute(1, "eventname", (Action)(() => { }));
            builder.SetUpdatesAttributeName(valuePropName);
            builder.CloseElement();
            var frames = builder.GetFrames();

            frames.Array[1] = frames.Array[1].WithAttributeEventHandlerId(123);

            // Act
            RenderTreeUpdater.UpdateToMatchClientState(builder, 123, false);
            frames = builder.GetFrames();

            // Assert
            Assert.Collection(frames.AsEnumerable(),
                              frame => AssertFrame.Element(frame, "elem", 2, 0),
                              frame => AssertFrame.Attribute(frame, "eventname", v => Assert.IsType <Action>(v), 1));
        }
        public void CanAccessToChildComponentInstance()
        {
            // Arrange
            var instance        = new DynamicComponent();
            var renderer        = new TestRenderer();
            var childParameters = new Dictionary <string, object>
            {
                { nameof(TestComponent.IntProp), 123 },
            };
            var parameters = ParameterView.FromDictionary(new Dictionary <string, object>
            {
                { nameof(DynamicComponent.Type), typeof(TestComponent) },
                { nameof(DynamicComponent.Parameters), childParameters },
            });

            // Act
            renderer.RenderRootComponent(
                renderer.AssignRootComponentId(instance),
                parameters);

            // Assert
            Assert.IsType <TestComponent>(instance.Instance);
            Assert.Equal(123, ((TestComponent)instance.Instance).IntProp);
        }
Esempio n. 8
0
        public void RunsOnInitAsyncAlsoOnBaseClassWhenRendered()
        {
            // Arrange
            var renderer  = new TestRenderer();
            var component = new TestComponent();

            var onInitAsyncRuns = 0;

            component.RunsBaseOnInitAsync = true;
            component.OnInitAsyncLogic    = c =>
            {
                onInitAsyncRuns++;
                return(Task.CompletedTask);
            };

            // Act
            var componentId = renderer.AssignRootComponentId(component);

            renderer.RenderRootComponent(componentId);

            // Assert
            Assert.Equal(1, onInitAsyncRuns);
            Assert.Single(renderer.Batches);
        }
        public void CanRenderComponentByTypeWithParameters()
        {
            // Arrange
            var instance        = new DynamicComponent();
            var renderer        = new TestRenderer();
            var childParameters = new Dictionary <string, object>
            {
                { nameof(TestComponent.IntProp), 123 },
                { nameof(TestComponent.ChildContent), (RenderFragment)(builder =>
                    {
                        builder.AddContent(0, "This is some child content");
                    }) },
            };
            var parameters = ParameterView.FromDictionary(new Dictionary <string, object>
            {
                { nameof(DynamicComponent.Type), typeof(TestComponent) },
                { nameof(DynamicComponent.Parameters), childParameters },
            });

            // Act
            renderer.RenderRootComponent(
                renderer.AssignRootComponentId(instance),
                parameters);

            // Assert
            var batch = renderer.Batches.Single();

            // It renders a reference to the child component with its parameters
            AssertFrame.Component <TestComponent>(batch.ReferenceFrames[0], 4, 0);
            AssertFrame.Attribute(batch.ReferenceFrames[1], nameof(TestComponent.IntProp), 123, 1);
            AssertFrame.Attribute(batch.ReferenceFrames[2], nameof(TestComponent.ChildContent), 1);

            // The child component itself is rendered
            AssertFrame.Text(batch.ReferenceFrames[4], "Hello from TestComponent with IntProp=123", 0);
            AssertFrame.Text(batch.ReferenceFrames[5], "This is some child content", 0);
        }
Esempio n. 10
0
        public void CanReRenderTopLevelComponents()
        {
            // Arrange
            var renderer  = new TestRenderer();
            var component = new MessageComponent {
                Message = "Initial message"
            };
            var componentId = renderer.AssignComponentId(component);

            // Act/Assert: first render
            renderer.RenderNewBatch(componentId);
            var firstDiff = renderer.Batches.Single().DiffsByComponentId[componentId].Single();

            Assert.Collection(firstDiff.Edits,
                              edit =>
            {
                Assert.Equal(RenderTreeEditType.PrependFrame, edit.Type);
                Assert.Equal(0, edit.ReferenceFrameIndex);
            });
            Assert.Collection(firstDiff.ReferenceFrames,
                              frame => AssertFrame.Text(frame, "Initial message"));

            // Act/Assert: second render
            component.Message = "Modified message";
            renderer.RenderNewBatch(componentId);
            var secondDiff = renderer.Batches.Skip(1).Single().DiffsByComponentId[componentId].Single();

            Assert.Collection(firstDiff.Edits,
                              edit =>
            {
                Assert.Equal(RenderTreeEditType.UpdateText, edit.Type);
                Assert.Equal(0, edit.ReferenceFrameIndex);
            });
            Assert.Collection(firstDiff.ReferenceFrames,
                              frame => AssertFrame.Text(frame, "Modified message"));
        }
Esempio n. 11
0
        public void PassesCascadingParametersToNestedComponents()
        {
            // Arrange
            var renderer  = new TestRenderer();
            var component = new TestComponent(builder =>
            {
                builder.OpenComponent <CascadingValue <string> >(0);
                builder.AddAttribute(1, "Value", "Hello");
                builder.AddAttribute(2, "ChildContent", new RenderFragment(childBuilder =>
                {
                    childBuilder.OpenComponent <CascadingParameterConsumerComponent <string> >(0);
                    childBuilder.AddAttribute(1, "RegularParameter", "Goodbye");
                    childBuilder.CloseComponent();
                }));
                builder.CloseComponent();
            });

            // Act/Assert
            var componentId = renderer.AssignRootComponentId(component);

            component.TriggerRender();
            var batch               = renderer.Batches.Single();
            var nestedComponent     = FindComponent <CascadingParameterConsumerComponent <string> >(batch, out var nestedComponentId);
            var nestedComponentDiff = batch.DiffsByComponentId[nestedComponentId].Single();

            // The nested component was rendered with the correct parameters
            Assert.Collection(nestedComponentDiff.Edits,
                              edit =>
            {
                Assert.Equal(RenderTreeEditType.PrependFrame, edit.Type);
                AssertFrame.Text(
                    batch.ReferenceFrames[edit.ReferenceFrameIndex],
                    "CascadingParameter=Hello; RegularParameter=Goodbye");
            });
            Assert.Equal(1, nestedComponent.NumRenders);
        }
Esempio n. 12
0
 public LayoutTest()
 {
     _renderer = new TestRenderer();
     _layoutDisplayComponent   = new LayoutDisplay();
     _layoutDisplayComponentId = _renderer.AssignRootComponentId(_layoutDisplayComponent);
 }
 public DependencyInjectionTest()
 {
     _serviceProvider = new TestServiceProvider();
     _renderer        = new TestRenderer(_serviceProvider);
 }
Esempio n. 14
0
        public void DoesNotNotifyDescendantsOfUpdatedCascadingParameterValuesWhenFixed()
        {
            // Arrange
            var providedValue      = "Initial value";
            var shouldIncludeChild = true;
            var renderer           = new TestRenderer();
            var component          = new TestComponent(builder =>
            {
                builder.OpenComponent <CascadingValue <string> >(0);
                builder.AddAttribute(1, "Value", providedValue);
                builder.AddAttribute(2, "IsFixed", true);
                builder.AddAttribute(3, "ChildContent", new RenderFragment(childBuilder =>
                {
                    if (shouldIncludeChild)
                    {
                        childBuilder.OpenComponent <CascadingParameterConsumerComponent <string> >(0);
                        childBuilder.AddAttribute(1, "RegularParameter", "Goodbye");
                        childBuilder.CloseComponent();
                    }
                }));
                builder.CloseComponent();
            });

            // Act 1: Initial render; capture nested component ID
            var componentId = renderer.AssignRootComponentId(component);

            component.TriggerRender();
            var firstBatch      = renderer.Batches.Single();
            var nestedComponent = FindComponent <CascadingParameterConsumerComponent <string> >(firstBatch, out var nestedComponentId);

            Assert.Equal(1, nestedComponent.NumRenders);

            // Assert: Initial value is supplied to descendant
            var nestedComponentDiff = firstBatch.DiffsByComponentId[nestedComponentId].Single();

            Assert.Collection(nestedComponentDiff.Edits, edit =>
            {
                Assert.Equal(RenderTreeEditType.PrependFrame, edit.Type);
                AssertFrame.Text(
                    firstBatch.ReferenceFrames[edit.ReferenceFrameIndex],
                    "CascadingParameter=Initial value; RegularParameter=Goodbye");
            });

            // Act 2: Re-render CascadingValue with new value
            providedValue = "Updated value";
            component.TriggerRender();

            // Assert: We did not re-render the descendant
            Assert.Equal(2, renderer.Batches.Count);
            var secondBatch = renderer.Batches[1];

            Assert.Equal(2, secondBatch.DiffsByComponentId.Count); // Root + CascadingValue, but not nested one
            Assert.Equal(1, nestedComponent.NumSetParametersCalls);
            Assert.Equal(1, nestedComponent.NumRenders);

            // Act 3: Dispose
            shouldIncludeChild = false;
            component.TriggerRender();

            // Assert: Absence of an exception here implies we didn't cause a problem by
            // trying to remove a non-existent subscription
        }
Esempio n. 15
0
        public void StopsNotifyingDescendantsIfTheyAreRemoved()
        {
            // Arrange
            var providedValue          = "Initial value";
            var displayNestedComponent = true;
            var renderer  = new TestRenderer();
            var component = new TestComponent(builder =>
            {
                // At the outer level, have an unrelated fixed cascading value to show we can deal with combining both types
                builder.OpenComponent <CascadingValue <int> >(0);
                builder.AddAttribute(1, "Value", 123);
                builder.AddAttribute(2, "IsFixed", true);
                builder.AddAttribute(3, "ChildContent", new RenderFragment(builder2 =>
                {
                    // Then also have a non-fixed cascading value so we can show that unsubscription works
                    builder2.OpenComponent <CascadingValue <string> >(0);
                    builder2.AddAttribute(1, "Value", providedValue);
                    builder2.AddAttribute(2, "ChildContent", new RenderFragment(builder3 =>
                    {
                        if (displayNestedComponent)
                        {
                            builder3.OpenComponent <SecondCascadingParameterConsumerComponent <string, int> >(0);
                            builder3.AddAttribute(1, "RegularParameter", "Goodbye");
                            builder3.CloseComponent();
                        }
                    }));
                    builder2.CloseComponent();
                }));
                builder.CloseComponent();
            });

            // Act 1: Initial render; capture nested component ID
            var componentId = renderer.AssignRootComponentId(component);

            component.TriggerRender();
            var firstBatch      = renderer.Batches.Single();
            var nestedComponent = FindComponent <CascadingParameterConsumerComponent <string> >(firstBatch, out var nestedComponentId);

            Assert.Equal(1, nestedComponent.NumSetParametersCalls);
            Assert.Equal(1, nestedComponent.NumRenders);

            // Act/Assert 2: Re-render the CascadingValue; observe nested component wasn't re-rendered
            providedValue          = "Updated value";
            displayNestedComponent = false; // Remove the nested component
            component.TriggerRender();

            // Assert: We did not render the nested component now it's been removed
            Assert.Equal(2, renderer.Batches.Count);
            var secondBatch = renderer.Batches[1];

            Assert.Equal(1, nestedComponent.NumRenders);
            Assert.Equal(3, secondBatch.DiffsByComponentId.Count); // Root + CascadingValue + CascadingValue, but not nested component

            // We *did* send updated params during the first render where it was removed,
            // because the params are sent before the disposal logic runs. We could avoid
            // this by moving the notifications into the OnAfterRender phase, but then we'd
            // often render descendants twice (once because they are descendants and some
            // direct parameter might have changed, then once because a cascading parameter
            // changed). We can't have it both ways, so optimize for the case when the
            // nested component *hasn't* just been removed.
            Assert.Equal(2, nestedComponent.NumSetParametersCalls);

            // Act 3: However, after disposal, the subscription is removed, so we won't send
            // updated params on subsequent CascadingValue renders.
            providedValue = "Updated value 2";
            component.TriggerRender();
            Assert.Equal(2, nestedComponent.NumSetParametersCalls);
        }
Esempio n. 16
0
        protected RenderTreeFrame[] GetRenderTree(IComponent component)
        {
            var renderer = new TestRenderer();

            return(GetRenderTree(renderer, component));
        }
Esempio n. 17
0
 public LayoutViewTest()
 {
     _renderer              = new TestRenderer();
     _layoutViewComponent   = new LayoutView();
     _layoutViewComponentId = _renderer.AssignRootComponentId(_layoutViewComponent);
 }
Esempio n. 18
0
 public PageDisplayTest()
 {
     _renderer               = new TestRenderer();
     _pageDisplayComponent   = new PageDisplay();
     _pageDisplayComponentId = _renderer.AssignRootComponentId(_pageDisplayComponent);
 }
Esempio n. 19
0
        public void ComponentCanTriggerRenderWhenExistingBatchIsInProgress()
        {
            // Arrange
            var           renderer          = new TestRenderer();
            TestComponent parent            = null;
            var           parentRenderCount = 0;

            parent = new TestComponent(builder =>
            {
                builder.OpenComponent <ReRendersParentComponent>(0);
                builder.AddAttribute(1, nameof(ReRendersParentComponent.Parent), parent);
                builder.CloseComponent();
                builder.AddContent(2, $"Parent render count: {++parentRenderCount}");
            });
            var parentComponentId = renderer.AssignComponentId(parent);

            // Act
            parent.TriggerRender();

            // Assert
            var batch = renderer.Batches.Single();

            Assert.Equal(4, batch.DiffsInOrder.Count);

            // First is the parent component's initial render
            var diff1 = batch.DiffsInOrder[0];

            Assert.Equal(parentComponentId, diff1.ComponentId);
            Assert.Collection(diff1.Edits,
                              edit =>
            {
                Assert.Equal(RenderTreeEditType.PrependFrame, edit.Type);
                AssertFrame.Component <ReRendersParentComponent>(
                    batch.ReferenceFrames[edit.ReferenceFrameIndex]);
            },
                              edit =>
            {
                Assert.Equal(RenderTreeEditType.PrependFrame, edit.Type);
                AssertFrame.Text(
                    batch.ReferenceFrames[edit.ReferenceFrameIndex],
                    "Parent render count: 1");
            });

            // Second is the child component's single render
            var diff2 = batch.DiffsInOrder[1];

            Assert.NotEqual(parentComponentId, diff2.ComponentId);
            var diff2edit = diff2.Edits.Single();

            Assert.Equal(RenderTreeEditType.PrependFrame, diff2edit.Type);
            AssertFrame.Text(batch.ReferenceFrames[diff2edit.ReferenceFrameIndex],
                             "Child is here");

            // Third is the parent's triggered render
            var diff3 = batch.DiffsInOrder[2];

            Assert.Equal(parentComponentId, diff3.ComponentId);
            var diff3edit = diff3.Edits.Single();

            Assert.Equal(RenderTreeEditType.UpdateText, diff3edit.Type);
            AssertFrame.Text(batch.ReferenceFrames[diff3edit.ReferenceFrameIndex],
                             "Parent render count: 2");

            // Fourth is child's rerender due to parent rendering
            var diff4 = batch.DiffsInOrder[3];

            Assert.NotEqual(parentComponentId, diff4.ComponentId);
            Assert.Empty(diff4.Edits);
        }
Esempio n. 20
0
        public void AllRendersTriggeredSynchronouslyDuringEventHandlerAreHandledAsSingleBatch()
        {
            // Arrange: A root component with a child whose event handler explicitly queues
            // a re-render of both the root component and the child
            var            renderer       = new TestRenderer();
            var            eventCount     = 0;
            TestComponent  rootComponent  = null;
            EventComponent childComponent = null;

            rootComponent = new TestComponent(builder =>
            {
                builder.AddContent(0, "Child event count: " + eventCount);
                builder.OpenComponent <EventComponent>(1);
                builder.AddAttribute(2, nameof(EventComponent.OnTest), args =>
                {
                    eventCount++;
                    rootComponent.TriggerRender();
                    childComponent.TriggerRender();
                });
                builder.CloseComponent();
            });
            var rootComponentId = renderer.AssignComponentId(rootComponent);

            rootComponent.TriggerRender();
            var origBatchReferenceFrames = renderer.Batches.Single().ReferenceFrames;
            var childComponentFrame      = origBatchReferenceFrames
                                           .Single(f => f.Component is EventComponent);
            var childComponentId = childComponentFrame.ComponentId;

            childComponent = (EventComponent)childComponentFrame.Component;
            var origEventHandlerId = origBatchReferenceFrames
                                     .Where(f => f.FrameType == RenderTreeFrameType.Attribute)
                                     .Last(f => f.AttributeEventHandlerId != 0)
                                     .AttributeEventHandlerId;

            Assert.Single(renderer.Batches);

            // Act
            renderer.DispatchEvent(childComponentId, origEventHandlerId, args: null);

            // Assert
            Assert.Equal(2, renderer.Batches.Count);
            var batch = renderer.Batches.Last();

            Assert.Collection(batch.DiffsInOrder,
                              diff =>
            {
                // First we triggered the root component to re-render
                Assert.Equal(rootComponentId, diff.ComponentId);
                Assert.Collection(diff.Edits, edit =>
                {
                    Assert.Equal(RenderTreeEditType.UpdateText, edit.Type);
                    AssertFrame.Text(
                        batch.ReferenceFrames[edit.ReferenceFrameIndex],
                        "Child event count: 1");
                });
            },
                              diff =>
            {
                // Then the root re-render will have triggered an update to the child
                Assert.Equal(childComponentId, diff.ComponentId);
                Assert.Collection(diff.Edits, edit =>
                {
                    Assert.Equal(RenderTreeEditType.UpdateText, edit.Type);
                    AssertFrame.Text(
                        batch.ReferenceFrames[edit.ReferenceFrameIndex],
                        "Render count: 2");
                });
            },
                              diff =>
            {
                // Finally we explicitly requested a re-render of the child
                Assert.Equal(childComponentId, diff.ComponentId);
                Assert.Collection(diff.Edits, edit =>
                {
                    Assert.Equal(RenderTreeEditType.UpdateText, edit.Type);
                    AssertFrame.Text(
                        batch.ReferenceFrames[edit.ReferenceFrameIndex],
                        "Render count: 3");
                });
            });
        }
Esempio n. 21
0
 public RouteViewTest()
 {
     _renderer             = new TestRenderer();
     _routeViewComponent   = new RouteView();
     _routeViewComponentId = _renderer.AssignRootComponentId(_routeViewComponent);
 }
Esempio n. 22
0
 public ContainerComponent(TestRenderer renderer)
 {
     this.renderer = renderer;
     componentId   = renderer.AttachTestRootComponent(this);
 }