Xamarin MultiBindingには、上位の祖先レベルまたはXAMLツリー内の名前付きアイテムからのBindingContextが必要です

マーク・ウォーデル

実行時に設定される動的な行と列を持つ同種のボタンの長方形グリッドを構築しています。コードはXamarinにあります。すべての最新バージョンなど。プロジェクト全体はここからダウンロードできます:https//github.com/BicycleMark/XamSweeper私が抱えている問題は、XAMLのマルチバインディング部分です。レビューや提案は非常に優れています

Nested StackPanelsを使用して、次のようなグリッドを作成しました。

ここに画像の説明を入力してください

正しく表示されているボタンのサイズ変更するためのMultiValueConverterを作成することに成功しましたユニットテストでコンバーターをテストしましたが、期待どおりに機能します。[R、C]は各ボタンのテストで印刷されます。これらは正しくバインドされているモデルから取得されます

私が抱えている問題は、ボタンのサイズを計算する必要がある3つのアイテムにマルチバインディングをリンクすることです。

各ボタンは、これら3つのパラメーターを使用して計算されます

  1. ボタンを保持しているフレームの実際の幅
  2. モデルのボタン
  3. 各ボタン間の間隔またはパディング
  4. いずれかの[1..3]がヌルの場合はリターン50 <---これは私のバインディングが動作していないので、私は返す何ですか

各ボタン高さは、これら3つのパラメーターを使用して計算されます

  1. ボタンを保持しているフレームのActualHeight
  2. モデルのボタン
  3. 各ボタン間の間隔またはパディング
  4. いずれかの[1..3]がヌルの場合はリターン50 <---これは私のバインディングが動作していないので、私は返す何ですか

説明されているコンバーターは次のとおりです。

    public class SizeConverter : IMultiValueConverter
{
    public object Convert(object[] values, Type targetType, object parameter, CultureInfo culture)
    {
        if (values == null || values.Length <3 || values[2] == null || values[1] == null || values[0] == null)
            return 50;
        int numItems = (int)values[2];
        int separatorSize = (int)values[1]; 
        double frameSize = System.Convert.ToDouble(values[0]) ;
        
        int totalSeparatorSize = (numItems - 1) * separatorSize;
        int remainingArea = System.Convert.ToInt32(frameSize) - totalSeparatorSize;
        return remainingArea / numItems;
    }
    public object[] ConvertBack(object value, Type[] targetTypes, object parameter, CultureInfo culture)
    {
        throw new NotImplementedException();
    }
}

そして合格するそのユニットテスト:

 [DataRow(100, 2, 4)]
    [DataTestMethod]
    public void Test_Piece_Sizing(double frameSize, int separatorSize, int numItems)
    {
        var sizeConverter = new SizeConverter();
        object[] values = new object[] { frameSize, separatorSize, numItems };
        Assert.AreNotEqual(0,sizeConverter.Convert(values, typeof(int), null, System.Globalization.CultureInfo.CurrentCulture));
    }

目前の問題は、Xamarinで値をバインドするときにコンバーターがXAMLからNullを渡すことです。これがXAMLです。

    <?xml version="1.0" encoding="utf-8" ?>
<ContentPage 
    xmlns="http://xamarin.com/schemas/2014/forms"
    xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
    xmlns:prism="http://prismlibrary.com"
    prism:ViewModelLocator.AutowireViewModel="True"
    xmlns:local="clr-namespace:Sweeper.Controls;assembly=Sweeper"
    xmlns:cvt="clr-namespace:Sweeper.Views.Converters;assembly=Sweeper"
    x:Class="Sweeper.Views.GamePage"    
    Title="Game"
    x:Name="page">
    <ContentPage.Resources>
        <cvt:SizeConverter  x:Key="SizeConverter" />
        <cvt:CoordinateConverter x:Key="CoordinateConverter" />
    </ContentPage.Resources>
    <Frame BackgroundColor="DarkSeaGreen" CornerRadius="15" Padding="15">
        <Grid RowDefinitions="*,3*">
            <Frame Grid.Row="0" Padding="0">
                <Grid ColumnDefinitions="*,*,*" Padding="0" >
                    <Frame Grid.Column="0">
                        <Label HorizontalOptions="Center" VerticalOptions="Center">
                            <Label.Text>
                                <MultiBinding Converter="{StaticResource CoordinateConverter}">
                                    <Binding Path="Board.Rows" />
                                    <Binding Path="Board.Columns" />
                                </MultiBinding>
                            </Label.Text>
                        </Label>
                    </Frame>
                    <Frame Grid.Column="1">
                        <Button Text="Ok"></Button>
                    </Frame>
                    <Frame Grid.Column="2">
                        <Label HorizontalOptions="Center" VerticalOptions="Center" Text="{Binding Game.Time}"/>
                    </Frame>
                </Grid>
            </Frame>
            <Frame Grid.Row="1" x:Name="frameButtons" Padding="4" HasShadow="True" >
                <StackLayout HorizontalOptions="FillAndExpand" Orientation="Vertical" Spacing="4" 
                             BindableLayout.ItemsSource="{Binding Board.RowItems}">
                    <BindableLayout.ItemTemplate>
                        <DataTemplate>
                            <StackLayout BindableLayout.ItemsSource="{Binding}" Orientation="Horizontal" HorizontalOptions="Center">
                                <BindableLayout.ItemTemplate>
                                    <DataTemplate>
                                        <Frame Padding="0"  HasShadow="False" BackgroundColor="LightBlue" >
                                            <Button  Text="{Binding Name}" FontSize="Body" HorizontalOptions="Center" TextColor="Navy"/>
                                            <Frame.WidthRequest>
                                                <MultiBinding Converter="{StaticResource SizeConverter}" >
                                                    <MultiBinding.Bindings>
                                                        <Binding Source="x:Reference frameButtons" Path="ActualWidth" />
                                                        <Binding Source="x:Reference frameButtons" Path="Padding" />
                                                        <Binding Source="x:Reference frameButtons" Path="BindingContext.Board.Columns" />
                                                    </MultiBinding.Bindings>
                                                </MultiBinding>
                                            </Frame.WidthRequest>
                                            <Frame.HeightRequest>
                                                <MultiBinding Converter="{StaticResource SizeConverter}" >
                                                    <MultiBinding.Bindings>
                                                        <Binding Source="x:Reference frameButtons" Path="ActualHeight"/>
                                                        <Binding Source="x:Reference frameButtons" Path="Padding" />
                                                        <Binding Source="x:Reference frameButtons" Path="BindingContext.Board.Rows" />
                                                    </MultiBinding.Bindings>
                                                </MultiBinding>
                                            </Frame.HeightRequest>
                                        </Frame >
                                    </DataTemplate>
                                </BindableLayout.ItemTemplate>
                            </StackLayout>
                        </DataTemplate>
                    </BindableLayout.ItemTemplate>
                </StackLayout>
            </Frame>
        </Grid>
    </Frame>
</ContentPage>

コンバーターが呼び出されていますが、毎回3つのnullを渡しています。これは私が修復しようとしているバインディングエラーです

プロジェクト全体はここからダウンロードできます:https//github.com/BicycleMark/XamSweeper

Leo Zhu-MSFT

コンバーターが呼び出されていますが、毎回3つのnullを渡しています。

BindingContextFrameように設定しみてください

<Frame Padding="0"  HasShadow="False" BackgroundColor="LightBlue" BindingContext="{x:Reference frameButtons}">
   <Button  Text="{Binding Name}" FontSize="Body" HorizontalOptions="Center" TextColor="Navy" Clicked="Button_Clicked"/>
   <Frame.WidthRequest>
      <MultiBinding Converter="{StaticResource SizeConverter}" >

         <MultiBinding.Bindings>
           <Binding Path="ActualWidth" />
           <Binding Path="Padding" />
           <Binding Path="BindingContext.Board.Columns" />
         </MultiBinding.Bindings>
      </MultiBinding>
   </Frame.WidthRequest>
   <Frame.HeightRequest>
      <MultiBinding Converter="{StaticResource SizeConverter}" >
         <MultiBinding.Bindings>
           <Binding Path="ActualHeight" />
           <Binding Path="Padding" />
           <Binding Path="BindingContext.Board.Rows" />
         </MultiBinding.Bindings>
      </MultiBinding>
    </Frame.HeightRequest>
 </Frame >

次に、の値を取得できますConverter

しかしActualWidth、既存のバインド可能なプロパティではないようです。

この記事はインターネットから収集されたものであり、転載の際にはソースを示してください。

侵害の場合は、連絡してください[email protected]

編集
0

コメントを追加

0

関連記事

Related 関連記事

ホットタグ

アーカイブ