using System;
using System.Collections.Generic;
using System.Text;
using ICommLayer;
using DBFactory;
using System.Data;
using Microsoft.VisualBasic;
namespace OPCClient
{
    public class CSendDeviceOrder:ISendDeviceOrder
    {
        Model.MDevice devinfo;
        string _commLayerError;
        StringBuilder sql = new StringBuilder();
        StringBuilder sss = new StringBuilder();
        public string CommLayerError
        {
            get { return _commLayerError; }
            set { _commLayerError = value; }
        }
        DBOperator dbo = CCommonOPCClient.dbo;
        //Model.MDevice devinfo;
        public CSendDeviceOrder()
        {
            dbo.Open();
        }

       

        /// <summary>
        /// 发送堆垛机命令
        /// </summary>
        /// <param name="MessageIndex">消息编号</param>
        /// <param name="TaskIndex">任务编号</param>
        /// <param name="Order">堆垛机命令字</param>
        ///1-复位 
        ///2-将取 
        ///3-将送
        ///4-取货
        ///5-放货
        ///6-取放货
        /// <param name="DeviceIndex">设备编号</param>
        /// <param name="StartX">起始x坐标，排-沿轨道方向</param>
        /// <param name="StartY">起始y坐标，层-高度方向</param>
        /// <param name="StartZ">起始z坐标，列-面向堆垛机操作面板，1-左侧，2-右侧</param>
        /// <param name="EndX">目标x坐标，列-沿轨道方向</param>
        /// <param name="EndY">目标y坐标，层-高度方向</param>
        /// <param name="EndZ">目标z坐标，排-面向堆垛机操作面板，1-左侧，2-右侧</param>
        /// <returns>发送堆垛机命令是否成功</returns>
        public bool SendDeviceOrder(int MessageIndex, int TaskIndex, int Order, int DeviceIndex, int StartX, int StartY, int StartZ, int EndX, int EndY, int EndZ)
        {
            string[] itemnames;
            string[] itemvalues;

            //if (MessageIndex == 2)//20101220
            //{
            //    Order = 100;
            //}
            try
            {
                int StartZ1 = 0; int EndZ1 = 0;
                int sn = 0; int UseAwayFork = 0; int UseAwayFork1 = 0;
                DataView dv = dbo.ExceSQL("SELECT F_DBW1Address,F_DBWSendLength,F_DeviceIndex,F_DeviceKindIndex,F_OPCProgID, F_RemoteIP FROM T_Base_Device where F_DeviceIndex=" + DeviceIndex).Tables[0].DefaultView;
                if (dv.Count == 0)
                {
                    _commLayerError = "OPCClient.CSendDeviceOrder.SendDeviceOrder发生错误：在设备表中没找到设备所引！";
                    return false;
                }
                else
                {
                    if ((dv[0]["F_DeviceKindIndex"].ToString() != "1"))
                    {//堆垛机使用此方法
                        _commLayerError = "OPCClient.CSendDeviceOrder.SendDeviceOrder发生错误：堆垛机以外的设备使用此方法不正确!";
                        return false;
                    }
                    #region 堆垛机

                    if (dv[0]["F_DeviceKindIndex"].ToString() == "1")
                    {
                        devinfo = Model.CGetInfo.GetDeviceInfo(DeviceIndex);
                        if (devinfo.IfCorrelDoubleFork == "1")
                        {
                            //堆垛机的双叉取货指令，在此决定分配货叉、同步还是异步发送20100323
                            if ((Order == 4) || (Order == 2))
                            {
                                #region 分配货叉

                                string[] rr = Model.CGeneralFunction.GetDoubleForkMonitorInfo(TaskIndex, DeviceIndex);

                                //如果不是双叉关联任务：根据货位奇偶和堆垛机号指定货叉
                                if (rr == null)
                                {
                                    //如果F_UseAwayFork='-',分配货叉，否则已经分配好货叉无需再分配
                                    if (Model.CGeneralFunction.GetUseAwayFork(TaskIndex) == "-")
                                    {
                                        switch (Model.CGeneralFunction.GetDoubleForkFromST_CELL(StartZ, StartX, StartY, Model.CGeneralFunction.GetWAREHOUSEFromSTCELL(DeviceIndex)))
                                        {
                                            case 1: // 指定近叉
                                                UseAwayFork = 0;
                                                break;
                                            case 2: // 指定远叉
                                                UseAwayFork = 1;
                                                break;
                                            case 0: // 没有指定货叉，要看是11001-11005 还是11006-11010；正好相反。
                                                // 20120422 南昌
                                                if (DeviceIndex > 11000 && DeviceIndex < 11006)
                                                {
                                                    if ((StartX % 2) == 0 || StartX == 1) // 双数列,增加输送机1排 20120529
                                                    {
                                                        UseAwayFork = 1;   // 远叉
                                                    }
                                                    else                  // 单数列
                                                    {
                                                        UseAwayFork = 0;   // 近叉
                                                    }
                                                }
                                                else
                                                {
                                                    if ((StartX % 2) == 0) // 双数列
                                                    {
                                                        UseAwayFork = 0;   // 近叉
                                                    }
                                                    else                  // 单数列
                                                    {
                                                        UseAwayFork = 1;   // 远叉
                                                    }
                                                }
                                                break;
                                        }

                                        //dbo.ExceSQL("UPDATE T_Monitor_Task SET F_UseAwayFork = '" + UseAwayFork + "' WHERE (F_ManageTaskIndex = " +
                                        //    Model.CGeneralFunction.GetManageTaskIndexfromMonitor(TaskIndex) + ") AND (F_ManageTASKKINDINDEX = " +
                                        //    Model.CGeneralFunction.GetManageTaskKindIndexFromMonitor(TaskIndex) + ")");//20101220

                                        dbo.ExceSQL("UPDATE T_Monitor_Task SET F_UseAwayFork = '" + UseAwayFork + "' WHERE (F_ManageTaskIndex = " +
                                          Model.CGeneralFunction.GetManageTaskIndexfromMonitor(TaskIndex) + ") AND (F_ManageTASKKINDINDEX = " +
                                          Model.CGeneralFunction.GetManageTaskKindIndexFromMonitor(TaskIndex) + ") AND (F_DeviceIndex = " + DeviceIndex +")");//20120615  对开堆垛机只修改本机的货叉
                                    }
                                    else // 已经分配货叉，或者手工任务，按照指定的发送
                                    {
                                        UseAwayFork = Convert.ToInt32(Model.CGeneralFunction.GetUseAwayFork(TaskIndex));
                                    }

                                    // 印钞厂堆垛机X发送时候 X= （X+1）/2 换成大货格

                                    //if (UseAwayFork == 1)//远货叉列数减一，因为近货叉是主货叉
                                    //{
                                    //    if (DeviceIndex > 11000 && DeviceIndex < 11006)
                                    //    {
                                    //        if (StartX != 1)
                                    //        {
                                    //            StartX = StartX - 1;
                                    //        }
                                    //    }
                                    //    else
                                    //    {
                                    //        if (StartX != 1)
                                    //        {
                                    //            StartX = StartX + 1;
                                    //        }
                                    //    }

                                    //}

                                }
                                // 双叉关联任务
                                else
                                {
                                    if (Model.CGeneralFunction.GetUseAwayFork(TaskIndex) == "-")
                                    {
                                        //如果是双叉关联任务并且没有指定货叉：根据货位奇偶和堆垛机号来判断。
                                        //UseAwayFork = Model.CGeneralFunction.GetUseAwayFork(TaskIndex, DeviceIndex, Order);
                                        if (DeviceIndex > 11000 && DeviceIndex < 11006)
                                        {
                                            if (StartX % 2 == 1) // 奇数
                                            {
                                                UseAwayFork = 0;// 近叉
                                            }
                                            else
                                            {
                                                UseAwayFork = 1;// 远叉
                                            }
                                        }
                                        else // 11006-11010 堆垛机
                                        {
                                            if (StartX % 2 == 0)// 偶数
                                            {
                                                UseAwayFork = 0;// 近叉
                                            }
                                            else
                                            {
                                                UseAwayFork = 1;// 远叉
                                            }
                                        }

                                        //dbo.ExceSQL("UPDATE T_Monitor_Task SET F_UseAwayFork = '" + UseAwayFork + "' WHERE (F_ManageTaskIndex = " +
                                        //    Model.CGeneralFunction.GetManageTaskIndexfromMonitor(TaskIndex) + ") AND (F_ManageTASKKINDINDEX = " +
                                        //    Model.CGeneralFunction.GetManageTaskKindIndexFromMonitor(TaskIndex) + ")");//20101220

                                        dbo.ExceSQL("UPDATE T_Monitor_Task SET F_UseAwayFork = '" + UseAwayFork + "' WHERE (F_ManageTaskIndex = " +
                                          Model.CGeneralFunction.GetManageTaskIndexfromMonitor(TaskIndex) + ") AND (F_ManageTASKKINDINDEX = " +
                                          Model.CGeneralFunction.GetManageTaskKindIndexFromMonitor(TaskIndex) + ") AND (F_DeviceIndex = " + DeviceIndex + ")");//20120615  对开堆垛机只修改本机的货叉

                                    }
                                    else
                                    {
                                        // 已经分配货叉的直接从任务获取
                                        UseAwayFork = Convert.ToInt32(Model.CGeneralFunction.GetUseAwayFork(TaskIndex));
                                    }

                                    //关联任务分配货叉
                                    int TaskIndex1 = Convert.ToInt32(rr[0]); // 关联任务号
                                    if (UseAwayFork == 1)
                                    {
                                        UseAwayFork1 = 0;
                                        //if (StartX != 1)
                                        //{
                                        //    StartX = StartX - 1;
                                        //}
                                    }
                                    else
                                    {
                                        UseAwayFork1 = 1;

                                    }
                                    // 设置关联任务的货叉
                                    dbo.ExceSQL("UPDATE T_Monitor_Task SET F_UseAwayFork = '" + UseAwayFork1 + "' WHERE (F_ManageTaskIndex = " +
                                        Model.CGeneralFunction.GetManageTaskIndexfromMonitor(TaskIndex1) + ") AND (F_ManageTASKKINDINDEX = " +
                                        Model.CGeneralFunction.GetManageTaskKindIndexFromMonitor(TaskIndex1) + ") AND (F_DeviceIndex = " + DeviceIndex + ")");//20120615  对开堆垛机只修改本机的货叉
                                }

                                #endregion

                                #region 同步还是异步发送
                                if (Model.CGeneralFunction.DoubleForkIfSync(TaskIndex, DeviceIndex, devinfo.DeviceKind) == true)
                                {
                                    if (UseAwayFork == 1)//远货叉
                                    {
                                        StartZ = Model.CGeneralFunction.GetZCoorFromMonitor(TaskIndex, DeviceIndex, Order);//远货叉
                                        EndZ = 0;//远货叉
                                        StartZ1 = Model.CGeneralFunction.GetDoubleForkZ(Model.CGeneralFunction.GetManageTaskKindIndexFromMonitor(TaskIndex),
                                        Model.CGeneralFunction.GetManageTaskIndexfromMonitor(TaskIndex), DeviceIndex, Order);  //近货叉
                                        EndZ1 = 0; //近货叉
                                    }
                                    else
                                    {                   //近货叉
                                        StartZ1 = Model.CGeneralFunction.GetZCoorFromMonitor(TaskIndex, DeviceIndex, Order); //近货叉
                                        EndZ1 = 0; //近货叉
                                        StartZ = Model.CGeneralFunction.GetDoubleForkZ(Model.CGeneralFunction.GetManageTaskKindIndexFromMonitor(TaskIndex),
                                        Model.CGeneralFunction.GetManageTaskIndexfromMonitor(TaskIndex), DeviceIndex, Order);//远货叉
                                        EndZ = 0;//远货叉
                                    }

                                }
                                else
                                {

                                    if (UseAwayFork == 1)//远货叉
                                    {
                                        StartZ = Model.CGeneralFunction.GetZCoorFromMonitor(TaskIndex, DeviceIndex, Order);//远货叉
                                        EndZ = 0;//远货叉
                                        StartZ1 = 0; //近货叉
                                        EndZ1 = 0; //近货叉
                                    }
                                    else
                                    {                   //近货叉
                                        StartZ1 = Model.CGeneralFunction.GetZCoorFromMonitor(TaskIndex, DeviceIndex, Order); //近货叉
                                        EndZ1 = 0; //近货叉
                                        StartZ = 0;//远货叉
                                        EndZ = 0;//远货叉
                                    }

                                }
                                #endregion

                            }
                            //堆垛机的双叉送货指令，取货时已经指定远近叉，在此决定同步还是异步发送20100323
                            //if ((Order == 5) || (Order == 3)) // 20120527插入的避让指令将送不用区分远近叉
                            if (Order == 5)
                            {
                                UseAwayFork = Convert.ToInt32(Model.CGeneralFunction.GetUseAwayFork(TaskIndex));
                                #region 同步还是异步发送
                                if (Model.CGeneralFunction.DoubleForkIfSync(TaskIndex, DeviceIndex, devinfo.DeviceKind) == true)
                                {

                                    if (UseAwayFork == 1)//远货叉
                                    {
                                        EndZ = Model.CGeneralFunction.GetZCoorFromMonitor(TaskIndex, DeviceIndex, Order);//远货叉
                                        StartZ = 0;//远货叉
                                        EndZ1 = Model.CGeneralFunction.GetDoubleForkZ(Model.CGeneralFunction.GetManageTaskKindIndexFromMonitor(TaskIndex),
                                        Model.CGeneralFunction.GetManageTaskIndexfromMonitor(TaskIndex), DeviceIndex, Order);  //近货叉
                                        StartZ1 = 0; //近货叉
                                    }
                                    else
                                    {                   //近货叉
                                        EndZ1 = Model.CGeneralFunction.GetZCoorFromMonitor(TaskIndex, DeviceIndex, Order); //近货叉
                                        StartZ1 = 0; //近货叉
                                        EndZ = Model.CGeneralFunction.GetDoubleForkZ(Model.CGeneralFunction.GetManageTaskKindIndexFromMonitor(TaskIndex),
                                        Model.CGeneralFunction.GetManageTaskIndexfromMonitor(TaskIndex), DeviceIndex, Order);//远货叉
                                        StartZ = 0;//远货叉
                                    }

                                }
                                else
                                {

                                    if (UseAwayFork == 1)//远货叉
                                    {
                                        EndZ = Model.CGeneralFunction.GetZCoorFromMonitor(TaskIndex, DeviceIndex, Order);//远货叉
                                        StartZ = 0;//远货叉
                                        StartZ1 = 0; //近货叉
                                        EndZ1 = 0; //近货叉
                                    }
                                    else
                                    {                   //近货叉
                                        EndZ1 = Model.CGeneralFunction.GetZCoorFromMonitor(TaskIndex, DeviceIndex, Order); //近货叉
                                        StartZ1 = 0; //近货叉
                                        StartZ = 0;//远货叉
                                        EndZ = 0;//远货叉
                                    }

                                }
                                #endregion
                                //if (Model.CGeneralFunction.GetUseAwayFork(TaskIndex) == "1")//远货叉列数减一，因为近货叉是主货叉
                                //{
                                //    if (EndX != 1)
                                //    {
                                //        EndX = EndX - 1;
                                //    }
                                //}
                            }
                        }
                        itemnames = new string[11];//20101220
                        itemvalues = new string[11];
                        //byte0,byte1,byte2,byte3,byte4
                        //      int1         int3       
                        //int0(byte0,byte1);int1(byte1,byte2);int2(byte2,byte3);int3(byte3,byte4)

                        #region 管理任务的坐标在此转换为PLC能识别的坐标

                        #region 转换（Y）层坐标
                        ////01-29-23;01-30-23;01-24-23;01-23-23,[01-22-23,01-28-23]为三楼输送机保持不变，1排的其余列的货位层数+1；2排23层都加+1
                        //if ((((StartZ == 1) || (StartZ1 == 1)) && (StartY == 23) && ((StartX != 23) && (StartX != 22) && (StartX != 24) && (StartX != 28) && (StartX != 29) && (StartX != 30)))
                        //    || (((StartZ == 2) || (StartZ1 == 2)) && (StartY == 23)))
                        //{
                        //    StartY++;
                        //}

                        //if ((((EndZ == 1) || (EndZ1 == 1)) && (EndY == 23) && ((EndX != 23) && (EndX != 22) && (EndX != 24) && (EndX != 28) && (EndX != 29) && (EndX != 30)))
                        //    || (((EndZ == 2) || (EndZ1 == 2)) && (EndY == 23)))
                        //{
                        //    EndY++;
                        //}

                        #endregion

                        #region 转换（Z）排坐标

                        if (StartZ != 0)
                        {
                            if (StartZ % 2 == 0)
                            {
                                StartZ = 2;
                            }
                            else
                            {
                                StartZ = 1;
                            }
                        }
                        if (EndZ != 0)
                        {
                            if (EndZ % 2 == 0)
                            {
                                EndZ = 2;
                            }
                            else
                            {
                                EndZ = 1;
                            }
                        }
                        ////////////////
                        if (StartZ1 != 0)
                        {
                            if (StartZ1 % 2 == 0)
                            {
                                StartZ1 = 2;
                            }
                            else
                            {
                                StartZ1 = 1;
                            }
                        }
                        if (EndZ1 != 0)
                        {
                            if (EndZ1 % 2 == 0)
                            {
                                EndZ1 = 2;
                            }
                            else
                            {
                                EndZ1 = 1;
                            }
                        }

                        #endregion

                        #endregion

                        sn = Convert.ToInt32(dv[0]["F_DBW1Address"]);
                        itemnames[0] = "DB1,byte" + Convert.ToString(sn + 0);//消息头
                        itemvalues[0] = "0";
                        itemnames[1] = "DB1,byte" + Convert.ToString(sn + 1);//命令
                        itemvalues[1] = Order.ToString();

                        itemnames[2] = "DB1,int" + Convert.ToString(sn + 2);//任务号
                        itemvalues[2] = TaskIndex.ToString();

                        itemnames[3] = "DB1,byte" + Convert.ToString(sn + 4);
                        itemvalues[3] = StartX.ToString();

                        itemnames[4] = "DB1,byte" + Convert.ToString(sn + 5);
                        itemvalues[4] = StartY.ToString();

                        itemnames[5] = "DB1,byte" + Convert.ToString(sn + 6);
                        itemvalues[5] = StartZ.ToString();//远货叉

                        itemnames[6] = "DB1,byte" + Convert.ToString(sn + 9);
                        itemvalues[6] = EndX.ToString();

                        itemnames[7] = "DB1,byte" + Convert.ToString(sn + 10);
                        itemvalues[7] = EndY.ToString();

                     

                        itemnames[8] = "DB1,byte" + Convert.ToString(sn + 11);
                        itemvalues[8] = EndZ.ToString();//远货叉
                        //双叉关联的指令Z坐标



                        CCommonOPCClient.Hostname = CommonClassLib.AppSettings.GetValue("HostName");//20090922 devinfo.RemoteIP;
                        CCommonOPCClient.ProgID = CommonClassLib.AppSettings.GetValue("OPCProgID");
                        CCommonOPCClient.PlcConnectionID = devinfo.S7Connection;//20110216

                        if (CCommonOPCClient.SyncWriteAllItemValue(itemnames, itemvalues) == false)
                        {
                            return false;
                        }
                        itemnames[0] = "DB1,byte" + Convert.ToString(sn + 0);//消息头
                        itemvalues[0] = MessageIndex.ToString();


                        if (CCommonOPCClient.SyncWriteAllItemValue(itemnames, itemvalues) == false)
                        {
                            return false;
                        }
                        string sss = "";
                        for (int j = 0; j <= 10; j++)
                        {
                            sss += "***" + itemvalues[j];
                        }
                        CommonClassLib.CCarryConvert.WriteDarkCasket("OPCClient", "SendDeviceOrder", DeviceIndex.ToString(), sss);
                        if (WriteBarcode(DeviceIndex, TaskIndex) == false)
                        {
                            return false;
                        }
                    }

                    #endregion
                    #region RGV

                    //if (dv[0]["F_DeviceKindIndex"].ToString() == "4")
                    //{
                    //    itemnames = new string[5];
                    //    itemvalues = new string[5];
                    //    //byte0,byte1,byte2,byte3,byte4
                    //    //      int1         int3       
                    //    //int0(byte0,byte1);int1(byte1,byte2);int2(byte2,byte3);int3(byte3,byte4)
                    //    sn = Convert.ToInt32(dv[0]["F_DBW1Address"]);

                    //    itemnames[0] = "DB1,byte" + Convert.ToString(sn + 1);
                    //    itemvalues[0] = Order.ToString();
                    //    itemnames[1] = "DB1,int" + Convert.ToString(sn + 2);
                    //    itemvalues[1] = TaskIndex.ToString();
                    //    itemnames[2] = "DB1,int" + Convert.ToString(sn + 4);
                    //    itemvalues[2] = StartX.ToString();
                    //    itemnames[3] = "DB1,byte" + Convert.ToString(sn + 0);
                    //    itemvalues[3] = "0";

                    //    CCommonOPCClient.Hostname = CommonClassLib.AppSettings.GetValue("HostName");//20090922 devinfo.RemoteIP;
                    //    CCommonOPCClient.ProgID = CommonClassLib.AppSettings.GetValue("OPCProgID");
                    //    if (CCommonOPCClient.SyncWriteAllItemValue(itemnames, itemvalues) == false)
                    //    {
                    //        _commLayerError = "OPCClient.CSendDeviceOrder.SendDeviceOrder发生错误：" + CCommonOPCClient.OpcError;
                    //        return false;
                    //    }
                    //    itemnames[3] = "DB1,byte" + Convert.ToString(sn + 0);
                    //    itemvalues[3] = MessageIndex.ToString();
                    //    if (CCommonOPCClient.SyncWriteAllItemValue(itemnames, itemvalues) == false)
                    //    {
                    //        _commLayerError = "OPCClient.CSendDeviceOrder.SendDeviceOrder发生错误：" + CCommonOPCClient.OpcError;
                    //        return false;
                    //    }
                    //    string sss = "";
                    //    for (int j = 0; j <= 3; j++)
                    //    {
                    //        sss += "***" + itemvalues[j];
                    //    }
                    //    CommonClassLib.CCarryConvert.WriteDarkCasket("OPCClient", "SendDeviceOrder", DeviceIndex.ToString(), sss);
                    //}

                    #endregion
                }
                return true;
            }
            catch (Exception ex)
            {
                _commLayerError = "OPCClient.CSendDeviceOrder.SendDeviceOrder发生错误：" + ex.Message;
                return false;
            }
            finally
            {

                itemnames = null;

                itemvalues = null;
            }

        }
        /// <summary>
        /// 发送穿梭车、输送机设备命令
        /// </summary>
        /// <param name="MessageIndex">消息编号</param>
        /// <param name="TaskIndex">任务编号</param>
        /// <param name="Order">命令字</param>
        /// 穿梭车命令字： 
        ///1-复位 
        ///2-左接货
        ///3-左送货
        ///4-右接货
        ///5-右送货
        ///6-停止
        ///7-运动（运动到第4、5字节指定的目标设备所引）
        ///输送机命令字：
        ///1-入库（朝向库）
        ///2-出库（背向库）
        ///3-送货
        ///4-接货
        ///5-停止
        /// <param name="DeviceIndex">设备编号</param>
        ///<param name="ArrowDeviceIndex">对于输送机、穿梭车代表目标设备所引，
        /// 0-代表单一设备控制，无目标设备所引；1…65535代表目标设备所引（终点输送机的设备所引）</param>
        /// <returns>发送穿梭车、输送机设备命令是否成功</returns>
        public bool SendDeviceOrder(int MessageIndex, int TaskIndex, int Order, int DeviceIndex, int ArrowDeviceIndex)
        {
            StringBuilder[] itemnames;
            StringBuilder[] itemvalues;
            devinfo = Model.CGetInfo.GetDeviceInfo(DeviceIndex);
            try
            {
                
                int[] sendmes = new int[5] { MessageIndex, TaskIndex, Order, DeviceIndex, ArrowDeviceIndex };
                int boxtype = 0;// 箱型
                int QUANTITY = 0; // 数量 20131203
                int outtimes=0;
               // devinfo.SendMessage = sendmes;
                Model.CGetInfo.SetDeviceMessage(devinfo);

                if (devinfo.UseCommonDB == "1")
                {
                    itemnames = new StringBuilder[5] { new StringBuilder(""), new StringBuilder(""), new StringBuilder(""), new StringBuilder(""), new StringBuilder("") }; ;
                    itemvalues = new StringBuilder[5] { new StringBuilder(""), new StringBuilder(""), new StringBuilder(""), new StringBuilder(""), new StringBuilder("") }; ;
                }
                else if (12505 == ArrowDeviceIndex || 12116 == ArrowDeviceIndex)
                {
                     itemnames = new StringBuilder[6] { new StringBuilder(""), new StringBuilder(""), new StringBuilder(""), new StringBuilder(""), new StringBuilder(""), new StringBuilder("") }; ;
                    itemvalues = new StringBuilder[6] { new StringBuilder(""), new StringBuilder(""), new StringBuilder(""), new StringBuilder(""), new StringBuilder("") , new StringBuilder("")}; ;
                }
                
                else 
                {
                    itemnames = new StringBuilder[4] { new StringBuilder(""), new StringBuilder(""), new StringBuilder(""), new StringBuilder("") }; ;
                    itemvalues = new StringBuilder[4] { new StringBuilder(""), new StringBuilder(""), new StringBuilder(""), new StringBuilder("") }; ;
                }

                int sn = 0;

                if (devinfo == null)
                {
                    _commLayerError = "OPCClient.CSendDeviceOrder.SendDeviceOrder发生错误：设备索引不存在!";
                    return false;
                }
                else
                {
                    if (12505 == ArrowDeviceIndex || 12116 == ArrowDeviceIndex)
                    {
                       
                        #region 获得要叠盘的表箱层数
                        if (12505 == ArrowDeviceIndex || 12116 == ArrowDeviceIndex)
                        {
                            Model.CGeneralFunction.GetBoxTypeAndQUANTITYFromMonitor(TaskIndex, out boxtype, out QUANTITY);
                        }
                        #endregion
                    }
                    else
                    {
                        //itemnames = new StringBuilder[4];
                        //itemvalues = new StringBuilder[4];
                        //outtimes = 3;
                    }
                    if (devinfo.DeviceKind == 7)
                    {
                        return true;
                    }
                    if (devinfo.DeviceKind == 1)
                    {//堆垛机不允许使用此方法
                        _commLayerError = "OPCClient.CSendDeviceOrder.SendDeviceOrder发生错误：堆垛机和RGV不允许使用此方法!";
                        return false;
                    }
                    //byte0,byte1,byte2,byte3,byte4
                    //      int1         int3       
                    //int0(byte0,byte1);int1(byte1,byte2);int2(byte2,byte3);int3(byte3,byte4)
                    sn = Convert.ToInt32(devinfo.Dbw1Address);
                    if (12505 == ArrowDeviceIndex || 12116 == ArrowDeviceIndex)
                    {//20110318
                        itemnames[0].Append(Model.CGeneralFunction.DBSend).Append(",byte").Append(Convert.ToString(sn + 1));
                        itemvalues[0].Append(Order.ToString());
                        itemnames[1].Append(Model.CGeneralFunction.DBSend).Append(",int").Append(Convert.ToString(sn + 2));
                        itemvalues[1].Append(TaskIndex.ToString());
                        itemnames[2].Append(Model.CGeneralFunction.DBSend).Append(",int").Append(Convert.ToString(sn + 4));
                        itemvalues[2].Append(ArrowDeviceIndex.ToString());
                        itemnames[3].Append(Model.CGeneralFunction.DBSend).Append(",byte").Append(Convert.ToString(sn + 0));
                        itemvalues[3].Append("0");
                        itemnames[4].Append(Model.CGeneralFunction.DBSend).Append(",byte").Append(Convert.ToString(sn + 6));
                        itemvalues[4].Append(boxtype);
                        itemnames[5].Append(Model.CGeneralFunction.DBSend).Append(",byte").Append(Convert.ToString(sn + 7));
                        itemvalues[5].Append(QUANTITY);     
                    }
                    else
                    {
                        itemnames[0].Append(Model.CGeneralFunction.DBSend).Append(",byte").Append(Convert.ToString(sn + 1));
                        itemvalues[0].Append(Order.ToString());
                        itemnames[1].Append(Model.CGeneralFunction.DBSend).Append(",int").Append(Convert.ToString(sn + 2));
                        itemvalues[1].Append(TaskIndex.ToString());
                        itemnames[2].Append(Model.CGeneralFunction.DBSend).Append(",int").Append(Convert.ToString(sn + 4));
                        itemvalues[2].Append(ArrowDeviceIndex.ToString());
                        itemnames[3].Append(Model.CGeneralFunction.DBSend).Append(",byte").Append(Convert.ToString(sn + 0));
                        itemvalues[3].Append("0");
                    }
                    if (devinfo.UseCommonDB == "1")
                    {
                        itemnames[4].Append(Model.CGeneralFunction.DBSend).Append(",int").Append(Convert.ToString(sn + 6));
                        itemvalues[4].Append(DeviceIndex.ToString());
                    }
                    CCommonOPCClient.Hostname = CommonClassLib.AppSettings.GetValue("HostName");//20090922 devinfo.RemoteIP;
                    CCommonOPCClient.ProgID = CommonClassLib.AppSettings.GetValue("OPCProgID");
                    CCommonOPCClient.PlcConnectionID = devinfo.S7Connection;//20110216
                    if (CCommonOPCClient.SyncWriteAllItemValue(itemnames, itemvalues) == false)
                    {
                        return false;
                    }
                    itemnames[3].Remove(0, itemnames[3].Length);
                    itemnames[3].Append(Model.CGeneralFunction.DBSend).Append(",byte").Append(Convert.ToString(sn + 0));
                    itemvalues[3].Remove(0, itemvalues[3].Length);
                    itemvalues[3].Append(MessageIndex);
                    if (CCommonOPCClient.SyncWriteAllItemValue(itemnames, itemvalues) == false)
                    {
                        return false;
                    }

                    sss.Remove(0, sss.Length);
                    sss.Append("**写标志").Append(MessageIndex.ToString()).Append ("起始地址").Append(Model.CGeneralFunction.DBSend).Append(",byte").Append(Convert.ToString(sn + 0)). Append("**命令字" + Order.ToString()).Append("**任务号" + TaskIndex.ToString())
                                        .Append("**目标位置" + ArrowDeviceIndex.ToString());
                    if (ArrowDeviceIndex == 12505 || 12116 == ArrowDeviceIndex)
                    {
                       
                        sss.Append ("**箱型"+boxtype .ToString ()).Append ("**数量"+QUANTITY .ToString ());
                    }
                    
                    CommonClassLib.CCarryConvert.WriteDarkCasket("OPCClient", "发送指令", DeviceIndex.ToString(), sss.ToString());
                    if (MessageIndex == 1)
                    {
                        if (WriteBarcode(DeviceIndex, TaskIndex) == false)
                        {
                            return false;
                        }
                    }
                }
                return true;
            }
            catch (Exception ex)
            {
                _commLayerError = "OPCClient.CSendDeviceOrder.SendDeviceOrder发生错误：" + ex.Message;
                return false;
            }
            finally
            {
                devinfo = null;
                itemnames = null;
                itemvalues = null;
            }

        }
        
        /// <summary>
        /// 上位机给下位机发送烟箱按品牌码分道信息共15字节,有数据时写入实际数据，否则全部写零
        /// </summary>
        /// <param name="DeviceIndex">码垛位设备号索引</param>
        /// <param name="TobaccoCode">第3--15字节,烟箱码</param>
        /// <param name="HaveFirstProjectCode">第1字节,1-有一号工程码,0-无一号工程码</param>
        /// <param name="IfSmallTobacco">第2字节,1-异型烟箱,0-正常烟箱</param>
        /// <returns>发送烟箱按品牌码分道信息是否成功</returns>
        public bool SendDeviceOrder(int DeviceIndex, string TobaccoCode, bool HaveFirstProjectCode, bool IfSmallTobacco,int Count)
        {
            StringBuilder[] itemnames=new StringBuilder[16];
            StringBuilder[] itemvalues = new StringBuilder[16];
            devinfo = Model.CGetInfo.GetDeviceInfo(DeviceIndex);
            try
            {

                int sn = 0;
                
                if (devinfo==null )
                {
                    _commLayerError = "OPCClient.CSendDeviceOrder.SendDeviceOrder发生错误：设备所引不存在!";
                    return false;
                }
                else
                {
                    sn = Convert.ToInt32(devinfo.Dbw1Address);

                    itemnames[0].Append(Model.CGeneralFunction.DBSend).Append(",byte").Append((sn + 0).ToString());
                    if (HaveFirstProjectCode == true)
                    {
                        itemvalues[0].Append( "1");
                    }
                    else
                    {
                        itemvalues[0] .Append( "0");
                    }
                    itemnames[1].Append(Model.CGeneralFunction.DBSend).Append(",byte").Append((sn + 1).ToString());
                    if (IfSmallTobacco == true)
                    {
                        itemvalues[1] .Append( "1");
                    }
                    else
                    {
                        itemvalues[1] .Append( "0");
                    }
                    for (int i = 2; i <= 14; i++)
                    {
                        itemnames[i].Append(Model.CGeneralFunction.DBSend).Append(",byte").Append((sn + i).ToString());
                        itemvalues[i] .Append( Strings.Asc(TobaccoCode.Substring(i - 2, 1)).ToString());
                    }
                    itemnames[15].Append(Model.CGeneralFunction.DBSend).Append(",byte").Append((sn + 15).ToString());
                    itemvalues[15] .Append( Count.ToString());

                    CCommonOPCClient.Hostname = CommonClassLib.AppSettings.GetValue("HostName");//20090922 devinfo.RemoteIP;
                    CCommonOPCClient.ProgID = CommonClassLib.AppSettings.GetValue("OPCProgID");
                    CCommonOPCClient.PlcConnectionID = devinfo.S7Connection;//20110216
                    if (CCommonOPCClient.SyncWriteAllItemValue(itemnames, itemvalues) == false)
                    {
                        return false;
                    }
                }
                return true;
            }
            catch (Exception ex)
            {
                _commLayerError = "OPCClient.CSendDeviceOrder.SendDeviceOrder发生错误：" + ex.Message;
                return false;
            }
            finally
            {
                devinfo = null;
                itemnames = null;
                itemvalues =null;
            }
        }
        
        public bool WriteBarcode(int deviceindex,int taskindex)
        {
            Model.MDevice devinfo;
            StringBuilder[] itemnames = new StringBuilder[11];
            StringBuilder[] itemvalues = new StringBuilder[11];
            
            int sn = 0;
            try
            {
                devinfo = Model.CGetInfo.GetDeviceInfo(deviceindex);
                sss.Remove(0, sss.Length);
                sss.Append("SELECT F_MonitorIndex, F_TxtParam FROM T_Monitor_Task WHERE (F_MonitorIndex = " ).Append( taskindex).Append( ")");
                DataView dvb = dbo.ExceSQL(sss.ToString()).Tables[0].DefaultView;
                if (dvb.Count > 0)
                {
                    sss.Remove(0, sss.Length);
                    sss.Append(dvb[0]["F_TxtParam"].ToString());

                    if ((sss.ToString() == "-") || (sss.ToString() == "")) return true;
                }
                else
                {
                    _commLayerError = "OPCClient.CSendDeviceOrder.SendDeviceOrder发生错误：写入附加条码时在调度任务表内没找到条码!";
                    return false;
                }
                
                if (devinfo.AppendBarcode > 0)
                {
                    Model.MDevice devinfo1 = Model.CGetInfo.GetDeviceInfo(devinfo.AppendBarcode);
                    if (devinfo1.DeviceIndex == 0)
                    {
                        _commLayerError = "OPCClient.CSendDeviceOrder.SendDeviceOrder发生错误：写入附加条码时设备索引不存在!";
                        return false;
                    }
                    else
                    {

                        //byte0,byte1,byte2,byte3,byte4
                        //      int1         int3       
                        //int0(byte0,byte1);int1(byte1,byte2);int2(byte2,byte3);int3(byte3,byte4)
                        sn = Convert.ToInt32(devinfo1.Dbw1Address);
                       // devinfo1 = null;
                        if (devinfo1.DeviceIndex == 61070)
                        {

                        }
                        for (int i = 0; i <= 9; i++)
                        {
                            itemnames[i].Append(Model.CGeneralFunction.DBSend).Append(",byte").Append(Convert.ToString(sn + i + 1));
                            itemvalues[i] .Append( Strings.Asc(sss.ToString().Substring((i), 1)).ToString());
                        }
                        itemnames[10].Append(Model.CGeneralFunction.DBSend).Append(",byte").Append(Convert.ToString(sn + 0));
                        itemvalues[10] .Append( "1");
                        CCommonOPCClient.Hostname = CommonClassLib.AppSettings.GetValue("HostName");//20090922 devinfo.RemoteIP;
                        CCommonOPCClient.ProgID = CommonClassLib.AppSettings.GetValue("OPCProgID");
                        CCommonOPCClient.PlcConnectionID = devinfo.S7Connection;//20110216
                        if (CCommonOPCClient.SyncWriteAllItemValue(itemnames, itemvalues) == false)
                        {
                            return false;
                        }

                        CommonClassLib.CCarryConvert.WriteDarkCasket("OPCClient", "SendDeviceOrder", deviceindex.ToString(), sss.ToString());
                    }
                    
                    return true;
                }
                else
                {
                    return true; ;
                }
            }
            catch (Exception ex)
            {
                _commLayerError = "OPCClient.CSendDeviceOrder.WriteBarcode发生错误：" + ex.Message;
                return false;
            }
            finally
            {
                devinfo=null;
                itemnames =null;
                itemvalues =null;
                
            }
        }
        
        /// <summary>
        /// 向PLC的DB区写入数据
        /// </summary>
        /// <param name="ItemNames">标签变量名称数组</param>
        /// <param name="ItemValues">标签值数组</param>
        /// <returns></returns>
        public bool WriteDBData(StringBuilder[] ItemNames, StringBuilder[] ItemValues ,int deviceindex)
        {
            try
            {
                devinfo = Model.CGetInfo.GetDeviceInfo(deviceindex);
                CCommonOPCClient.PlcConnectionID = devinfo.S7Connection;//20110216
                if (CCommonOPCClient.SyncWriteAllItemValue(ItemNames, ItemValues) == false)
                {
                    return false;
                }
                else
                {
                    sss.Remove(0, sss.Length);
                    sss.Append("**" + ItemNames[0].ToString() + "**" + ItemValues[0].ToString());

                    CommonClassLib.CCarryConvert.WriteDarkCasket("OPCClient", "发送应答标志", deviceindex.ToString (), sss.ToString());
                    return true;
                }
            }
            catch (Exception ex)
            {
                _commLayerError = "OPCClient.CSendDeviceOrder.WriteDBData发生错误：" + ex.Message;
                return false;
            }
            finally
            {
                ItemNames = null;
                ItemValues=null;
            }
        }

        public bool SendDeviceOrder(int MessageIndex, int TaskIndex, int Order, int DeviceIndex, int StartX, int StartY, int StartZ, int EndX, int EndY, int EndZ, string DoubleFork)
        {
            return true;

        }


    }
}
