LoginSignup
1
1

More than 1 year has passed since last update.

MainWindow.xamlでアナログ時計を滑らかに

Last updated at Posted at 2020-07-03

C#でアナログ時計を作ってみた

だいたい9時6分33秒くらい?かな
秒針がとても滑らかに動きます
そんな超単純なアニメーションでxamlの実力を知りました
スクリーンショット 2020-07-03 21.20.10.jpg
早速、xamlコードは以下のようになりました。

MainWindow.xaml
<Window x:Class="MainWindow.AnalogClock"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        mc:Ignorable="d"
        Title="アプリケーション課題3:Analog Clock" Height="500" Width="500" 
        Loaded="Window_Loaded" >
    <Window.Resources>
        <Storyboard x:Key="SecondHand" x:Name="SecondHand" RepeatBehavior="Forever" >
            <DoubleAnimation
                Duration="0:1:0" From="0" To="360"
                Storyboard.TargetName="SecondLine"
                Storyboard.TargetProperty="(Line.RenderTransform).(RotateTransform.Angle)"
            />
        </Storyboard>
        <Storyboard x:Key="MinuteHand" x:Name="MinuteHand" RepeatBehavior="Forever">
            <DoubleAnimation
                Duration="1:0:0" From="0" To="360"
                Storyboard.TargetName="MinuteLine"
                Storyboard.TargetProperty="(Line.RenderTransform).(RotateTransform.Angle)"
            />
        </Storyboard>
        <Storyboard x:Key="HourHand" x:Name="HourHand" RepeatBehavior="Forever">
            <DoubleAnimation
                Duration="12:0:0" From="0" To="360"
                Storyboard.TargetName="HourLine"
                Storyboard.TargetProperty="(Line.RenderTransform).(RotateTransform.Angle)"
            />
        </Storyboard>
    </Window.Resources>
    <Canvas Width="400" Height="400">
        <Line x:Name="HourLine"  Stroke="Black" Fill="Black" 
              X1="200" Y1="200" X2="200" Y2="80"              
               StrokeThickness="3" >
            <Line.RenderTransform>
                <RotateTransform  x:Name="AngleHour" Angle="0" 
                                  CenterX="200" CenterY="200"/>
            </Line.RenderTransform>
        </Line>
        <Line x:Name="MinuteLine"  Stroke="Black" Fill="Black" 
              X1="200" Y1="200" X2="200" Y2="40"              
               StrokeThickness="2" >
            <Line.RenderTransform>
                <RotateTransform x:Name="AngleMinute"  Angle="0" 
                                 CenterX="200" CenterY="200"/>
            </Line.RenderTransform>
        </Line>
        <Line x:Name="SecondLine"  Stroke="Black" Fill="LightGray"
              X1="200" Y1="240" X2="200" Y2="30"  >
            <Line.RenderTransform>
                <RotateTransform x:Name="AngleSecond" Angle="0"  
                                 CenterX="200" CenterY="200"/>
            </Line.RenderTransform>
        </Line>
        <Ellipse Fill="Black" Width="10" Height="10" HorizontalAlignment="Center" 
                 VerticalAlignment="Center" 
                 Canvas.Top="195" Canvas.Left="195"/>
    </Canvas>
</Window>

さらにC#サイドのコードは以下の通り

MainWindows.xaml.cs
// ********************************************************
// *
// * 処理内容:滑らかなアナログ時計の動作を実現
// *
// *        MainWindow.xaml.cs :アナログ時計表示
// *
// *        2020.07.03 ProOJI
// *
// ********************************************************

using System;
using System.Windows;
using System.Windows.Media.Animation;

namespace MainWindow
{
    /// <summary>
    /// アナログ時計のクラス
    /// </summary>
    public partial class AnalogClock : Window
    {
        /// <summary>
        /// 初期設定
        /// </summary>
        public AnalogClock()
        {
            InitializeComponent();
            InitializeAngle();
        }
        /// <summary>
        /// アナログ時計のアニメーション
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void Window_Loaded(object sender, RoutedEventArgs e)
        {
            // 時間の針
            StartAnimation("HourHand", this.AngleHour.Angle);
            // 分の針
            StartAnimation("MinuteHand", this.AngleMinute.Angle);
            // 秒の針
            StartAnimation("SecondHand", this.AngleSecond.Angle);
        }
        /// <summary>
        /// 針の角度の初期設定
        /// </summary>
        /// <returns>なし</returns>
        void InitializeAngle()
        {
            DateTime dt = DateTime.Now;
            this.AngleSecond.Angle = dt.Second * 360.0 / 60.0;
            this.AngleMinute.Angle = (dt.Minute + dt.Second / 60.0) * 360.0 / 60.0;
            this.AngleHour.Angle = (dt.Hour + dt.Minute / 60.0) * 360.0 / 12;
        }

        /// <summary>
        /// 時計の針のアニメーション表示
        /// </summary>
        /// <param name="name">各針の名称</param>
        /// <param name="angle">針の角度</param>
        /// <returns>なし</returns>
        private void StartAnimation(string name, double angle)
        {
            var sb = this.Resources[name] as Storyboard;
            var da = sb.Children[0] as DoubleAnimation;
            da.From = angle;
            da.To = da.From + 360.0;
            sb.Begin();
        }
    }
}

まとめ

XAMLのみで、かなりのアニメーションを作ることができるのはすごい
以上!( ̄∀ ̄)

1
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
1