using System;
using System.ComponentModel;

namespace Azyobuzi.Twirunrun
{
    public class TabInfo : INotifyPropertyChanged
    {
        public event PropertyChangedEventHandler PropertyChanged;

        protected void OnPropertyChanged(string propertyName)
        {
            if (PropertyChanged != null)
                PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
        }

        private string name;
        /// <summary>
        /// タブ名
        /// </summary>
        public string Name
        {
            set
            {
                if (name != value)
                {
                    name = value;
                    OnPropertyChanged("Name");
                }
            }
            get
            {
                return name;
            }
        }

        private TabTypes type;
        /// <summary>
        /// タブの種類。TabTypesの1つ
        /// </summary>
        public TabTypes Type
        {
            set
            {
                if (type != value)
                {
                    type = value;
                    OnPropertyChanged("Type");
                }
            }
            get
            {
                return type;
            }
        }

        private bool deletable;
        /// <summary>
        /// 削除可能か
        /// </summary>
        public bool Deletable
        {
            set
            {
                if (deletable != value)
                {
                    deletable = value;
                    OnPropertyChanged("Deletable");
                }
            }
            get
            {
                return deletable;
            }
        }

        private bool notifyNewTweet;
        /// <summary>
        /// 新着通知するか
        /// </summary>
        public bool NotifyNewTweet
        {
            set
            {
                if (notifyNewTweet != value)
                {
                    notifyNewTweet = value;
                    OnPropertyChanged("NotifyNewTweet");
                }
            }
            get
            {
                return notifyNewTweet;
            }
        }

        private string notifySoundFile;
        /// <summary>
        /// 通知音。null可
        /// </summary>
        public string NotifySoundFile
        {
            set
            {
                if (notifySoundFile != value)
                {
                    notifySoundFile = value;
                    OnPropertyChanged("NotifySoundFile");
                }
            }
            get
            {
                return notifySoundFile;
            }
        }

        private int refreshInterval;
        /// <summary>
        /// 更新間隔
        /// </summary>
        public int RefreshInterval
        {
            set
            {
                if (refreshInterval != value)
                {
                    refreshInterval = value;
                    OnPropertyChanged("RefreshInterval");
                }
            }
            get
            {
                return refreshInterval;
            }
        }

        private bool postGet;
        /// <summary>
        /// 投稿時取得
        /// </summary>
        public bool PostGet
        {
            set
            {
                if (postGet != value)
                {
                    postGet = value;
                    OnPropertyChanged("PostGet");
                }
            }
            get
            {
                return postGet;
            }
        }

        private int getHits;
        /// <summary>
        /// 取得件数
        /// </summary>
        public int GetHits
        {
            set
            {
                if (getHits != value)
                {
                    getHits = value;
                    OnPropertyChanged("GetHits");
                }
            }
            get
            {
                return getHits;
            }
        }

        private SearchQuery searchQuery;
        /// <summary>
        /// 検索条件。null可
        /// </summary>
        public SearchQuery SearchQuery
        {
            set
            {
                if (!searchQuery.Equals(value))
                {
                    searchQuery = value;
                    OnPropertyChanged("SearchQuery");
                }
            }
            get
            {
                return searchQuery;
            }
        }

        private ListName listName;
        /// <summary>
        /// リスト名。null可
        /// </summary>
        public ListName ListName
        {
            set
            {
                if (!listName.Equals(value))
                {
                    listName = value;
                    OnPropertyChanged("ListName");
                }
            }
            get
            {
                return listName;
            }
        }

        public TimelineTabPage CreateTabPage(TwirunrunTabControl tabControl)
        {
            return this.Type.SelectCase()
                .Case(TabTypes.Home, () => new HomeTimelineTabPage(/*tabControl, */this))
                .Case(TabTypes.Mentions, () => new MentionsTabPage(/*tabControl, */this))
                .Case(TabTypes.DirectMessages, () => new DirectMessagesTimelineTabPage(/*tabControl, */this))
                .Result as TimelineTabPage;
            //TODO
        }
    }

    public enum TabTypes
    {
        /// <summary>
        /// ホーム
        /// </summary>
        Home,
        /// <summary>
        /// @関連
        /// </summary>
        Mentions,
        /// <summary>
        /// DM
        /// </summary>
        DirectMessages,
        ///// <summary>
        ///// お気に入り
        ///// </summary>
        //Favorites,
        /// <summary>
        /// リスト
        /// </summary>
        List,
        /// <summary>
        /// 検索
        /// </summary>
        Search,
        /// <summary>
        /// 空のタブ。振り分けなどに使う
        /// </summary>
        Blank
    }

    public class SearchQuery : IEquatable<SearchQuery>
    {
        public string Query { set; get; }
        public bool JapaneseOnly { set; get; }

        public bool Equals(SearchQuery other)
        {
            return this.Query == other.Query && this.JapaneseOnly == other.JapaneseOnly;
        }
    }

    public struct ListName : IEquatable<ListName>
    {
        public string UserName { set; get; }
        public string Name { set; get; }

        public bool Equals(ListName other)
        {
            return this.UserName == other.UserName && this.Name == other.Name;
        }
    }
}
