using System;
using System.Collections.Generic;
using System.Drawing;
using System.Text;
using System.Windows.Forms;

namespace IMLibrary.Controls.Toolbox
{
    partial class Toolbox
    {
        #region RenameTextBox
        private class RenameTextBox : TextBox
        {
            private string _currentCaption;
            private IToolboxObject _tool;
            private Toolbox _owner;

            public RenameTextBox(Toolbox toolbox)
            {
                _owner = toolbox;

                this.Visible = false;
                //this.BorderStyle = BorderStyle.None;

                toolbox.Controls.Add(this);
            }

            public IToolboxObject Tool
            {
                get { return _tool; }
                set { _tool = value; }
            }

            public string Caption
            {
                get
                {
                    if (Tool is Item && string.IsNullOrEmpty(_currentCaption))
                        _currentCaption = ((Item)Tool).Text;
                    return _currentCaption;
                }
                set { _currentCaption = value; }
            }

            public new void Show()
            {
                if (this._tool == null)
                    throw new Exception(Properties.Resources.ToolboxRenamerNothingToRename);
                
                System.Drawing.Rectangle rect;

                if (_tool is Tab)
                {
                    Tab tab = (Tab)_tool;
                    rect = tab.GetCaptionRectangle(false);
                    tab.Renaming = true;
                }
                else if (_tool is Item)
                {
                    Item item = (Item)_tool;
                    rect = item.GetBounds(false);
                    item.Renaming = true;
                }
                else
                    throw new Exception(Properties.Resources.ToolboxRenamerNotItemNorTab);

                this.Visible = true;
                this.Text = Caption;
                this.Capture = true;
                this.MaximumSize = rect.Size;

                int yOffset = (rect.Height > this.Height) ? (rect.Height - this.Height) / 2 : 0;
                this.Bounds = new Rectangle(rect.Left, rect.Top + yOffset, rect.Width, rect.Height);

                this.BringToFront();
                this.Focus();
            }

            protected override void OnValidated(EventArgs e)
            {
                if (Text == string.Empty && string.IsNullOrEmpty(Caption) && Tool is Tab)
                {
                    Tab tab = (Tab)Tool;
                    bool allowDelete = tab.AllowDelete;
                    tab.AllowDelete = true;
                    try
                    {
                        _owner.Categories.Remove(tab);
                    }
                    finally
                    {
                        tab.AllowDelete = allowDelete;
                    }
                }
                else if (Text != string.Empty)
                {
                    if (Tool is Tab)
                        ((Tab)Tool).Text = Text;
                    else if (Tool is Item)
                        ((Item)Tool).Text = Text;
                }
                HideRenamer();

                base.OnValidated(e);
            }

            private void ShowWarning(string text)
            {
                MessageBox.Show(text, Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Warning);
            }

            protected override void OnKeyDown(KeyEventArgs e)
            {
                if (e.KeyData == Keys.Enter)
                {
                    if (Text == string.Empty)
                    {
                        ShowWarning(Properties.Resources.ToolboxEmptyTextMessage);
                    }
                    else
                    {
                        if (Tool is Tab)
                            ((Tab)Tool).Text = Text;
                        else if (Tool is Item)
                            ((Item)Tool).Text = Text;
                        HideRenamer();
                    }
                }
                else if (e.KeyData == Keys.Escape)
                {
                    HideRenamer();
                }
                else
                    base.OnKeyDown(e);
            }

            protected override void OnMouseDown(MouseEventArgs e)
            {
                if (!this.ClientRectangle.Contains(e.Location))
                {
                    OnValidated(EventArgs.Empty);
                }
                base.OnMouseDown(e);
            }

            private void HideRenamer()
            {
                this.Capture = false;
                if (this.Focused)
                    this.InvokeLostFocus(this, EventArgs.Empty);
                if (Tool is Tab)
                    ((Tab)Tool).Renaming = false;
                else if (Tool is Item)
                    ((Item)Tool).Renaming = false;
                this.Visible = false;
            }
        }
        #endregion 

        private RenameTextBox _renamerBox;
        private RenameTextBox RenamerBox
        {
            get
            {
                if (_renamerBox == null)
                {
                    _renamerBox = new RenameTextBox(this);
                }
                return _renamerBox;
            }
        }

        /// <summary>
        /// Starts renaming of the <paramref name="tab"/> using the <paramref name="baseName"/>.
        /// </summary>
        /// <param name="tab">A <see cref="Tab"/> to rename.</param>
        /// <param name="baseName">A default name displayed in the rename textbox.</param>
        protected virtual void OnRenameTab(Tab tab, string baseName)
        {
            RenameTextBox box = RenamerBox;
            box.Tool = tab;
            box.Caption = baseName;
            box.Show();
        }

        /// <summary>
        /// Starts renaming of the <paramref name="item"/>.
        /// </summary>
        /// <param name="item">An <see cref="Item"/> to rename.</param>
        protected virtual void OnRenameItem(Item item)
        {
            RenameTextBox box = RenamerBox;
            box.Tool = item;
            box.Caption = item.Text;
            box.Show();
        }
    }
}
