using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;

namespace BookDemo.QA.Admin
{
    public partial class Catalogs : System.Web.UI.Page
    {
        BookDemoEntities ctx = new BookDemoEntities();

        protected void Page_Load(object sender, EventArgs e)
        {
            if (!IsPostBack)
            {
                BindToDdlCatalogs();//绑定目录下拉列表
            }
        }

        /// <summary>
        /// 绑定目录下拉列表
        /// </summary>
        private void BindToDdlCatalogs()
        {
            #region 原始读取数据库方法
            //Common.BindToDdlCatalogs(ddlCatalogs, ctx, true);//绑定目录到列表
            #endregion

            #region 从缓存中读取
            Common.BindToDdlCatalogs(ddlCatalogs, true);//绑定目录到列表
            #endregion
        }

        /// <summary>
        /// 清空编辑区域，还原到“新建目录”状态
        /// </summary>
        private void Clear()
        {
            lblCatalogId.Text = "0";            //将目录ID设为0
            lblParentCatalog.Text = "根目录";   //根目录
            lblParentCatalogId.Text = "0";      //根目录ID
            txtName.Text = "";                  //目录名
            txtOrder.Text = "";                 //排序
            panEdit.GroupingText = "新增";      //“编辑”区域标题
            lblMsg.Text = "";                   //提示信息
        }

        protected void btnSubEdit_Click(object sender, EventArgs e)
        {
            //获取当前编辑的目录ID，如果为0，则表示新增
            int id = Convert.ToInt32(lblCatalogId.Text);

            string name = txtName.Text.Trim();//获取目录名称
            int order = Convert.ToInt32(txtOrder.Text.Trim());//获取排序

            //判断目录名称是否为空，如果为空，终止操作并给出提示
            if (string.IsNullOrEmpty(name))
            {
                lblMsg.Text = "目录名称不能为空，请填写！";
                return;
            }

            //判断此目录名字是否已经存在,如果存在,则不能添加
            int existCount = (from c in ctx.QACatalog    //在QACatalog中查找
                              where c.Name == name       //Name字段等于当前设置的字符串
                                 && c.Id != id           //ID不能与当前的相同
                              select c).Count();         //使用Count方法计算符合条件记录的数量

            if (existCount > 0)
            {
                //已经存在同名目录，给出提示并返回
                lblMsg.Text = "已有相同名称的目录存在，不能重复添加！";
                return;
            }

            //定义一个空的QACatalog实例，用于新增或添加
            QACatalog cata;
            if (id == 0)
            {
                //“新增”状态
                //获取上级目录ID
                int parentId = Convert.ToInt32(lblParentCatalogId.Text);
                int layer = 0;
                if (parentId != 0)
                {
                    //查询上级目录
                    QACatalog parentCatalog = ctx.QACatalog.First(c => c.Id == parentId);
                    layer = parentCatalog.Layer + 1;//当前目录的层次为上级目录的层数+1
                }
                cata = new QACatalog//新建一个QACatalog实例
                {
                    Layer = layer,          //层数
                    Name = name,            //名称
                    DisplayOrder = order,   //排序
                    ParentID = parentId,    //上级目录ID
                    Status = true,          //状态（可见）
                };
                ctx.AddToQACatalog(cata);//添加目录
            }
            else
            {
                //“编辑”状态
                //获取当前编辑的目录实体
                cata = ctx.QACatalog.First(c => c.Id == id);
                cata.Name = name;           //设置名称
                cata.DisplayOrder = order;  //设置排序
            }
            ctx.SaveChanges();//将修改的数据保存到数据库
            BindToDdlCatalogs();//重新绑定目录下拉菜单
            Clear();//还原编辑状态

            lblMsg.Text = (id == 0) ? "添加成功！" : "编辑成功！";//提示信息
        }

        protected void btnEdit_Click(object sender, EventArgs e)
        {
            Clear();//还原编辑状态
            //获取当前编辑的目录ID
            int id = Convert.ToInt32(ddlCatalogs.SelectedValue);
            //如果ID为0（选中了“根目录”），则不能编辑
            if (id == 0)
            {
                //错误提示信息
                lblMsg.Text = "此项无法编辑！";
                return;//返回
            }
            //获取当前选中的目录实体信息
            QACatalog cata = ctx.QACatalog.First(c => c.Id == id);

            lblCatalogId.Text = cata.Id.ToString();//编辑目录ID
            lblParentCatalogId.Text = cata.ParentID.ToString();//上级目录ID
            txtName.Text = cata.Name;//目录名称
            txtOrder.Text = cata.DisplayOrder.ToString();//排序
            if (cata.ParentID > 0)
            {
                //当此目录还有上级目录时，获取上级目录实体信息
                QACatalog parentCatalog = ctx.QACatalog.First(c => c.Id == cata.ParentID);
                lblParentCatalog.Text = parentCatalog.Name;//显示上级目录名称
            }

            panEdit.GroupingText = "编辑目录-" + cata.Name;//设置“编辑”区域标题
        }

        protected void btnDelete_Click(object sender, EventArgs e)
        {
            int id = Convert.ToInt32(ddlCatalogs.SelectedValue);//获取当前要删除的目录ID
            if (id == 0)
            {
                lblMsg.Text = "此项无法删除！";//当前选中“根目录”，不能删除
                return;//返回
            }

            QACatalog cata = ctx.QACatalog.First(c => c.Id == id);//获取当前要删除的目录的实体
            //判断目录下是否有提问，如果有，则不能删除
            bool childQuestionExist = CheckChildQuestionExist(cata.Id);
            if (childQuestionExist)
            {
                lblMsg.Text = "此目录下属有提问存在，无法删除！";
                return;//返回
            }

            ctx.DeleteObject(cata);//删除目录

            //删除下属目录
            List<QACatalog> childrenCatalogs = ctx.QACatalog.Where(c => c.ParentID == id).ToList();//获取所有下属目录
            //遍历删除所有下属目录
            foreach (var childCatalog in childrenCatalogs)
            {
                //判断目录下是否有提问，如果有，则不能删除
                childQuestionExist = CheckChildQuestionExist(childCatalog.Id);
                if (childQuestionExist)
                {
                    lblMsg.Text = "此目录下属有提问存在，无法删除！";
                    return;//返回
                }

                ctx.DeleteObject(childCatalog);//删除下属目录
            }

            ctx.SaveChanges();//保存所有数据库更新
            BindToDdlCatalogs();//重新绑定目录下拉菜单
            lblMsg.Text = "删除成功！";//删除成功提示
        }
        /// <summary>
        /// 查询指定目录下是否有提问存在
        /// </summary>
        /// <param name="catalogId"></param>
        /// <returns></returns>
        private bool CheckChildQuestionExist(int catalogId)
        {
            int chlidQuestionCount =
               (from q in ctx.QAQuestion.Include("QACatalog")   //在QAQuestion集合中查询，使用Include方法联表查询
                where q.QACatalog.Id == catalogId               //查找目录为当前目录的提问
                select q).Count();                              //计算总数
            return chlidQuestionCount > 0;
        }


        protected void btnAdd_Click(object sender, EventArgs e)
        {
            Clear();//还原编辑状态
            //获取新建目录的上级目录ID，如果为0，则比目录为根目录（一级目录）
            int parentId = Convert.ToInt32(ddlCatalogs.SelectedValue);
            if (parentId > 0)
            {
                //获取上级目录信息
                QACatalog cata = ctx.QACatalog.First(c => c.Id == parentId);
                //如果上级目录不是根目录（二级目录），则不允许在下面添加
                if (cata.Layer > 0)
                {
                    //提示错误信息
                    lblMsg.Text = "只能根目录或一级目录下添加目录，您当前选择的是二级目录！";
                    return;//返回
                }

                lblParentCatalog.Text = cata.Name;//上级目录名称
                lblParentCatalogId.Text = cata.Id.ToString();//上级目录ID
            }
        }

        protected void btnCancel_Click(object sender, EventArgs e)
        {
            Clear();
        }
    }
}
