Solución:
En WPF hay ciertos controles de ‘contenedor’ que cambian automáticamente el tamaño de su contenido y hay algunos que no lo hacen.
Aquí hay algunos que lo hacen no cambiar el tamaño de su contenido (supongo que está utilizando uno o más de estos):
StackPanel
WrapPanel
Canvas
TabControl
Aquí hay algunos que hacer cambiar el tamaño de su contenido:
Grid
UniformGrid
DockPanel
Por tanto, casi siempre es preferible utilizar un Grid
en lugar de un StackPanel
a menos que hagas no desea que se produzca un cambio de tamaño automático. Tenga en cuenta que todavía es posible Grid
para no el tamaño de sus controles internos … todo depende de su Grid.RowDefinition
y Grid.ColumnDefinition
ajustes:
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="100" /> <!--<<< Exact Height... won't resize -->
<RowDefinition Height="Auto" /> <!--<<< Will resize to the size of contents -->
<RowDefinition Height="*" /> <!--<<< Will resize taking all remaining space -->
</Grid.RowDefinitions>
</Grid>
Puede obtener más información sobre el Grid
control desde el Grid
Página de clase en MSDN. También puede obtener más información sobre estos controles de contenedor en la página Descripción general de controles de contenedor de WPF en MSDN.
Se puede lograr un cambio de tamaño adicional utilizando el FrameworkElement.HorizontalAlignment
y FrameworkElement.VerticalAlignment
propiedades. El valor predeterminado de estas propiedades es Stretch
que estirará los elementos para que se ajusten al tamaño de los controles que los contienen. Sin embargo, cuando se establecen en cualquier otro valor, los elementos no estirarse.
ACTUALIZAR >>>
En respuesta a las preguntas de su comentario:
Utilizar el Grid.RowDefinition
y Grid.ColumnDefinition
configuraciones para organizar una estructura básica primero … es común agregar Grid
controles en las celdas del exterior Grid
controles si es necesario. También puede utilizar el Grid.ColumnSpan
y Grid.RowSpan
propiedades para permitir que los controles abarquen varias columnas y / o filas de un Grid
.
Es más común tener al menos una fila / columna con un Height
/Width
de "*"
que llenará todo el espacio restante, pero puede tener dos o más con esta configuración, en cuyo caso el espacio restante se dividirá entre las dos (o más) filas / columnas. ‘Auto’ es una buena configuración para las filas / columnas que no están configuradas en ‘”*”‘, pero realmente depende de cómo desee que sea el diseño.
No hay Auto
configuración que puede utilizar en los controles de las celdas, pero esto es igual de bueno, porque queremos que el Grid
ajustar el tamaño de los controles para nosotros … por lo tanto, no queremos establecer el Height
o Width
de estos controles en absoluto.
El punto que hice sobre el FrameworkElement.HorizontalAlignment
y FrameworkElement.VerticalAlignment
properties fue solo para informarle de su existencia … ya que su valor predeterminado ya es Stretch
, por lo general, no es necesario establecerlos explícitamente.
los Margin
La propiedad generalmente solo se usa para espaciar sus controles de manera uniforme … si arrastra y suelta controles desde Visual Studio Toolbox, VS establecerá el Margin
propiedad para colocar su control exactamente donde lo dejó caer, pero en general, esto es no lo que queremos, ya que interferirá con el tamaño automático de los controles. Si hace esto, simplemente elimine o edite el Margin
propiedad a la medida de sus necesidades.
Bueno, es bastante sencillo de hacer.
En el controlador de eventos de cambio de tamaño de la ventana, calcule cuánto ha crecido / encogido la ventana y use esa fracción para ajustar 1) Alto, 2) Ancho, 3) Canvas.Top, 4) Canvas.Left propiedades de todos los controles secundarios dentro del lienzo.
Aquí está el código:
private void window1_SizeChanged(object sender, SizeChangedEventArgs e)
{
myCanvas.Width = e.NewSize.Width;
myCanvas.Height = e.NewSize.Height;
double xChange = 1, yChange = 1;
if (e.PreviousSize.Width != 0)
xChange = (e.NewSize.Width/e.PreviousSize.Width);
if (e.PreviousSize.Height != 0)
yChange = (e.NewSize.Height / e.PreviousSize.Height);
foreach (FrameworkElement fe in myCanvas.Children )
{
/*because I didn't want to resize the grid I'm having inside the canvas in this particular instance. (doing that from xaml) */
if (fe is Grid == false)
{
fe.Height = fe.ActualHeight * yChange;
fe.Width = fe.ActualWidth * xChange;
Canvas.SetTop(fe, Canvas.GetTop(fe) * yChange);
Canvas.SetLeft(fe, Canvas.GetLeft(fe) * xChange);
}
}
}
Pensé en compartir esto con cualquiera que necesite más claridad sobre cómo lograrlo:
myCanvas es un control Canvas y padre de todos los demás controladores. Este código funciona para cambiar el tamaño de forma ordenada a cualquier resolución desde 1366 x 768 en adelante. Probado hasta una resolución de 4k 4096 x 2160
Tome nota de todas las configuraciones de propiedades de MainWindow (WindowStartupLocation, SizeToContent y WindowState) – importante para que esto funcione correctamente – Se maximizó el requisito de WindowState para mi caso de usuario
xaml
<Window x:Name="mainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="clr-namespace:MyApp"
xmlns:ed="http://schemas.microsoft.com/expression/2010/drawing"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d"
x:Class="MyApp.MainWindow"
Title="MainWindow" SizeChanged="MainWindow_SizeChanged"
Width="1366" Height="768" WindowState="Maximized" WindowStartupLocation="CenterOwner" SizeToContent="WidthAndHeight">
<Canvas x:Name="myCanvas" HorizontalAlignment="Left" Height="768" VerticalAlignment="Top" Width="1356">
<Image x:Name="maxresdefault_1_1__jpg" Source="maxresdefault-1[1].jpg" Stretch="Fill" Opacity="0.6" Height="767" Canvas.Left="-6" Width="1366"/>
<Separator Margin="0" Background="#FF302D2D" Foreground="#FF111010" Height="0" Canvas.Left="-811" Canvas.Top="148" Width="766"/>
<Separator Margin="0" Background="#FF302D2D" Foreground="#FF111010" HorizontalAlignment="Right" Width="210" Height="0" Canvas.Left="1653" Canvas.Top="102"/>
<Image x:Name="imgscroll" Source="BcaKKb47i[1].png" Stretch="Fill" RenderTransformOrigin="0.5,0.5" Height="523" Canvas.Left="-3" Canvas.Top="122" Width="580">
<Image.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform Angle="89.093"/>
<TranslateTransform/>
</TransformGroup>
</Image.RenderTransform>
</Image>
.cs
private void MainWindow_SizeChanged(object sender, SizeChangedEventArgs e)
{
myCanvas.Width = e.NewSize.Width;
myCanvas.Height = e.NewSize.Height;
double xChange = 1, yChange = 1;
if (e.PreviousSize.Width != 0)
xChange = (e.NewSize.Width / e.PreviousSize.Width);
if (e.PreviousSize.Height != 0)
yChange = (e.NewSize.Height / e.PreviousSize.Height);
ScaleTransform scale = new ScaleTransform(myCanvas.LayoutTransform.Value.M11 * xChange, myCanvas.LayoutTransform.Value.M22 * yChange);
myCanvas.LayoutTransform = scale;
myCanvas.UpdateLayout();
}