moel@345: using System; moel@345: using System.Collections.Generic; moel@345: using System.Text; moel@345: using System.Drawing; moel@345: using System.Threading; moel@345: using System.Windows.Forms; moel@345: moel@345: namespace Aga.Controls.Tree.NodeControls moel@345: { moel@345: /// moel@345: /// Displays an animated icon for those nodes, who are in expanding state. moel@345: /// Parent TreeView must have AsyncExpanding property set to true. moel@345: /// moel@345: public class ExpandingIcon: NodeControl moel@345: { moel@345: private static GifDecoder _gif = ResourceHelper.LoadingIcon; moel@345: private static int _index = 0; moel@345: private static volatile Thread _animatingThread; moel@345: private static object _lock = new object(); moel@345: moel@345: public override Size MeasureSize(TreeNodeAdv node, DrawContext context) moel@345: { moel@345: return ResourceHelper.LoadingIcon.FrameSize; moel@345: } moel@345: moel@345: protected override void OnIsVisibleValueNeeded(NodeControlValueEventArgs args) moel@345: { moel@345: args.Value = args.Node.IsExpandingNow; moel@345: base.OnIsVisibleValueNeeded(args); moel@345: } moel@345: moel@345: public override void Draw(TreeNodeAdv node, DrawContext context) moel@345: { moel@345: Rectangle rect = GetBounds(node, context); moel@345: Image img = _gif.GetFrame(_index).Image; moel@345: context.Graphics.DrawImage(img, rect.Location); moel@345: } moel@345: moel@345: public static void Start() moel@345: { moel@345: lock (_lock) moel@345: { moel@345: if (_animatingThread == null) moel@345: { moel@345: _index = 0; moel@345: _animatingThread = new Thread(new ThreadStart(IterateIcons)); moel@345: _animatingThread.IsBackground = true; moel@345: _animatingThread.Priority = ThreadPriority.Lowest; moel@345: _animatingThread.Start(); moel@345: } moel@345: } moel@345: } moel@345: moel@345: public static void Stop() moel@345: { moel@345: lock (_lock) moel@345: { moel@345: _index = 0; moel@345: _animatingThread = null; moel@345: } moel@345: } moel@345: moel@345: private static void IterateIcons() moel@345: { moel@345: while (_animatingThread != null) moel@345: { moel@345: if (_index < _gif.FrameCount - 1) moel@345: _index++; moel@345: else moel@345: _index = 0; moel@345: moel@345: if (IconChanged != null) moel@345: IconChanged(null, EventArgs.Empty); moel@345: moel@345: int delay = _gif.GetFrame(_index).Delay; moel@345: Thread.Sleep(delay); moel@345: } moel@345: System.Diagnostics.Debug.WriteLine("IterateIcons Stopped"); moel@345: } moel@345: moel@345: public static event EventHandler IconChanged; moel@345: } moel@345: }