Open jimmyjxiao opened 4 years ago
More information:
Xamarin.Forms.Element.FindByName(string)
Xamarin.Forms.Setter.Apply(Xamarin.Forms.BindableObject, bool)
Xamarin.Forms.VisualStateManager.GoToState(Xamarin.Forms.VisualElement, string)
Xamarin.Forms.VisualStateGroup.UpdateStateTriggers()
Xamarin.Forms.VisualStateGroupList.Validate(System.Collections.Generic.IList<Xamarin.Forms.VisualStateGroup>)
Xamarin.Forms.VisualStateGroupList.ValidateAndNotify(System.Collections.Generic.IList<Xamarin.Forms.VisualStateGroup>)
Xamarin.Forms.WatchAddList<T>.Add(T)
Xamarin.Forms.VisualStateGroupList.Add(Xamarin.Forms.VisualStateGroup)
VsmDemos.VsmSetterTargetNamePage.InitializeComponent() en VsmSetterTargetNamePage.xaml.g.cs
VsmDemos.VsmSetterTargetNamePage.VsmSetterTargetNamePage() en VsmSetterTargetNamePage.xaml.cs
Issue seems to come without using AdaptiveTrigger just by using VisualState with TargetName. We have a Style that contains a VisualState definition and when the page loads it crashes when the Disabled state is getting used (IsEnabled==False).
<VisualStateGroup x:Name="CommonStates">
<VisualState x:Name="Normal">
<VisualState.Setters>
<Setter Property="BackgroundColor" Value="{DynamicResource EnterButtonBackgroundColor}" />
</VisualState.Setters>
</VisualState>
<VisualState x:Name="Disabled">
<VisualState.Setters>
<Setter Property="BackgroundColor" Value="{DynamicResource DisabledEnterButtonBackgroundColor}" />
<Setter TargetName="buttonLabel" Property="Label.TextColor" Value="{DynamicResource DisabledEnterButtonTextColor}" />
</VisualState.Setters>
</VisualState>
</VisualStateGroup>
The control this style is applied to is a Frame, the control with the name "buttonLabel" is a Label inside the Frame.
at Xamarin.Forms.Element.FindByName (System.String name) [0x00009] in D:\a\1\s\Xamarin.Forms.Core\Element.cs:274
at Xamarin.Forms.Setter.Apply (Xamarin.Forms.BindableObject target, System.Boolean fromStyle) [0x00027] in D:\a\1\s\Xamarin.Forms.Core\Setter.cs:58
at Xamarin.Forms.VisualStateManager.GoToState (Xamarin.Forms.VisualElement visualElement, System.String name) [0x000be] in D:\a\1\s\Xamarin.Forms.Core\VisualStateManager.cs:90
at Xamarin.Forms.VisualElement.ChangeVisualState () [0x00008] in D:\a\1\s\Xamarin.Forms.Core\VisualElement.cs:946
at Xamarin.Forms.VisualElement.OnIsEnabledPropertyChanged (Xamarin.Forms.BindableObject bindable, System.Object oldValue, System.Object newValue) [0x00012] in D:\a\1\s\Xamarin.Forms.Core\VisualElement.cs:997
...
@jsuarezruiz /Team, Issue still persist in XF 5.0.01558-pre3. Tested below code on UWP and Android. Necessary comments to reproduce the issue are mentioned in the sample code below. (If you run below code it will work but if you use commented sections, it will crash) Using Style Key causing issue so we cant apply Style to specific Grid. Also tried to apply Style at Control level (directly on MainGrid) but same issue.
<ContentPage x:Class="Test2.Views.AdaptiveTest" xmlns="http://xamarin.com/schemas/2014/forms" xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml" xmlns:viewmodels="clr-namespace:Test2.ViewModels">
<ContentPage.BindingContext>
<viewmodels:MonkeysViewModel />
</ContentPage.BindingContext>
<ContentPage.Resources>
<!-- If we use Key then it will not work and crash with exception - System.InvalidOperationException: this element is not in a namescope -->
<!--<Style TargetType="Grid" x:Key="MainGridStyle"> -->
<Style TargetType="Grid">
<Setter Property="VisualStateManager.VisualStateGroups">
<VisualStateGroupList>
<VisualStateGroup Name="ScreenStates">
<VisualState Name="NarrowState">
<VisualState.StateTriggers>
<AdaptiveTrigger MinWindowWidth="0" />
</VisualState.StateTriggers>
<VisualState.Setters>
<Setter Property="BackgroundColor" Value="LightCoral" />
<Setter Property="Padding" Value="0,10" />
<Setter TargetName="LeftOne" Property="ColumnDefinition.Width" Value="50" />
<Setter TargetName="RightOne" Property="ColumnDefinition.Width" Value="50" />
</VisualState.Setters>
</VisualState>
<VisualState Name="WideState">
<VisualState.StateTriggers>
<AdaptiveTrigger MinWindowWidth="1000" />
</VisualState.StateTriggers>
<VisualState.Setters>
<Setter Property="BackgroundColor" Value="LightGreen" />
<Setter Property="Padding" Value="40" />
<Setter TargetName="LeftOne" Property="ColumnDefinition.Width" Value="300" />
<Setter TargetName="RightOne" Property="ColumnDefinition.Width" Value="300" />
</VisualState.Setters>
</VisualState>
</VisualStateGroup>
</VisualStateGroupList>
</Setter>
</Style>
</ContentPage.Resources>
<!-- If we use this Style Key for below MainGrid, it will not work and crash with exception - System.InvalidOperationException: this element is not in a namescope -->
<!-- <Grid x:Name="MainGrid" RowDefinitions="*, 8*,*" Style="{StaticResource MainGridStyle}" -->
<Grid x:Name="MainGrid" RowDefinitions="*, 8*,*">
<Grid.ColumnDefinitions>
<ColumnDefinition x:Name="LeftOne" Width="2*" />
<ColumnDefinition x:Name="Middle" Width="6*" />
<ColumnDefinition x:Name="RightOne" Width="2*" />
</Grid.ColumnDefinitions>
<BoxView
x:Name="Box1"
Grid.Row="0"
Grid.Column="0"
BackgroundColor="SkyBlue" />
<BoxView
x:Name="Box2"
Grid.Row="0"
Grid.Column="2"
BackgroundColor="Red" />
<CollectionView
Grid.Row="1"
Grid.Column="1"
BackgroundColor="Azure"
HorizontalScrollBarVisibility="Always"
ItemsSource="{Binding Monkeys}"
VerticalScrollBarVisibility="Never">
<CollectionView.ItemTemplate>
<DataTemplate>
<StackLayout>
<Label LineBreakMode="WordWrap">
<Label.FormattedText>
<FormattedString>
<Span
FontAttributes="Bold"
Text="If we use STACK, it is working fine."
TextColor="Red" />
<Span
FontAttributes="Bold"
Text="If we removme STACK and use GRID in data template it doesn't work and app crashes."
TextColor="Red" />
<Span
FontAttributes="Bold"
Text="Remove this STACK and try uncommenting GRID section."
TextColor="Red" />
</FormattedString>
</Label.FormattedText>
</Label>
</StackLayout>
<!-- Using below child GRID in data teample will cause application to crash -->
<!--<Grid x:Name="ChildGrid" Padding="10">
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="Auto" />
</Grid.ColumnDefinitions>
<Image
Grid.RowSpan="2"
Aspect="AspectFill"
HeightRequest="60"
Source="{Binding ImageUrl}"
WidthRequest="60" />
<Label
Grid.Column="1"
FontAttributes="Bold"
Text="{Binding Name}" />
<Label
Grid.Row="1"
Grid.Column="1"
FontAttributes="Italic"
Text="{Binding Location}"
VerticalOptions="End" />
</Grid>-->
</DataTemplate>
</CollectionView.ItemTemplate>
</CollectionView>
</Grid>
Below error comes when we use Style Key.
Below error comes when we comment stack section in CollectionView data template and use Grid. Then launch application and try to narrow down the application window.
any updates on this?
I would like to know as well. Triggers and state managersare rather important, and they're currently quite hard to get to work.
@jsuarezruiz @samhouts Issue still persist even in latest XF 5 release. Same error while trying to apply style to a child Grid inside the Main Grid as mentioned earlier.
Problem is still there
The temporary solution to avoid the error. (Using code behind) `public partial class DetailPage : ContentPage { public DetailPage() { InitializeComponent();
VisualStateGroup vsGroup = new VisualStateGroup();
VisualState vsButtonDisabled = new VisualState()
{
Name = VisualStateManager.CommonStates.Disabled
};
vsButtonDisabled.Setters.Add(Button.BackgroundColorProperty, Color.DarkGray);
VisualState vsButtonPressed = new VisualState()
{
Name = "Pressed"
};
vsButtonPressed.Setters.Add(Button.BackgroundColorProperty, Color.Green);
vsButtonPressed.Setters.Add(Button.ScaleProperty, 0.90);
VisualState vsButtonNormal = new VisualState()
{
Name = VisualStateManager.CommonStates.Normal
};
vsButtonNormal.Setters.Add(Button.BackgroundColorProperty, Color.Red);
vsButtonNormal.Setters.Add(Button.ScaleProperty, 1);
vsGroup.States.Add(vsButtonDisabled);
vsGroup.States.Add(vsButtonPressed);
vsGroup.States.Add(vsButtonNormal);
VisualStateManager.SetVisualStateGroups(btnPause, new VisualStateGroupList() { vsGroup });
}
}`
I decided to use this 'adaptive state trigger' feature today. And quickly realized that it is not working properly
<Grid x:Name="PaneContainer" ColumnDefinitions="200, *">
<Grid
x:Name="LeftPane"
Grid.Column="0"
BackgroundColor="Green">
<Label
FontSize="22"
HorizontalOptions="Center"
Text="LEFT PANE"
TextColor="White"
VerticalOptions="Center" />
</Grid>
<Grid
x:Name="RightPane"
Grid.Column="1"
BackgroundColor="Orange">
<Label
FontSize="22"
HorizontalOptions="Center"
Text="RIGHT PANE"
TextColor="White"
VerticalOptions="Center" />
</Grid>
<VisualStateManager.VisualStateGroups>
<VisualStateGroupList>
<VisualStateGroup>
<VisualState x:Name="Portrait">
<VisualState.StateTriggers>
<OrientationStateTrigger Orientation="Portrait" />
</VisualState.StateTriggers>
<VisualState.Setters>
<Setter Property="BackgroundColor" Value="Silver" />
<Setter TargetName="RightPane" Property="Opacity" Value="0" />
<Setter TargetName="RightPane" Property="IsVisible" Value="False" />
</VisualState.Setters>
</VisualState>
<VisualState x:Name="Landscape">
<VisualState.StateTriggers>
<OrientationStateTrigger Orientation="Landscape" />
</VisualState.StateTriggers>
<VisualState.Setters>
<Setter Property="BackgroundColor" Value="White" />
</VisualState.Setters>
</VisualState>
</VisualStateGroup>
</VisualStateGroupList>
</VisualStateManager.VisualStateGroups>
</Grid>
Description
When paired with a
Setter
that has theTargetName
property, usingAdaptiveTrigger
can throw an exception that crashes the application if the trigger is hit when the page loads. The exception thrown isSteps to Reproduce
Device.SetFlags(new string[] { "StateTriggers_Experimental" });
to App.xaml.csExpected Behavior
The visual state is triggered, the effects from the Visual State are visible, because the width of the window/device is more than 200
Actual Behavior
The page crashes during loading, with the exception mentioned above.
Basic Information
This behavior is not present if the
Setter
doesn't have aTargetName
property set. My guess is the cause of this issue is the Setter is getting triggered by theAdaptiveTrigger
beforeInitializeComponent
is finished running. The behavior also works as expected if the window is small when the page is opened, then the width goes above 200 after the page is loaded (easy to test on UWP).