using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Diagnostics;
using System.Runtime.InteropServices;
using ModuleDataLib;

namespace Setup
{
    /// <summary>
    /// Hlavní formulář aplikace
    /// </summary>
    public partial class Form1 : Form
    {
        /// <summary>
        /// Odkaz na právě aktivní sadu panelů (TabControl)
        /// </summary>
        TabControl activeTabControl = null;

        /// <summary>
        /// Odkaz na větev snímačů v TreeNode
        /// </summary>
        TreeNode nodeSens;

        /// <summary>
        /// Odkaz na větev zobrazovačů v TreeNode 
        /// </summary>
        TreeNode nodeDisp;

        /// <summary>
        /// Vytvoření instance formuláře
        /// </summary>
        public Form1()
        {
            InitializeComponent();
            treeView1.ExpandAll();
            nodeSens = treeView1.Nodes[0].Nodes["nodeSens"];
            nodeDisp = treeView1.Nodes[0].Nodes["nodeDisp"];
        }

        /// <summary>
        /// Připojení/přidání modulu
        /// </summary>
        void addModule()
        {
            EnterIp enterIp = new EnterIp();

            if (enterIp.ShowDialog(this) == DialogResult.OK)
            {
                TreeNode n = findNode(enterIp.Value.ToString());
                if (n != null)
                {
                    MessageBox.Show(
                        String.Format(
                            "Modul nelze přidat, protože na adrese {0} už existuje modul {1}",
                            enterIp.Value,
                            n.Text
                            ),
                        "Chyba přidání modulu",
                        MessageBoxButtons.OK,
                        MessageBoxIcon.Error);
                    return;
                }

                SetStatusComm();

                // pokus o připojení modulu
                ModuleBase module = ModuleBase.Connect(enterIp.Value);

                if (module is ModuleBase)
                {
                    // modul byl připojen

                    TreeNode node = new TreeNode();
                    setNodeLabel(node, module);

                    // vytvoření TabControls

                    TabControl tc = new TabControl();
                    tc.Tag = module;
                    tc.Parent = splitContainer1.Panel2;
                    tc.Dock = DockStyle.Fill;
                    tc.BringToFront();

                    if (module is ModuleSensor)
                    {
                        // modul je snímač

                        nodeSens.Nodes.Add(node);
                        nodeSens.Expand();

                        createPanel(tc, "Teploty", (module as ModuleSensor).Data, typeof(CtrlPanelData));
                        createPanel(tc, "Měření", (module as ModuleSensor).Meas, typeof(CtrlPanelMeas));
                    }
                    else if (module is ModuleDisplay)
                    {
                        // modul je zobrazovač

                        nodeDisp.Nodes.Add(node);
                        nodeDisp.Expand();

                        createPanel(tc, "Zdroj dat", (module as ModuleDisplay).Source, typeof(CtrlPanelSrc));
                        createPanel(tc, "Zobrazení", (module as ModuleDisplay).Display, typeof(CtrlPanelDisp));
                                                
                    }

                    // společné panely

                    createPanel(tc, "IP", module.Net, typeof(CtrlPanelNet));
                    createPanel(tc, "WLAN", module.Wlan, typeof(CtrlPanelWlan));

                    node.Tag = tc;
                    hideActiveModule();
                    treeView1.SelectedNode = node;

                    // aktivace titulního panelu 

                    tc.TabPages[0].Select();
                    (tc.TabPages[0].Controls[0] as CtrlPanel).ShowData();
                }
                else
                {
                    // modul nebyl připojen nebo je nepodporovaného typu

                    MessageBox.Show(
                        String.Format(
                            "Na adrese {0} nebyl nalezen žádný kompatilní modul",
                            enterIp.Value
                            ),
                        "Chyba přidání modulu",
                        MessageBoxButtons.OK,
                        MessageBoxIcon.Error);
                }
                SetStatus();
            }
        }

        void createPanel(TabControl tc, string caption, DataBase dataObject, Type panelType)
        {
            TabPage tab = new TabPage(caption);
            CtrlPanel panel = (CtrlPanel)Activator.CreateInstance(panelType);

            panel.DataObject = dataObject;

            tc.TabPages.Add(tab);
            tab.Controls.Add(panel);
            panel.Parent = tab;
            panel.Dock = DockStyle.Bottom;
        }

        /// <summary>
        /// Skytí sady panelů aktivního modulu
        /// </summary>
        void hideActiveModule()
        {
            if (activeTabControl != null)
                activeTabControl.Visible = false;            
        }

        /// <summary>
        /// Nastaví text ve status liště a tvar kurzoru
        /// </summary>
        public void SetStatusComm()
        {
            status.Items[0].Text = "Probíhá komunikace s modulem ...";
            status.Items[0].ForeColor = Color.Blue;
            UseWaitCursor = true;
            Application.DoEvents();
        }

        /// <summary>
        /// Nastaví text ve status liště a tvar kurzoru
        /// </summary>
        public void SetStatusErr()
        {
            status.Items[0].Text = "Modul ve stanovené době neodpověděl";
            status.Items[0].ForeColor = Color.Red;
            UseWaitCursor = false;
            Application.DoEvents();
        }

        /// <summary>
        /// Nastaví text ve status liště podle jména zvoleného modulu
        /// </summary>
        public void SetStatus()
        {
            status.Items[0].ForeColor = Color.Black;
            UseWaitCursor = false;

            if (activeTabControl == null)
                status.Items[0].Text = "Není zvolen žádný modul";
            else
                status.Items[0].Text = treeView1.SelectedNode.Text;

            Application.DoEvents();
        }

        /// <summary>
        /// Událost po změně zvoleného TreeNode (vyvolá změnu aktivního modulu)
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void treeView1_AfterSelect(object sender, TreeViewEventArgs e)
        {
            hideActiveModule();
            activeTabControl = (TabControl)treeView1.SelectedNode.Tag;

            cmnRename.Enabled = (activeTabControl != null);
            cmnRst.Enabled = (activeTabControl != null);
            cmnDel.Enabled = (activeTabControl != null);

            if (activeTabControl == null)
                panRoot.Visible = true;
            else
                activeTabControl.Visible = true;

            SetStatus();            
        }

        /// <summary>
        /// Prohledá TreeViewm, jestli neobsahuje uzel se zadanám textem
        /// </summary>
        /// <param name="contains"></param>
        /// <returns></returns>
        TreeNode findNode(string contains)
        {
            foreach (TreeNode node in nodeSens.Nodes)
            {
                if (node.Text.Contains(contains))
                    return node;
            }
            foreach (TreeNode node in nodeDisp.Nodes)
            {
                if (node.Text.Contains(contains))
                    return node;
            }
            return null;
        }

        /// <summary>
        /// Link: Připojit modul
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void lnkNewModule_LinkClicked(object sender, LinkLabelLinkClickedEventArgs e)
        {
            addModule();
        }

        /// <summary>
        /// Menu: Připojit modul
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void cmnAdd_Click(object sender, EventArgs e)
        {
            addModule();
        }

        /// <summary>
        /// Menu: Ukončení aplikace
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void mnuExit_Click(object sender, EventArgs e)
        {
            Application.Exit();
        }

        /// <summary>
        /// Menu: O programu
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void oProgramuToolStripMenuItem_Click(object sender, EventArgs e)
        {
            About about = new About();
            about.ShowDialog();
        }

        /// <summary>
        /// Menu: Restart modulu
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void cmnRst_Click(object sender, EventArgs e)
        {
            if (activeTabControl.Tag is ModuleBase)
            {
                if (MessageBox.Show(
                    "Opravdu chcete provést restart modulu?",
                    "Potvrzení",
                    MessageBoxButtons.YesNo,
                    MessageBoxIcon.Warning) == System.Windows.Forms.DialogResult.Yes)
                {
                    (activeTabControl.Tag as ModuleBase).Restart();
                }
                
            }
        }

        /// <summary>
        /// Menu: odstranění modulu
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void cmnDel_Click(object sender, EventArgs e)
        {
            if (activeTabControl != null)
            {
                if (MessageBox.Show(
                    "Opravdu odstranit modul ?",
                    "Potvrzení",
                    MessageBoxButtons.YesNo,
                    MessageBoxIcon.Warning) == System.Windows.Forms.DialogResult.Yes)
                {
                    (activeTabControl.Tag as ModuleBase).Dispose();
                    activeTabControl.Dispose();
                    treeView1.SelectedNode.Remove();
                }
            }
        }

        /// <summary>
        /// Menu: Změna jména modulu
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void cmnRename_Click(object sender, EventArgs e)
        {
            DataId data = (activeTabControl.Tag as ModuleBase).Id;

            EnterIdString enterIdString = new EnterIdString() { Value = data.IdString };

            if (enterIdString.ShowDialog(this) == DialogResult.OK)
            {
                data.IdString = enterIdString.Value;
                if (data.Upload())
                    setNodeLabel(treeView1.SelectedNode, (activeTabControl.Tag as ModuleBase)); 
                else
                    MessageBox.Show(
                        "Zápis do modulu se nezdařil",
                        "Chyba",
                        MessageBoxButtons.OK,
                        MessageBoxIcon.Error);
            }
        }

        /// <summary>
        /// Nastavení textu u uzlu v TreeView
        /// </summary>
        /// <param name="node"></param>
        /// <param name="module"></param>
        private void setNodeLabel(TreeNode node, ModuleBase module)
        {
            node.Text = String.Format(
                "{0} ({1}@{2})",
                (module as ModuleBase).Id.IdString,
                (module as ModuleBase).Id.HwString,
                module.CommObject.EndPoint.Address);
        }

    }
}
