Skip to content

Commit 83fc434

Browse files
committed
enhance: Growl demo.
1 parent 8405e7f commit 83fc434

File tree

5 files changed

+165
-68
lines changed

5 files changed

+165
-68
lines changed

src/Shared/HandyControlDemo_Shared/App.xaml

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,12 +2,12 @@
22
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
33
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
44
xmlns:viewModel="clr-namespace:HandyControlDemo.ViewModel"
5-
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
5+
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
66
xmlns:d1P1="http://schemas.openxmlformats.org/markup-compatibility/2006"
77
xmlns:data="clr-namespace:HandyControlDemo.Data"
88
xmlns:hc="https://handyorg.github.io/handycontrol"
99
xmlns:langs="clr-namespace:HandyControlDemo.Properties.Langs"
10-
d1P1:Ignorable="d"
10+
d1P1:Ignorable="d"
1111
StartupUri="MainWindow.xaml">
1212
<Application.Resources>
1313
<ResourceDictionary>
@@ -30,6 +30,7 @@
3030
<hc:EnumDataProvider x:Key="DemoTypes" Type="data:DemoType"/>
3131
<hc:EnumDataProvider x:Key="ShowAnimations" Type="hc:ShowAnimation"/>
3232
<hc:EnumDataProvider x:Key="HatchStyles" Type="hc:HatchStyle"/>
33+
<hc:EnumDataProvider x:Key="TransitionModes" Type="hc:TransitionMode"/>
3334
</ResourceDictionary>
3435
</Application.Resources>
3536
</Application>

src/Shared/HandyControlDemo_Shared/UserControl/Controls/GrowlDemo.xaml

Lines changed: 71 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -7,30 +7,82 @@
77
DataContext="{Binding GrowlDemo,Source={StaticResource Locator}}"
88
Background="{DynamicResource RegionBrush}">
99
<hc:TransitioningContentControl>
10-
<StackPanel Margin="32">
11-
<GroupBox Header="Window" Padding="10,5">
10+
<hc:UniformSpacingPanel Margin="32"
11+
Orientation="Vertical"
12+
Spacing="32">
13+
<ComboBox SelectedValue="{Binding TransitionMode}"
14+
ItemsSource="{Binding Source={StaticResource TransitionModes}}" />
15+
<GroupBox Header="Window"
16+
Padding="10,5">
1217
<WrapPanel VerticalAlignment="Center">
13-
<Button Command="{Binding InfoCmd}" Content="{ex:Lang Key={x:Static langs:LangKeys.Info}}" Margin="0,5,5,5" Style="{StaticResource ButtonInfo}"/>
14-
<Button Command="{Binding SuccessCmd}" Content="{ex:Lang Key={x:Static langs:LangKeys.Success}}" Margin="5" Style="{StaticResource ButtonSuccess}"/>
15-
<Button Command="{Binding WarningCmd}" Content="{ex:Lang Key={x:Static langs:LangKeys.Warning}}" Margin="5" Style="{StaticResource ButtonWarning}"/>
16-
<Button Command="{Binding ErrorCmd}" Content="{ex:Lang Key={x:Static langs:LangKeys.Error}}" Margin="5" Style="{StaticResource ButtonDanger}"/>
17-
<Button Command="{Binding AskCmd}" Content="{ex:Lang Key={x:Static langs:LangKeys.Ask}}" Margin="5" Background="BlueViolet" Foreground="White" BorderThickness="0"/>
18-
<Button Command="{Binding FatalCmd}" Content="{ex:Lang Key={x:Static langs:LangKeys.Fatal}}" Margin="5,0"/>
19-
<Button Command="{Binding ClearCmd}" Content="{ex:Lang Key={x:Static langs:LangKeys.Clear}}" Margin="5,0,0,0" Style="{StaticResource ButtonPrimary}"/>
18+
<Button Command="{Binding InfoCmd}"
19+
Content="{ex:Lang Key={x:Static langs:LangKeys.Info}}"
20+
Margin="0,5,5,5"
21+
Style="{StaticResource ButtonInfo}" />
22+
<Button Command="{Binding SuccessCmd}"
23+
Content="{ex:Lang Key={x:Static langs:LangKeys.Success}}"
24+
Margin="5"
25+
Style="{StaticResource ButtonSuccess}" />
26+
<Button Command="{Binding WarningCmd}"
27+
Content="{ex:Lang Key={x:Static langs:LangKeys.Warning}}"
28+
Margin="5"
29+
Style="{StaticResource ButtonWarning}" />
30+
<Button Command="{Binding ErrorCmd}"
31+
Content="{ex:Lang Key={x:Static langs:LangKeys.Error}}"
32+
Margin="5"
33+
Style="{StaticResource ButtonDanger}" />
34+
<Button Command="{Binding AskCmd}"
35+
Content="{ex:Lang Key={x:Static langs:LangKeys.Ask}}"
36+
Margin="5"
37+
Background="BlueViolet"
38+
Foreground="White"
39+
BorderThickness="0" />
40+
<Button Command="{Binding FatalCmd}"
41+
Content="{ex:Lang Key={x:Static langs:LangKeys.Fatal}}"
42+
Margin="5,0" />
43+
<Button Command="{Binding ClearCmd}"
44+
Content="{ex:Lang Key={x:Static langs:LangKeys.Clear}}"
45+
Margin="5,0,0,0"
46+
Style="{StaticResource ButtonPrimary}" />
2047
</WrapPanel>
2148
</GroupBox>
22-
<Button Command="{Binding NewWindowCmd}" Content="{ex:Lang Key={x:Static langs:LangKeys.NewWindow}}" Margin="0,32" HorizontalAlignment="Left"/>
23-
<GroupBox Header="Desktop" Padding="10,5">
49+
<Button Command="{Binding NewWindowCmd}"
50+
Content="{ex:Lang Key={x:Static langs:LangKeys.NewWindow}}"
51+
HorizontalAlignment="Left" />
52+
<GroupBox Header="Desktop"
53+
Padding="10,5">
2454
<WrapPanel VerticalAlignment="Center">
25-
<Button Command="{Binding InfoGlobalCmd}" Content="{ex:Lang Key={x:Static langs:LangKeys.Info}}" Margin="0,5,5,5" Style="{StaticResource ButtonInfo}"/>
26-
<Button Command="{Binding SuccessGlobalCmd}" Content="{ex:Lang Key={x:Static langs:LangKeys.Success}}" Margin="5" Style="{StaticResource ButtonSuccess}"/>
27-
<Button Command="{Binding WarningGlobalCmd}" Content="{ex:Lang Key={x:Static langs:LangKeys.Warning}}" Margin="5" Style="{StaticResource ButtonWarning}"/>
28-
<Button Command="{Binding ErrorGlobalCmd}" Content="{ex:Lang Key={x:Static langs:LangKeys.Error}}" Margin="5" Style="{StaticResource ButtonDanger}"/>
29-
<Button Command="{Binding AskGlobalCmd}" Content="{ex:Lang Key={x:Static langs:LangKeys.Ask}}" Margin="5" Background="BlueViolet" Foreground="White" BorderThickness="0"/>
30-
<Button Command="{Binding FatalGlobalCmd}" Content="{ex:Lang Key={x:Static langs:LangKeys.Fatal}}" Margin="5,0"/>
31-
<Button Command="{Binding ClearGlobalCmd}" Content="{ex:Lang Key={x:Static langs:LangKeys.Clear}}" Margin="5,0,0,0" Style="{StaticResource ButtonPrimary}"/>
55+
<Button Command="{Binding InfoGlobalCmd}"
56+
Content="{ex:Lang Key={x:Static langs:LangKeys.Info}}"
57+
Margin="0,5,5,5"
58+
Style="{StaticResource ButtonInfo}" />
59+
<Button Command="{Binding SuccessGlobalCmd}"
60+
Content="{ex:Lang Key={x:Static langs:LangKeys.Success}}"
61+
Margin="5"
62+
Style="{StaticResource ButtonSuccess}" />
63+
<Button Command="{Binding WarningGlobalCmd}"
64+
Content="{ex:Lang Key={x:Static langs:LangKeys.Warning}}"
65+
Margin="5"
66+
Style="{StaticResource ButtonWarning}" />
67+
<Button Command="{Binding ErrorGlobalCmd}"
68+
Content="{ex:Lang Key={x:Static langs:LangKeys.Error}}"
69+
Margin="5"
70+
Style="{StaticResource ButtonDanger}" />
71+
<Button Command="{Binding AskGlobalCmd}"
72+
Content="{ex:Lang Key={x:Static langs:LangKeys.Ask}}"
73+
Margin="5"
74+
Background="BlueViolet"
75+
Foreground="White"
76+
BorderThickness="0" />
77+
<Button Command="{Binding FatalGlobalCmd}"
78+
Content="{ex:Lang Key={x:Static langs:LangKeys.Fatal}}"
79+
Margin="5,0" />
80+
<Button Command="{Binding ClearGlobalCmd}"
81+
Content="{ex:Lang Key={x:Static langs:LangKeys.Clear}}"
82+
Margin="5,0,0,0"
83+
Style="{StaticResource ButtonPrimary}" />
3284
</WrapPanel>
3385
</GroupBox>
34-
</StackPanel>
86+
</hc:UniformSpacingPanel>
3587
</hc:TransitioningContentControl>
3688
</UserControl>

src/Shared/HandyControlDemo_Shared/ViewModel/Controls/GrowlDemoViewModel.cs

Lines changed: 22 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,18 @@
11
using System.Windows;
2+
using GalaSoft.MvvmLight;
23
using GalaSoft.MvvmLight.Command;
34
using HandyControl.Controls;
45
using HandyControl.Data;
56
using HandyControlDemo.Window;
67

78
namespace HandyControlDemo.ViewModel;
89

9-
public class GrowlDemoViewModel
10+
public class GrowlDemoViewModel : ViewModelBase
1011
{
1112
private readonly string _token;
1213

14+
private TransitionMode _transitionMode;
15+
1316
public GrowlDemoViewModel()
1417
{
1518

@@ -20,6 +23,24 @@ public GrowlDemoViewModel(string token)
2023
_token = token;
2124
}
2225

26+
public TransitionMode TransitionMode
27+
{
28+
get => _transitionMode;
29+
#if NET40
30+
set
31+
{
32+
Set(nameof(TransitionMode), ref _transitionMode, value);
33+
Growl.SetTransitionMode(Application.Current.MainWindow, value);
34+
}
35+
#else
36+
set
37+
{
38+
Set(ref _transitionMode, value);
39+
Growl.SetTransitionMode(Application.Current.MainWindow, value);
40+
}
41+
#endif
42+
}
43+
2344
#region Window
2445

2546
public RelayCommand InfoCmd => new(() => Growl.Info(Properties.Langs.Lang.GrowlInfo, _token));

src/Shared/HandyControl_Shared/Controls/Growl/Growl.cs

Lines changed: 68 additions & 46 deletions
Original file line numberDiff line numberDiff line change
@@ -47,11 +47,13 @@ public class Growl : Control
4747
"ShowMode", typeof(GrowlShowMode), typeof(Growl),
4848
new FrameworkPropertyMetadata(default(GrowlShowMode), FrameworkPropertyMetadataOptions.Inherits));
4949

50-
public static readonly DependencyProperty TransitionModeProperty = DependencyProperty.Register(
51-
nameof(TransitionMode), typeof(TransitionMode), typeof(Growl), new PropertyMetadata(default(TransitionMode)));
50+
public static readonly DependencyProperty TransitionModeProperty = DependencyProperty.RegisterAttached(
51+
"TransitionMode", typeof(TransitionMode), typeof(Growl),
52+
new FrameworkPropertyMetadata(default(TransitionMode), FrameworkPropertyMetadataOptions.Inherits));
5253

53-
public static readonly DependencyProperty TransitionStoryboardProperty = DependencyProperty.Register(
54-
nameof(TransitionStoryboard), typeof(Storyboard), typeof(Growl), new PropertyMetadata(default(Storyboard)));
54+
public static readonly DependencyProperty TransitionStoryboardProperty = DependencyProperty.RegisterAttached(
55+
"TransitionStoryboard", typeof(Storyboard), typeof(Growl),
56+
new FrameworkPropertyMetadata(null, FrameworkPropertyMetadataOptions.Inherits));
5557

5658
public static readonly DependencyProperty ShowDateTimeProperty = DependencyProperty.Register(
5759
nameof(ShowDateTime), typeof(bool), typeof(Growl), new PropertyMetadata(ValueBoxes.TrueBox));
@@ -105,18 +107,6 @@ public class Growl : Control
105107
/// </summary>
106108
public static Panel GrowlPanel { get; set; }
107109

108-
public TransitionMode TransitionMode
109-
{
110-
get => (TransitionMode) GetValue(TransitionModeProperty);
111-
set => SetValue(TransitionModeProperty, value);
112-
}
113-
114-
public Storyboard TransitionStoryboard
115-
{
116-
get => (Storyboard) GetValue(TransitionStoryboardProperty);
117-
set => SetValue(TransitionStoryboardProperty, value);
118-
}
119-
120110
public InfoType Type
121111
{
122112
get => (InfoType) GetValue(TypeProperty);
@@ -231,6 +221,18 @@ public static void SetShowMode(DependencyObject element, GrowlShowMode value) =>
231221
public static GrowlShowMode GetShowMode(DependencyObject element) =>
232222
(GrowlShowMode) element.GetValue(ShowModeProperty);
233223

224+
public static void SetTransitionMode(DependencyObject element, TransitionMode value)
225+
=> element.SetValue(TransitionModeProperty, value);
226+
227+
public static TransitionMode GetTransitionMode(DependencyObject element)
228+
=> (TransitionMode) element.GetValue(TransitionModeProperty);
229+
230+
public static void SetTransitionStoryboard(DependencyObject element, Storyboard value)
231+
=> element.SetValue(TransitionStoryboardProperty, value);
232+
233+
public static Storyboard GetTransitionStoryboard(DependencyObject element)
234+
=> (Storyboard) element.GetValue(TransitionStoryboardProperty);
235+
234236
public static void SetGrowlParent(DependencyObject element, bool value) =>
235237
element.SetValue(GrowlParentProperty, ValueBoxes.BooleanBox(value));
236238

@@ -371,7 +373,6 @@ private static void ShowGlobal(GrowlInfo growlInfo)
371373
CancelStr = growlInfo.CancelStr,
372374
Type = growlInfo.Type,
373375
_waitTime = Math.Max(growlInfo.WaitTime, MinWaitTime),
374-
FlowDirection = growlInfo.FlowDirection
375376
};
376377

377378
ShowInternal(GrowlWindow.GrowlPanel, ctl);
@@ -422,6 +423,10 @@ private static void Show(GrowlInfo growlInfo)
422423
// GrowlPanel is null, we create it automatically
423424
GrowlPanel ??= CreateDefaultPanel();
424425
ShowInternal(GrowlPanel, ctl);
426+
427+
var transitionMode = GetTransitionMode(ctl);
428+
GrowlPanel.VerticalAlignment = GetPanelVerticalAlignment(transitionMode);
429+
GrowlPanel.HorizontalAlignment = GetPanelHorizontalAlignment(transitionMode);
425430
}
426431
}
427432
#if NET40
@@ -435,40 +440,33 @@ private static Panel CreateDefaultPanel()
435440
FrameworkElement element = WindowHelper.GetActiveWindow();
436441
var decorator = VisualHelper.GetChild<AdornerDecorator>(element);
437442

438-
if (decorator != null)
443+
var layer = decorator?.AdornerLayer;
444+
if (layer == null)
439445
{
440-
var layer = decorator.AdornerLayer;
441-
if (layer != null)
442-
{
443-
var panel = new StackPanel
444-
{
445-
VerticalAlignment = VerticalAlignment.Top
446-
};
446+
return null;
447+
}
447448

448-
InitGrowlPanel(panel);
449-
SetIsCreatedAutomatically(panel, true);
449+
var panel = new SimpleStackPanel();
450450

451-
var scrollViewer = new ScrollViewer
452-
{
453-
HorizontalAlignment = HorizontalAlignment.Right,
454-
VerticalScrollBarVisibility = ScrollBarVisibility.Hidden,
455-
IsInertiaEnabled = true,
456-
IsPenetrating = true,
457-
Content = panel
458-
};
459-
460-
var container = new AdornerContainer(layer)
461-
{
462-
Child = scrollViewer
463-
};
451+
InitGrowlPanel(panel);
452+
SetIsCreatedAutomatically(panel, true);
464453

465-
layer.Add(container);
454+
var scrollViewer = new ScrollViewer
455+
{
456+
VerticalScrollBarVisibility = ScrollBarVisibility.Hidden,
457+
IsInertiaEnabled = true,
458+
IsPenetrating = true,
459+
Content = panel
460+
};
466461

467-
return panel;
468-
}
469-
}
462+
var container = new AdornerContainer(layer)
463+
{
464+
Child = scrollViewer
465+
};
470466

471-
return null;
467+
layer.Add(container);
468+
469+
return panel;
472470
}
473471

474472
private static void RemoveDefaultPanel(Panel panel)
@@ -918,7 +916,7 @@ public static void ClearGlobal()
918916

919917
private void StartTransition(bool isClose, Action completed = null)
920918
{
921-
var actualStoryboard = TransitionStoryboard ?? CreateStoryboard(isClose, TransitionMode);
919+
var actualStoryboard = GetTransitionStoryboard(this) ?? CreateStoryboard(isClose, GetTransitionMode(this));
922920
if (actualStoryboard is null)
923921
{
924922
return;
@@ -1064,4 +1062,28 @@ TransitionMode.Bottom2Top or TransitionMode.Bottom2TopWithFade or TransitionMode
10641062
_ => null
10651063
};
10661064
}
1065+
1066+
private static VerticalAlignment GetPanelVerticalAlignment(TransitionMode transitionMode)
1067+
{
1068+
return transitionMode switch
1069+
{
1070+
TransitionMode.Right2Left or TransitionMode.Right2LeftWithFade or TransitionMode.Left2Right
1071+
or TransitionMode.Left2RightWithFade => VerticalAlignment.Top,
1072+
TransitionMode.Bottom2Top or TransitionMode.Bottom2TopWithFade => VerticalAlignment.Bottom,
1073+
TransitionMode.Top2Bottom or TransitionMode.Top2BottomWithFade => VerticalAlignment.Top,
1074+
_ => VerticalAlignment.Stretch
1075+
};
1076+
}
1077+
1078+
private static HorizontalAlignment GetPanelHorizontalAlignment(TransitionMode transitionMode)
1079+
{
1080+
return transitionMode switch
1081+
{
1082+
TransitionMode.Right2Left or TransitionMode.Right2LeftWithFade => HorizontalAlignment.Right,
1083+
TransitionMode.Left2Right or TransitionMode.Left2RightWithFade => HorizontalAlignment.Left,
1084+
TransitionMode.Bottom2Top or TransitionMode.Bottom2TopWithFade or TransitionMode.Top2Bottom
1085+
or TransitionMode.Top2BottomWithFade => HorizontalAlignment.Center,
1086+
_ => HorizontalAlignment.Stretch
1087+
};
1088+
}
10671089
}

src/Shared/HandyControl_Shared/Data/Info/GrowlInfo.cs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,7 @@ public class GrowlInfo
3737

3838
public string Token { get; set; }
3939

40+
[Obsolete("use TransitionMode instead")]
4041
public FlowDirection FlowDirection { get; set; }
4142

4243
public Dispatcher Dispatcher { get; set; }

0 commit comments

Comments
 (0)