⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 serialport.cs

📁 本源码为OpenNETCF源代码
💻 CS
📖 第 1 页 / 共 3 页
字号:
		/// </summary>
		/// <return>A value of the enumeration <see cref="Handshake"/>.</return>
#if DESIGN
	[DefaultValue(0x0)]
#endif
		public Handshake Handshake 
		{
			get {
				return this.mHandshake;
			}
			set {
				if ((value < Handshake.None) || (value > Handshake.RequestToSendXOnXOff)) {
					throw new ArgumentOutOfRangeException("Handshake. Use the enum");
				}
				this.mHandshake = value;
				if (this.IsOpen) {
					this.UpdateSettings();
				}
			}
		}

		/// <summary>
		/// Gets the open or closed status of the <see cref="SerialPort"/> object.
		/// </summary>
		/// <return>true if the serial port is open, otherwise false.</return>
#if DESIGN
	[Browsable(false)]
#endif
		public bool IsOpen 
		{
			get {
				return this.mIsOpen;
			}
		}
		/// <summary>
		/// Gets or sets the parity-checking protocol.
		/// </summary>
		/// <return>A <see cref="Parity"/> object that represents the parity-checking protocol.</return>
#if DESIGN
	[DefaultValue(0x0)]
#endif
		public Parity Parity {
			get 
			{
				return this.mParity;
			}
			set {
				if ((value < Parity.None) || (value > Parity.Space)) {
					throw new ArgumentOutOfRangeException("Parity. Use the enum");
				}
				this.mParity = value;
				if (this.IsOpen) {
					this.UpdateSettings();
				}
			}
		}
		/// <summary>
		/// Gets or sets the byte that is used to replace invalid characters in a data stream when a parity error occurs.
		/// </summary>
		/// <return>A byte used to replace invalid characters.</return>
#if DESIGN
	[DefaultValue(63)]
#endif
		public byte ParityReplace {
			get 
			{
				return this.mErrorChar;
			}
			set {
				this.mErrorChar = value;
				if (this.IsOpen) {
					this.UpdateSettings();
				}
			}
		}
		/// <summary>
		/// Gets or sets the port for communications, including but not limited to all available COM ports.
		/// </summary>
		/// <value>A string object representing the communications port e.g. "COM1", "COM10" etc.</value>
#if DESIGN
	[DefaultValue("COM1")]
#endif		
		public string PortName {
			get 
			{
				//trim the last colon if present
				return this.mPortName.Trim(new char[]{'\\','.',':'});
				//return this.mPortName.TrimEnd(new char[]{':'});
				
			}
			set {
				if(! CommAPI.FullFramework) {
					if(! value.EndsWith(":")) {
						//append the colon
						this.mPortName = "\\\\.\\" + value + ":";
						return;
						//throw new ApplicationException("On WinCE comm port must end with :");						
					}
				}

				this.mPortName = "\\\\.\\" + value;
			}
		}

		/// <summary>
		/// Gets or sets the number of bytes in the internal input buffer before a OpenNETCF.IO.Ports.SerialPort.ReceivedEvent is fired.
		/// </summary>
		/// <return>An integer object.</return>
#if DESIGN
	[DefaultValue(1)]
#endif
		public int ReceivedBytesThreshold 
		{
			get {
				return this.mRthreshold;
			}
			set {
				this.mRthreshold = value;
			}
		}

		/// <summary>
		/// Gets or sets the standard number of stopbits per byte.
		/// </summary>
		/// <return>A value of the enumeration <see cref="StopBits"/>.</return>
#if DESIGN
	[DefaultValue(1)]
#endif		
		public StopBits StopBits {
			get 
			{
				return this.mStopBits;
			}
			set {
				if ((value < StopBits.One) || (value > StopBits.OnePointFive)) {
					throw new ArgumentOutOfRangeException("StopBits. Use the Enum");
				}
				this.mStopBits = value;
				if (this.IsOpen) {
					this.UpdateSettings();
				}
			}
		}
		/// <summary>
		/// Gets or sets whether the Request to Transmit (RTS) signal is enabled during serial communication.
		/// </summary>
		/// <return>true to enable RTS, otherwise false.</return>
#if DESIGN
	[DefaultValue(false)]
#endif
		public bool RtsEnable {
			get 
			{
				return (this.mRts == 1);
			}
			set {
				if(this.mRts < 0) return;
				if(hPort == (IntPtr)CommAPI.INVALID_HANDLE_VALUE) return;

				if (value) {
					if (m_CommAPI.EscapeCommFunction(hPort, CommEscapes.SETRTS))
						this.mRts = 1;
					else
						throw new ApplicationException("Failed to set RTS!");
				}
				else {
					if (m_CommAPI.EscapeCommFunction(hPort, CommEscapes.CLRRTS))
						this.mRts = 0;
					else
						throw new ApplicationException("Failed to clear RTS!");
				}
			}
		}
		
		/// <summary>
		/// Gets or sets the number of milliseconds before a timeout occurs when a write operation does not finish.
		/// </summary>
		/// <return>An integer object.</return>
#if DESIGN
	[DefaultValue(-1)]
#endif
		public int WriteTimeout {
			get 
			{
				return this.mWriteTimeout;
			}
			set {
				if ((value == 0) || (value < InfiniteTimeout)) {
					throw new ArgumentOutOfRangeException("WriteTimeout. Only valid negative value is -1");
				}
				this.mWriteTimeout = value;
				if (this.IsOpen) {
					this.UpdateTimeouts();
				}
			}
		}
		/// <summary>
		/// Gets or sets the number of milliseconds before a timeout occurs when a read operation does not finish.
		/// </summary>
		/// <return>An integer object.</return>
#if DESIGN
	[DefaultValue(-1)]
#endif
		public int ReadTimeout {
			get 
			{
				return this.mReadTimeout;
			}
			set {
				if (value < InfiniteTimeout) {
					throw new ArgumentOutOfRangeException("ReadTimeout. Cannot be 0 or <-1");
				}
				this.mReadTimeout = value;
				if (this.IsOpen) {
					this.UpdateTimeouts();
				}
			}
		}
		/// <summary>
		/// Gets or sets the size of the serial port output buffer.
		/// </summary>
		/// <return>An integer value representing the size of the output buffer. The default value is 2048.</return>
#if DESIGN
	[DefaultValue(2048)]
#endif
		public int WriteBufferSize {
			get 
			{
				return this.mTxBufferSize;
			}
			set {
				if (value <= 0) {
					throw new ArgumentOutOfRangeException("WriteBufferSize must be > 0");
				}
				this.mTxBufferSize = value;
				if (this.IsOpen) {					
					throw new InvalidOperationException("WriteBufferSize cannot be set when open");
				}
			}
		}
		/// <summary>
		/// Gets or sets the size of the <see cref="SerialPort"/> input buffer.
		/// </summary>
		/// <return>An integer value representing the buffer size The default value is 4096..</return>
#if DESIGN
	[DefaultValue(4096)]
#endif
		public int ReadBufferSize {
			get 
			{
				return this.mRxBufferSize;
			}
			set {
				if (value <= 0) {
					throw new ArgumentOutOfRangeException("ReadBufferSize must be > 0");
				}
				this.mRxBufferSize = value;
				if (this.IsOpen) {
					throw new InvalidOperationException("ReadBufferSize cannot be set when open");
				}
			}
		} 
		/// <summary>
		/// Gets or sets the character encoding for pre- and post-transmission conversion of text.
		/// </summary>
		/// <return>A <see cref="System.Text.Encoding"/> object.</return>
#if DESIGN
	[Browsable(false)]
#endif
		public Encoding Encoding 
		{
			get {
				return this.mEncoding;
			}
			set {
				if (value == null) {
					throw new ArgumentNullException("Encoding");
				}
				this.mEncoding = value;
				this.mDecoder = this.mEncoding.GetDecoder();
			}
		}

		#endregion

		#region Public Methods
		/// <summary>
		/// Not Currently Supported. Gets an array of serial port names for the current machine.
		/// </summary>
		/// <returns>An array of serial port names for the current machine.</returns>
		public static string[] GetPortNames() {
			// TODO iterate over reg key and return array of port names
			// @"HARDWARE\DEVICEMAP\SERIALCOMM"
			throw new NotSupportedException("not yet");
		}

		/// <summary>
		/// Discards data from the serial driver's receive buffer.
		/// </summary>
		public void DiscardInBuffer() {
			if (!this.IsOpen) {
				throw new InvalidOperationException("Port is not open");
			}

			if (m_CommAPI.PurgeComm(hPort, 10) != 0 ) {
				throw new ApplicationException("could not discard in buffer");
			}

			this.mReadLen = 0;
			this.mReadPos = 0;
		}
		/// <summary>
		/// Discards data from the serial driver's transmit buffer.
		/// </summary>
		public void DiscardOutBuffer() {
			if (!this.IsOpen) {
				throw new InvalidOperationException("Port is not open");
			}

			if (m_CommAPI.PurgeComm(hPort, 5) != 0 ) {
				throw new ApplicationException("could not discard out buffer");
			}
		}

		/// <summary>
		/// Opens a new serial port connection.
		/// </summary>
		public void Open() {
			if(this.mIsOpen) throw new InvalidOperationException("Comm Port is already open!");

			if(CommAPI.FullFramework) {
				// set up the overlapped tx IO
				OVERLAPPED o = new OVERLAPPED();
				this.mTxOverlapped = LocalAlloc(0x40, Marshal.SizeOf(o));
				o.Offset = 0; 
				o.OffsetHigh = 0;
				o.hEvent = IntPtr.Zero;
				Marshal.StructureToPtr(o, this.mTxOverlapped, true);
			}

			hPort = m_CommAPI.CreateFile(this.mPortName);

			if(hPort == (IntPtr)CommAPI.INVALID_HANDLE_VALUE) {
				int e = Marshal.GetLastWin32Error();

				if(e == (int)APIErrors.ERROR_ACCESS_DENIED) {
					// port is unavailable
					throw new ApplicationException("ERROR_ACCESS_DENIED");
				}

				// ClearCommError failed!
				string error = String.Format("CreateFile Failed: {0}", e);
				throw new ApplicationException(error);
			}

			
			this.mIsOpen = true;

			// clear errors
			CommErrorFlags errorFlags = new CommErrorFlags();
			CommStat commStat = new CommStat();				
			if(!m_CommAPI.ClearCommError(hPort, ref errorFlags, commStat)) {
				throw new ApplicationException("Failed to clear error/read");
			}

			// set queue sizes
			m_CommAPI.SetupComm(hPort, this.mRxBufferSize, this.mTxBufferSize);

			// update dcb
			this.UpdateSettings();

			// store some state values
			this.mInBreak = false;

			// read/write timeouts
			this.UpdateTimeouts();

			// start the receive thread
			this.mEventThread = new Thread(new ThreadStart(CommEventThread));
			this.mEventThread.Priority = ThreadPriority.Normal; //by design
			this.mEventThread.Start();

			// wait for the thread to actually get spun up
			this.mThreadStarted.WaitOne();
		}

		/// <summary>
		/// Closes the port connection, sets OpenNETCF.IO.Ports.SerialPort.IsOpen to false and disposes of the internal System.IO.Stream object.
		/// </summary>
		public void Close() {
			if(this.mTxOverlapped != IntPtr.Zero) {
				LocalFree(this.mTxOverlapped);
				this.mTxOverlapped = IntPtr.Zero;
			}

			if(!this.mIsOpen) return;

			this.mIsOpen = false; // to help catch intentional close

			if(m_CommAPI.CloseHandle(hPort)) {
				m_CommAPI.SetEvent(this.mCloseEvent);

				this.mIsOpen = false;

				hPort = (IntPtr)CommAPI.INVALID_HANDLE_VALUE;
				
				m_CommAPI.SetEvent(this.mCloseEvent);
			}
		}


		#region Read
		/// <summary>
		/// Reads a number of bytes from the OpenNETCF.IO.Ports.SerialPort input buffer and writes those bytes into a character array at a given offset.
		/// </summary>
		/// <param name="buffer">The byte array to which the input is written.</param>
		/// <param name="offset">The offset in the buffer array where writing should begin.</param>
		/// <param name="count">The number of bytes to be read.</param>
		public int Read(byte[] buffer, int offset, int count) {
			if (!this.IsOpen) {
				throw new InvalidOperationException("Port is not open");
			}
			if (buffer == null) {
				throw new ArgumentNullException("buffer");
			}
			if (offset < 0) {
				throw new ArgumentOutOfRangeException("offset must be > 0");
			}
			if (count < 0) {
				throw new ArgumentOutOfRangeException("count must be > 0");
			}
			if ((buffer.Length - offset) < count) {
				throw new ArgumentException("Failed: ((buffer.Length - offset) < count)");
			}
			int bytesToRead = 0;
			if ((this.mReadLen - this.mReadPos) >= 1) {
				bytesToRead = Math.Min((this.mReadLen - this.mReadPos), count);
				Buffer.BlockCopy(this.mInBuffer, this.mReadPos, buffer, offset, bytesToRead);
				this.mReadPos += bytesToRead;
				if (bytesToRead == count) {
					if (this.mReadPos == this.mReadLen) {
						this.mReadLen = 0;
						this.mReadPos = 0;
					}
					return count;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -