我正忙于将WPF解决方案迁移到Windows应用商店应用。该解决方案使用了App中没有的ViewPort3D
开发所以我试图使用PlaneProjection
转换它。
目标是实现一个可以使用故事板围绕一个轴旋转的立方体。我对立方体的两侧没有任何问题 但顶部的矩形让我很头疼。
我制作了一个测试集来可视化我的问题。如果您创建一个新的blanc Windows应用商店应用(不是电话)并将其命名为PlaneTest
,那么将XAML粘贴到
您的整个MainPage.xaml
并将C#类放在MainPage.xaml.cs
。
XAML:
<Page
x:Class="PlaneTest.MainPage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="using:PlaneTest"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="500"/>
<ColumnDefinition Width="700"/>
</Grid.ColumnDefinitions>
<Grid.Resources>
<Style TargetType="Slider">
<Setter Property="Width" Value="400"/>
<Setter Property="Height" Value="23"/>
</Style>
<Style TargetType="TextBlock">
<Setter Property="Margin" Value="0,5,0,0"/>
</Style>
</Grid.Resources>
<StackPanel Orientation="Vertical" Width="450" Grid.Column="0">
<TextBlock Text="CUBE SLIDERS" Margin="25"></TextBlock>
<TextBlock Text="Rotation X = 23. CUBE ROTATES AROUND THIS AXIS."></TextBlock>
<Slider Name="RotateX" Minimum="-90" Maximum="90" Value="23"></Slider>
<TextBlock Text="Rotation Y = -25"></TextBlock>
<Slider Name="RotateY" Minimum="-90" Maximum="90" Value="-25"></Slider>
<TextBlock Text="Rotation Z = -90"></TextBlock>
<Slider Name="RotateZ" Minimum="-90" Maximum="90" Value="-90"></Slider>
<TextBlock Text="TOP RECTANGLE" Margin="25,50,0,0"></TextBlock>
<TextBlock Text="Rotation X"></TextBlock>
<Slider Name="TopRotateX" Minimum="-180" Maximum="180"></Slider>
<TextBlock Text="Rotation Y"></TextBlock>
<Slider Name="TopRotateY" Minimum="-180" Maximum="180"></Slider>
<TextBlock Text="Rotation Z"></TextBlock>
<Slider Name="TopRotateZ" Minimum="-180" Maximum="180"></Slider>
<TextBlock Text="Center Of Rotation X" Margin="0,40,0,0"></TextBlock>
<Slider Name="CenterOfXRotation" Value="0.5" Minimum="0" Maximum="1" StepFrequency="0.1"></Slider>
<TextBlock Text="Center Of Rotation Y"></TextBlock>
<Slider Name="CenterOfYRotation" Value="0.5" Minimum="0" Maximum="1" StepFrequency="0.1"></Slider>
<TextBlock Text="Center Of Rotation Z"></TextBlock>
<Slider Name="CenterOfZRotation" Value="200" Minimum="-200" Maximum="200"></Slider>
<TextBlock Text="GlobalOffSet X" Margin="0,40,0,0"></TextBlock>
<Slider Name="GlobalXOffSet" Minimum="-200" Maximum="200" ></Slider>
<TextBlock Text="GlobalOffSet Y"></TextBlock>
<Slider Name="GlobalYOffSet" Width="400" Height="23" Minimum="-200" Maximum="200"></Slider>
<TextBlock Text="GlobalOffSet Z"></TextBlock>
<Slider Name="GlobalZOffSet" Minimum="-200" Maximum="200"></Slider>
</StackPanel>
<Grid x:Name="LayoutRoot" Grid.Column="1">
<Grid.Resources>
<Style TargetType="Rectangle">
<Setter Property="Height" Value="400"/>
<Setter Property="Width" Value="400"/>
</Style>
<local:RotationXOffset x:Key="rotationXOffset"/>
</Grid.Resources>
<Rectangle Fill="#a0FF0000" Name="Side1">
<Rectangle.Projection>
<PlaneProjection CenterOfRotationZ="200"
RotationX="{Binding ElementName=RotateX, Path=Value, Converter={StaticResource rotationXOffset}, ConverterParameter='-90'}"
RotationY="{Binding ElementName=RotateY, Path=Value}"
RotationZ="{Binding ElementName=RotateZ,Path=Value}"/>
</Rectangle.Projection>
</Rectangle>
<Rectangle Fill="#a00000FF" Name="Side2">
<Rectangle.Projection>
<PlaneProjection CenterOfRotationZ="200"
RotationX="{Binding ElementName=RotateX, Path=Value, Converter={StaticResource rotationXOffset}, ConverterParameter='-0'}"
RotationY="{Binding ElementName=RotateY, Path=Value}"
RotationZ="{Binding ElementName=RotateZ, Path=Value}"/>
</Rectangle.Projection>
</Rectangle>
<Rectangle Fill="#a0EFFF30" Name="Side3">
<Rectangle.Projection>
<PlaneProjection CenterOfRotationZ="200"
RotationX="{Binding ElementName=RotateX, Path=Value, Converter={StaticResource rotationXOffset}, ConverterParameter='90'}"
RotationY="{Binding ElementName=RotateY, Path=Value}"
RotationZ="{Binding ElementName=RotateZ, Path=Value}"/>
</Rectangle.Projection>
</Rectangle>
<Rectangle Fill="#af00FF00" Name="Side4">
<Rectangle.Projection>
<PlaneProjection CenterOfRotationZ="200"
RotationX="{Binding ElementName=RotateX, Path=Value, Converter={StaticResource rotationXOffset}, ConverterParameter='180'}"
RotationY="{Binding ElementName=RotateY, Path=Value}"
RotationZ="{Binding ElementName=RotateZ, Path=Value}"/>
</Rectangle.Projection>
</Rectangle>
<Rectangle Fill="Orange" Name="Top">
<Rectangle.Projection>
<PlaneProjection
CenterOfRotationX="{Binding ElementName=CenterOfXRotation, Path=Value}"
CenterOfRotationY="{Binding ElementName=CenterOfYRotation, Path=Value}"
CenterOfRotationZ="{Binding ElementName=CenterOfZRotation, Path=Value}"
GlobalOffsetX="{Binding ElementName=GlobalXOffSet, Path=Value}"
GlobalOffsetY="{Binding ElementName=GlobalYOffSet, Path=Value}"
GlobalOffsetZ="{Binding ElementName=GlobalZOffSet, Path=Value}"
RotationX="{Binding ElementName=TopRotateX, Path=Value}"
RotationY="{Binding ElementName=TopRotateY, Path=Value}"
RotationZ="{Binding ElementName=TopRotateZ, Path=Value}" />
</Rectangle.Projection>
</Rectangle>
</Grid>
</Grid>
</Page>
C#
class RotationXOffset : IValueConverter
{
object IValueConverter.Convert(object value, Type targetType, object parameter, string language)
{
return (double)value + Convert.ToDouble(parameter);
}
object IValueConverter.ConvertBack(object value, Type targetType, object parameter, string language)
{
throw new NotImplementedException();
}
}
如果您没有触及3个顶部滑块,请尝试使用其他滑块将橙色顶部矩形放在立方体顶部。 我不能。
当我将旋转X最顶部滑块移动到0或90时,我可以适合顶部,但不能与任何其他值一起移动。
我究竟做错了什么?甚至可以使用PlaneProjection
吗?
我是否遇到了仿射转换限制?
http://www.charlespetzold.com/blog/2009/01/Non-Affine-Transforms-in-Silverlight.html
答案 0 :(得分:0)
与此同时,我正在研究另一个项目,现在回到这个解决方案,我又看了一遍。
使用这个XAML和问题的值转换器,它可以正常工作。
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="500"/>
<ColumnDefinition Width="700"/>
</Grid.ColumnDefinitions>
<Grid.Resources>
<Style TargetType="Slider">
<Setter Property="Width" Value="400"/>
<Setter Property="Height" Value="23"/>
</Style>
<Style TargetType="TextBlock">
<Setter Property="Margin" Value="0,5,0,0"/>
</Style>
</Grid.Resources>
<StackPanel Orientation="Vertical" Width="450" Grid.Column="0">
<TextBlock Text="CUBE SLIDERS" Margin="25"></TextBlock>
<TextBlock Text="Rotation X = 23. CUBE ROTATES AROUND THIS AXIS."></TextBlock>
<Slider Name="RotateX" Minimum="-90" Maximum="90" Value="23"></Slider>
<TextBlock Text="Rotation Y = -25"></TextBlock>
<Slider Name="RotateY" Minimum="-90" Maximum="90" Value="-25"></Slider>
<TextBlock Text="Rotation Z = -90"></TextBlock>
<Slider Name="RotateZ" Minimum="-90" Maximum="90" Value="-90"></Slider>
</StackPanel>
<Grid x:Name="LayoutRoot" Grid.Column="1">
<Grid.Resources>
<Style TargetType="Rectangle">
<Setter Property="Height" Value="400"/>
<Setter Property="Width" Value="400"/>
</Style>
<local:RotationXOffset x:Key="rotationXOffset"/>
</Grid.Resources>
<Rectangle Fill="#a0FF0000" Name="Side1">
<Rectangle.Projection>
<PlaneProjection CenterOfRotationZ="200"
RotationX="{Binding ElementName=RotateX, Path=Value, Converter={StaticResource rotationXOffset}, ConverterParameter='-90'}"
RotationY="{Binding ElementName=RotateY, Path=Value}"
RotationZ="{Binding ElementName=RotateZ,Path=Value}"/>
</Rectangle.Projection>
</Rectangle>
<Rectangle Fill="#a00000FF" Name="Side2">
<Rectangle.Projection>
<PlaneProjection CenterOfRotationZ="200"
RotationX="{Binding ElementName=RotateX, Path=Value, Converter={StaticResource rotationXOffset}, ConverterParameter='-0'}"
RotationY="{Binding ElementName=RotateY, Path=Value}"
RotationZ="{Binding ElementName=RotateZ, Path=Value}"/>
</Rectangle.Projection>
</Rectangle>
<Rectangle Fill="#a0EFFF30" Name="Side3">
<Rectangle.Projection>
<PlaneProjection CenterOfRotationZ="200"
RotationX="{Binding ElementName=RotateX, Path=Value, Converter={StaticResource rotationXOffset}, ConverterParameter='90'}"
RotationY="{Binding ElementName=RotateY, Path=Value}"
RotationZ="{Binding ElementName=RotateZ, Path=Value}"/>
</Rectangle.Projection>
</Rectangle>
<Rectangle Fill="#af00FF00" Name="Side4">
<Rectangle.Projection>
<PlaneProjection CenterOfRotationZ="200"
RotationX="{Binding ElementName=RotateX, Path=Value, Converter={StaticResource rotationXOffset}, ConverterParameter='180'}"
RotationY="{Binding ElementName=RotateY, Path=Value}"
RotationZ="{Binding ElementName=RotateZ, Path=Value}"/>
</Rectangle.Projection>
</Rectangle>
</Grid>
<Grid Grid.Column="1">
<Grid.Projection>
<PlaneProjection RotationX="115" CenterOfRotationZ="200"/>
</Grid.Projection>
<Rectangle Fill="Orange" Name="Top" Height="400" Width="400" >
<Rectangle.Projection>
<PlaneProjection RotationZ="{Binding ElementName=RotateX, Path=Value}"/>
</Rectangle.Projection>
</Rectangle>
</Grid>
</Grid>