Reputation: 3647
I want to make a small Wheel of Fortune game, but I have issues making an event that rotates the image
This is the code I have now, but it only seems to run the _thread once
private readonly Timer _timer;
private Thread _thread;
private int _angle;
public MainWindow()
{
InitializeComponent();
_timer = new Timer(500);
_timer.Elapsed += RotateWheelEvent;
_timer.Start();
_angle = 0;
SetupRotationThread();
_thread.Start();
}
public void RotateWheelEvent(object sender, EventArgs args)
{
_thread.Abort();
_angle = _angle + 15;
_thread.Start();
}
public void SetupRotationThread()
{
var rotatetransform = new RotateTransform(_angle);
_thread = new Thread(
delegate()
{
ImageWheel.Dispatcher.Invoke(
System.Windows.Threading.DispatcherPriority.SystemIdle,
TimeSpan.FromSeconds(1),
new Action(
delegate()
{
ImageWheel.RenderTransformOrigin = new Point(0.5, 0.5);
ImageWheel.RenderTransform = rotatetransform;
}
));
});
}
Upvotes: 0
Views: 1307
Reputation: 178780
At worst you should just use a DispatcherTimer
in your code-behind:
var timer = new DispatcherTimer
{
Interval = TimeSpan.FromSeconds(0.5)
};
timer.Tick += (s, e) => ((RotateTransform)ImageWheel.RenderTransform).Angle += 15;
timer.IsEnabled = true;
But there's really no need for that at all. You can just set up a Storyboard
in your XAML. Something like:
<Image x:Name="image" RenderTransformOrigin="0.5,0.5" ...>
<Image.RenderTransform>
<RotateTransform/>
</Image.RenderTransform>
<Image.Triggers>
<EventTrigger RoutedEvent="Loaded">
<BeginStoryboard>
<Storyboard Duration="00:00:00.5" RepeatBehavior="Forever">
<DoubleAnimation Storyboard.TargetName="image" Storyboard.TargetProperty="(Image.RenderTransform).(RotateTransform.Angle)" By="15"/>
</Storyboard>
</BeginStoryboard>
</EventTrigger>
</Image.Triggers>
</Image>
Some of that syntax may not be quite right (on linux so cannot check), but you get the idea. You've overly complicated something very simple.
Upvotes: 1
Reputation: 43636
You could just use a System.Threading.Timer
instead of a System.Timer
spawning a new thraed each time.
private System.Threading.Timer _timer;
private int _angle;
public MainWindow()
{
InitializeComponent();
_timer = new System.Threading.Timer((o) =>
{
_angle += 15;
Dispatcher.Invoke(DispatcherPriority.Background, (Action)delegate
{
ImageWheel.RenderTransformOrigin = new Point(0.5, 0.5);
ImageWheel.RenderTransform = new RotateTransform(_angle);
});
}, null, 500, 500);
}
However its not clear why you are threading this at all, you seem to be starting a thread that just invokes code back to the UI thread, I dont see any work this thread needs to do.
So all I think you need is this
private readonly Timer _timer;
private int _angle;
public MainWindow()
{
InitializeComponent();
_timer = new Timer(500);
_timer.Elapsed += RotateWheelEvent;
_timer.Start();
_angle = 0;
}
public void RotateWheelEvent(object sender, EventArgs args)
{
Dispatcher.Invoke(DispatcherPriority.Background, (Action)delegate
{
_angle += 15;
ImageWheel.RenderTransformOrigin = new Point(0.5, 0.5);
ImageWheel.RenderTransform = new RotateTransform(_angle);
});
}
Upvotes: 3