山大泰克条屏写串口的核心代码(海宏原创,转载请注明)

山大泰克条屏写串口的核心代码,海宏原创,转载请注明。

using System;
using System.Collections.Generic;
using System.Text;
//
using System.Runtime.InteropServices;
using System.IO.Ports;
using System.Windows.Forms;
using iPublic;

namespace sdLed
{
    /// <summary>
    /// 用来连接LED的API。作者:海宏软件,周承昊,20130411
    /// </summary>
    public partial class apiComm
    {
        //System.IO.Ports.SerialPort port = null;

        //测试用的,考虑用这种方式,现在用不到了
        //[DllImport("API_COM.DLL", EntryPoint = "com_init", CharSet = CharSet.Ansi)]
        //public static extern Boolean com_init(int com, ulong baud);
        //[DllImport("API_COM.DLL", EntryPoint = "com_rest")]
        //public static extern Boolean com_rest();
        //[DllImport("API_COM.DLL", EntryPoint = "com_send", CharSet = CharSet.Ansi)]
        //public static extern Boolean com_send(ref string buf, int len); //StringBuilder buf

        
        /* 下边是delphi的定义
        function com_init(com:Integer; baud:Dword):Boolean;stdcall;external 'api_com.dll';
        function com_rest:Boolean;stdcall;external 'api_com.dll';
        function com_send(buf:PChar; len:Integer):Boolean;stdcall;external 'api_com.dll';
        */
        /// <summary>
        /// 向LED发送文字
        /// </summary>
        /// <returns></returns>
        public static int sendText(string sPort, ulong baud, string sText)
        {
            int result = -1, j=0;
            string s = "";
            iDefine._SysConfig sys=iDefine.SysConfig;                   //设置
            StringBuilder buf = null;
            System.IO.Ports.SerialPort port = null;
            try
            {
                //处理传入的字符串,山大格式的
                buf = buildSdthText(sText, sys.sLed屏号, sys.nLed出场方式, sys.nLed移动速度, sys.nLed停留时间, sys.nLed显示次数);
                //下边这个地方很奇怪,C#发出去的字符串,总是莫名其妙的超出F3就乱码,于是转成Unicode,但是Unicode每个字节前多一个00字节,这样移除
                byte[] db2 = Encoding.Unicode.GetBytes(buf.ToString()), db = new byte[db2.Length / 2];
                for (int i = 0; i < db2.Length; i++) if ((i % 2) == 0) db[i / 2] = db2[i];
                //打开串口,发过去
                port = new SerialPort(sPort);
                port.BaudRate = Convert.ToInt32(baud);                  //波特率
                port.Parity = System.IO.Ports.Parity.None;              //校验位
                port.DataBits = 8;                                      //数据位
                port.StopBits = System.IO.Ports.StopBits.One;           //停止位
                port.NewLine = "
";                                    //这行必须,c#默认在发完的数据后加了
0A0D回车换行
                port.Encoding = Encoding.Unicode;                       //这行可以不写
                //port.RtsEnable = true;    port.DtrEnable = true;
                if (!port.IsOpen) port.Open();                          //打开端口
                System.Threading.Thread.Sleep(10);
                port.Write(db, 0, db.Length);                           //发出。port.Write(buf.ToString());
                //延时
                System.Threading.Thread.Sleep(10);
                port.Close();
                
                //换一种方式再写一遍
                //s = buf.ToString();
                //com_init(1, baud);
                //com_send(sDb, sDb.Length);
                //com_send(ref s, s.Length);
                //com_rest();
                //完成
            }
            catch (Exception x)
            {
                throw new Exception("发送文字出错:" + x.Message + "
 错误来源:sendText");
            }
            finally
            {
                if (port != null) port.Close();          //关闭
            }
            //
            return result;
        }
        /// <summary>
        /// 组装生成山大格式的LED字符串
        /// </summary>
        /// <param name="sText">要组装的原始文字</param>
        /// <returns>返回值</returns>
        public static StringBuilder buildSdthText(string sText, string sLed屏号_长度6字符,
            byte 出场方式, byte 移动速度, byte 停留时间, byte 显示次数
            )
        {
            StringBuilder result = new StringBuilder();
            DateTime dNow=DateTime.Now;
            byte b = 0;
            int n = 0;
            //标记头
            byte[] bs=new byte[]{0x23,0x14,0x24,0x15,0x13,0x18};
            for (int i = 0; i <bs.Length; i++) result.Append((char)bs[i]);
            //凭号,6字节
            string sLed = sLed屏号_长度6字符.Trim();
            if (string.IsNullOrEmpty(sLed)) sLed = "XXXXXX";    //全部屏幕
            sLed = sLed.PadLeft(6, '0');                        //凑够6字符
            result.Append(sLed);
            //控制命令:D
            StringBuilder mainDb = new StringBuilder();         //从控制位开始的所有数据
            mainDb.Append('D');
            //出场方式等
            mainDb.Append((char)出场方式);
            mainDb.Append((char)移动速度);
            mainDb.Append((char)停留时间);
            mainDb.Append((char)显示次数);
            //汉字个数
            byte nLen = Convert.ToByte(sText.Length);
            mainDb.Append((char)nLen);
            //发送文字内容。数据可以是字符和汉字。汉字用区位码表示,字符用ASCII码表示
            StringBuilder sQuwei = new StringBuilder();
            for (int i = 0; i < sText.Length; i++)
            {
                byte[] bytes = System.Text.Encoding.GetEncoding("GB2312").GetBytes(sText.Substring(i, 1));
                //如果长度1位,直接加入,否则两位加入
                if (bytes.Length == 1) sQuwei.Append((char)bytes[0]);
                else
                {
                    sQuwei.Append((char)bytes[0]);    //取出低字节编码内容(两位16进制)
                    sQuwei.Append((char)bytes[1]);    //取出高字节编码内容(两位16进制)
                }
            }
            mainDb.Append(sQuwei);              //文字
            //时钟格式:时钟以十六进制表示:秒    分    时    日    月    星期    年
            mainDb.Append((char)dNow.Second);   //
            mainDb.Append((char)dNow.Minute);   //
            mainDb.Append((char)dNow.Hour);     //
            mainDb.Append((char)dNow.Day);      //
            mainDb.Append((char)dNow.Month);    //
            n = getWeekDay(dNow.Year, dNow.Month, dNow.Day);
            if (n > 6) n = 0;                   //星期日用0X00表示、星期一用0X01表示
            mainDb.Append((char)n);
            b = Convert.ToByte(dNow.Year.ToString().Substring(2));  //年只发后两位,如:2008年只发送08 (即0X08)
            mainDb.Append((char)b);
            //累加校验和:从控制命令开始的所有数据之和不包括其本身,高位益出不处理
            n=0;
            for (int i = 0; i < mainDb.Length; i++) n += (byte)mainDb[i];
            bs = BitConverter.GetBytes(n);
            b = bs[0];                          //最低位的一个byte
            mainDb.Append((char)b);
            //组装拼合
            result.Append(mainDb);
            //完成
            return result;
        }

        /// <summary>根据日期,获得星期几</summary>
        /// <param name="y"></param>
        /// <param name="m"></param>
        /// <param name="d"></param>
        /// <returns>星期几,1代表星期一;7代表星期日</returns>
        public static int getWeekDay(int y, int m, int d)
        {
            if (m == 1) m = 13;
            if (m == 2) m = 14;
            int week = (d + 2 * m + 3 * (m + 1) / 5 + y + y / 4 - y / 100 + y / 400) % 7 + 1;
            return week;
        }

    }


    public partial class QuWeiMaHanZi
    {
        /// <summary>
        /// 汉字转区位码
        /// </summary>
        /// <param name="character"></param>
        /// <returns></returns>
        public static string CharacterToCoding(string character)
        {
            string coding = string.Empty;
            for (int i = 0; i < character.Length; i++)
            {
                byte[] bytes = System.Text.Encoding.GetEncoding("GB2312").GetBytes(character.Substring(i, 1));
                string lowCode = System.Convert.ToString(bytes[0], 16); //取出低字节编码内容(两位16进制)
                if (lowCode.Length == 1)
                    lowCode = "0" + lowCode;
                string hightCode = System.Convert.ToString(bytes[1], 16);//取出高字节编码内容(两位16进制)
                if (hightCode.Length == 1)
                    hightCode = "0" + hightCode;
                coding += (lowCode + hightCode);//加入到字符串中,
            }
            return coding;
        }
        /// <summary>
        /// 区位码取汉字
        /// </summary>
        /// <param name="coding"></param>
        /// <returns></returns>
        public static string CodingToCharacter(string coding)
        {
            string characters = string.Empty;
            if (coding.Length % 4 != 0)//编码为16进制,必须为4的倍数。
            {
                throw new System.Exception("编码格式不正确");
            }
            for (int i = 0; i < coding.Length / 4; i++)
            {
                byte[] bytes = new byte[2];
                int j = i * 4;
                string lowCode = coding.Substring(j, 2); //取出低字节,并以16进制进制转换
                bytes[0] = System.Convert.ToByte(lowCode, 16);
                string highCode = coding.Substring(j + 2, 2); //取出高字节,并以16进制进行转换
                bytes[1] = System.Convert.ToByte(highCode, 16);
                string character = System.Text.Encoding.GetEncoding("GB2312").GetString(bytes);
                characters += character;
            }
            return characters;
        }
    }

}

原文地址:https://www.cnblogs.com/HaiHong/p/5581337.html