國內的WPF技術先行者周銀輝曾介紹過如何動態改變應用程序的主題樣式,今天咱們來介紹一種輕量級的改變界面風格的方式——動態改變主題色。
程序容許用戶根據本身的喜愛來對界面進行配色,這種技術在不少軟件中都有應用,好比這款名爲AirPlay的音樂播放器軟件:html
下面咱們就來本身動手實現這種技術:
首先在App.xaml文件中定義一個鍵值爲「color」的單色筆刷,這個筆刷就是能夠被用戶改變的動態資源:ide
<SolidColorBrush x:Key="color" Color="SkyBlue" />post
而後來設計這樣一個界面:ui
咱們讓用戶經過4個滑塊來分別定製顏色的A、R、G、B值,其完整代碼爲:this
<Grid>url
<Grid.RowDefinitions>spa
<RowDefinition Height="28" />設計
<RowDefinition Height="28" />3d
<RowDefinition Height="28" />htm
<RowDefinition Height="28" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="65*" />
<ColumnDefinition Width="213*" />
</Grid.ColumnDefinitions>
<Label Grid.Row="0" HorizontalContentAlignment="Right">透明度:</Label>
<Label Grid.Row="1" HorizontalContentAlignment="Right">紅色:</Label>
<Label Grid.Row="2" HorizontalContentAlignment="Right">綠色:</Label>
<Label Grid.Row="3" HorizontalContentAlignment="Right">藍色:</Label>
<Slider Grid.Row="0" Grid.Column="1" Margin="3" Name="a" SmallChange="1" LargeChange="15" Maximum="255" Value="255" />
<Slider Grid.Row="1" Grid.Column="1" Margin="3" Name="r" SmallChange="1" LargeChange="15" Maximum="255" Value="255" />
<Slider Grid.Row="2" Grid.Column="1" Margin="3" Name="g" SmallChange="1" LargeChange="15" Maximum="255" Value="255" />
<Slider Grid.Row="3" Grid.Column="1" Margin="3" Name="b" SmallChange="1" LargeChange="15" Maximum="255" Value="255" />
<Button Grid.Column="1" Grid.Row="4" HorizontalAlignment="Left" Margin="3,5,0,5" Name="button1" Width="75" Click="button1_Click">更新顏色</Button>
</Grid>
需注意,要把滑塊的最大值設爲255。
而後回到App.xaml中,咱們來定義窗口、標籤及按鈕的樣式:
窗口樣式代碼以下:
<Style x:Key="window" TargetType="Window">
<Setter Property="OverridesDefaultStyle" Value="true" />
<Setter Property="AllowsTransparency" Value="true" />
<Setter Property="SnapsToDevicePixels" Value="true" />
<Setter Property="WindowStyle" Value="None" />
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="Window">
<Border BorderBrush="{DynamicResource color}" BorderThickness="3" CornerRadius="5" Padding="4">
<Border BorderBrush="{DynamicResource color}" BorderThickness="3" CornerRadius="5" Background="{DynamicResource color}">
<Border BorderBrush="#1000" BorderThickness="3" CornerRadius="5" Padding="6">
<Border.Background>
<LinearGradientBrush StartPoint="0,0" EndPoint="0,1">
<GradientStop Color="#3FFF" Offset="0.5" />
<GradientStop Color="#1666" Offset="0.5" />
</LinearGradientBrush>
</Border.Background>
<ContentPresenter />
</Border>
</Border>
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
定義樣式爲幾個Border進行嵌套,在最底層引用的以前定義的單色筆刷,在上層用低不透明度的白色和黑色覆蓋以產生不一樣的層次效果。
標籤樣式爲:
<Style TargetType="Label">
<Setter Property="Foreground" Value="#AAFFFFFF" />
</Style>
按鈕樣式爲:
<Style TargetType="Button">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="Button">
<Border Background="{DynamicResource color}" CornerRadius="3">
<Border BorderThickness="2" CornerRadius="3" Padding="{TemplateBinding Padding}">
<Border.Background>
<LinearGradientBrush StartPoint="0,0" EndPoint="0,1">
<GradientStop Color="#6FFF" Offset="0" />
<GradientStop Color="#2000" Offset="1" />
</LinearGradientBrush>
</Border.Background>
<Border.BorderBrush>
<LinearGradientBrush StartPoint="0,0" EndPoint="0,1">
<GradientStop Color="#1000" Offset="0" />
<GradientStop Color="#4000" Offset="1" />
</LinearGradientBrush>
</Border.BorderBrush>
<TextBlock TextAlignment="Center" Foreground="#AFFF"><ContentPresenter /></TextBlock>
</Border>
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
其原理與窗口樣式相同。
而後回到主界面設計窗口,設置窗體的樣式:
Style="{StaticResource window}"
接下來編輯後臺代碼,首先爲窗體增長事件處理以提供拖動功能:
MouseLeftButtonDown="Window_MouseLeftButtonDown"
後臺事件處理代碼:
private void Window_MouseLeftButtonDown(object sender, MouseButtonEventArgs e)
{
this.DragMove();
}
爲按鈕增長事件處理來更新界面顏色:
private void button1_Click(object sender, RoutedEventArgs e)
{
更新顏色(Color.FromArgb((byte)a.Value, (byte)r.Value, (byte)g.Value, (byte)b.Value));
}
「更新顏色」方法代碼以下:
public void 更新顏色(Color c)
{
this.Resources.Remove("color");
this.Resources.Add("color", new SolidColorBrush(c));
}
此方法首先移除資源「color」,而後再添加一個同名的新筆刷,這樣就完成了動態替換工做。
如今編譯並執行程序,能夠看到以下效果: