Skip to content

Commit

Permalink
fix: Fix NRE from x:Bind two-way through converter
Browse files Browse the repository at this point in the history
Fix NRE when accessing ValueType property in this binding scenario. (Also probably a couple of other would-be NREs as well.)
  • Loading branch information
davidjohnoliver committed Apr 13, 2021
1 parent da50b8f commit 101e5bf
Show file tree
Hide file tree
Showing 6 changed files with 273 additions and 58 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
<Page
x:Class="Uno.UI.Tests.Windows_UI_Xaml_Data.xBindTests.Controls.Binding_Converter_TwoWay"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="using:Uno.UI.Tests.Windows_UI_Xaml_Data.xBindTests.Controls"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
<Page.Resources>
<local:BoolToIntegerConverter x:Key="BoolToIntegerInverseConverter"
IsInverse="True" />
<local:InverseBoolConverter x:Key="InverseBoolConverter" />
</Page.Resources>
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>

<ListView x:Name="ViewToggleListView"
x:FieldModifier="public"
Margin="0,0,0,8"
SelectedIndex="{x:Bind ViewModel.ShowImages, Mode=TwoWay, Converter={StaticResource BoolToIntegerInverseConverter}, FallbackValue=0}">
<ListViewItem Padding="8,1,8,0">
<TextBlock Text="Image" />
</ListViewItem>
<ListViewItem Padding="8,1,8,0">
<TextBlock Text="List" />
</ListViewItem>
</ListView>

<CheckBox x:Name="BoundCheckBox"
x:FieldModifier="public"
IsChecked="{x:Bind ViewModel.ShowImages, Mode=OneWay}" />

<Grid Grid.Row="1">
<Border x:Name="ImageContent"
x:Load="{x:Bind ViewModel.ShowImages}">
<TextBlock Text="SHOWING IMAGES" />
</Border>
<Border x:Name="ListContent"
x:Load="{x:Bind ViewModel.ShowImages, Converter={StaticResource InverseBoolConverter}}">
<TextBlock Text="SHOWING LIST" />
</Border>
</Grid>
</Grid>
</Page>
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.IO;
using System.Linq;
using System.Runtime.InteropServices.WindowsRuntime;
using Windows.Foundation;
using Windows.Foundation.Collections;
using Windows.UI.Xaml;
using Windows.UI.Xaml.Controls;
using Windows.UI.Xaml.Controls.Primitives;
using Windows.UI.Xaml.Data;
using Windows.UI.Xaml.Input;
using Windows.UI.Xaml.Media;
using Windows.UI.Xaml.Navigation;

// The Blank Page item template is documented at https://go.microsoft.com/fwlink/?LinkId=234238

namespace Uno.UI.Tests.Windows_UI_Xaml_Data.xBindTests.Controls
{
/// <summary>
/// An empty page that can be used on its own or navigated to within a Frame.
/// </summary>
public sealed partial class Binding_Converter_TwoWay : Page
{
public TestViewModel ViewModel { get; }

public Binding_Converter_TwoWay()
{
this.InitializeComponent();

DataContext = ViewModel = new TestViewModel() { ShowImages = true };

//Loaded += MainPage_Loaded;
}

//private void MainPage_Loaded(object sender, Windows.UI.Xaml.RoutedEventArgs e)
//{
//}

public class TestViewModel : INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged;

public bool ShowImages
{
get { return _showImages; }
set
{
if (_showImages != value)
{
_showImages = value;
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(nameof(ShowImages)));
}
}
}
bool _showImages = false;
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Windows.UI.Xaml.Data;

namespace Uno.UI.Tests.Windows_UI_Xaml_Data.xBindTests.Controls
{
public class BoolToIntegerConverter : IValueConverter
{
public bool IsInverse { get; set; }

public object Convert(object value, Type targetType, object parameter, string language)
{
var boolValue = value as bool?;
if (!boolValue.HasValue)
{
return null;
}

if (IsInverse)
{
boolValue = !boolValue.Value;
}

return boolValue.Value ? 1 : 0;
}

public object ConvertBack(object value, Type targetType, object parameter, string language)
{
var intValue = value as int?;
if (!intValue.HasValue)
{
return null;
}

var result = intValue.Value >= 1;

if (IsInverse)
{
result = !result;
}

return result;
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Windows.UI.Xaml.Data;

namespace Uno.UI.Tests.Windows_UI_Xaml_Data.xBindTests.Controls
{
public class InverseBoolConverter : IValueConverter
{
public object Convert(object value, System.Type targetType, object parameter, string language)
{
if (value is bool)
{
return !(bool)value;
}

return null;
}

public object ConvertBack(object value, System.Type targetType, object parameter, string language)
{
if (value is bool)
{
return !(bool)value;
}

return null;
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -142,7 +142,7 @@ public void When_DataTemplate_TwoWay_Nested()

Assert.AreEqual(2, rootData.Model.MyIntProperty);
}

[TestMethod]
public void When_Object_TwoWay()
{
Expand Down Expand Up @@ -344,6 +344,31 @@ public void When_Converter()
Assert.AreEqual("v:Uno.UI.Tests.Windows_UI_Xaml_Data.xBindTests.Controls.Binding_Converter p:test", SUT.myTextBlock2.Text);
}

[TestMethod]
public void When_Converter_TwoWay()
{
var SUT = new Binding_Converter_TwoWay();

SUT.ForceLoaded();

ListView list = SUT.ViewToggleListView;

CheckBox cb = SUT.BoundCheckBox;

Assert.AreEqual(0, list.SelectedIndex);
Assert.IsTrue(cb.IsChecked.Value);

list.SelectedItem = list.Items[1];

Assert.AreEqual(1, list.SelectedIndex);
Assert.IsFalse(cb.IsChecked.Value);

list.SelectedItem = list.Items[0];

Assert.AreEqual(0, list.SelectedIndex);
Assert.IsTrue(cb.IsChecked.Value);
}

[TestMethod]
public void When_ConverterParameter()
{
Expand Down Expand Up @@ -479,7 +504,7 @@ public void When_DefaultBindingMode_TwoWay()
Assert.AreEqual("TwoWay updated 5", SUT.Default_TwoWay_OneWay_Property);
Assert.AreEqual("TwoWay updated 9", SUT.Default_TwoWay_TwoWay_Property);
}

[TestMethod]
public void When_DefaultBindingMode_Nested()
{
Expand Down
Loading

0 comments on commit 101e5bf

Please sign in to comment.