In my program I have 2 classes at this moment it will grow eventually with more classes, the first class is the main class of my windows form where I have all my buttons and text etc. now in my main form I have a button called close connection where when this is click the a loop will end from the second class. the problem I am having is how to accomplished that be able to close that loop from the button of my main class.
Here is the main class code
using System;
using System.Windows.Forms;
namespace BarcodeReceivingApp
{
//TelnetConnection stopConnection = new TelnetConnection();
public partial class BarcodeReceivingForm : Form
{
//GLOBAL VARIABLES
private const string Hostname = "myip";
private const int Port = 23;
public BarcodeReceivingForm()
{
InitializeComponent();
//FormBorderStyle = System.Windows.Forms.FormBorderStyle.None;
WindowState = FormWindowState.Maximized;
}
private void btn_ConnectT_Click(object sender, EventArgs e)
{
var readData = new TelnetConnection(Hostname, Port);
readData.ServerSocket(Hostname, Port, this);
}
private void btn_StopConnection_Click(object sender, EventArgs e)
{
var connection = new TelnetConnection(Hostname, Port);
connection.CloseConnection();
}
private void btn_RemoveItemFromListAt_Click(object sender, EventArgs e)
{
for (var i = lst_BarcodeScan.SelectedIndices.Count - 1; i >= 0; i--)
{
lst_BarcodeScan.Items.RemoveAt(lst_BarcodeScan.SelectedIndices[i]);
}
}
private void BarcodeReceivingForm_Load(object sender, EventArgs e)
{
lst_BarcodeScan.SelectionMode = SelectionMode.MultiSimple;
}
private void btn_ApplicationSettings_Click(object sender, EventArgs e)
{
var bcSettingsForm = new BarcodeReceivingSettingsForm();
bcSettingsForm.Show();
}
}
}
Second class code where most of the logic is In the ReadWrite() method there is where I need to put for example if button.click from the stopconnection then break the loop and close the port 23 connection that part I have it done in my close connection method I am calling after the while loop. write now I have is command variable = exit then break the loop but I don't want to be that why I want the button to do that
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net.Sockets;
using System.Runtime.Remoting.Messaging;
using System.Security.Authentication.ExtendedProtection;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Windows.Forms;
namespace BarcodeReceivingApp
{
public class TelnetConnection
{
private Thread _readWriteThread;
private TcpClient _client;
private NetworkStream _networkStream;
private string _hostname;
private int _port;
private BarcodeReceivingForm _form;
public TelnetConnection(string hostname, int port)
{
this._hostname = hostname;
this._port = port;
}
public TelnetConnection()
{
}
public void ServerSocket(string ip, int port, BarcodeReceivingForm f)
{
this._form = f;
try
{
_client = new TcpClient(ip, port);
}
catch (SocketException)
{
MessageBox.Show(@"Failed to connect to server");
return;
}
_networkStream = _client.GetStream();
_readWriteThread = new Thread(ReadWrite);
//_readWriteThread = new Thread(() => ReadWrite(f));
_readWriteThread.Start();
}
public void ReadWrite()
{
while (true)
{
var command = "";
if (command == "Exit")
break;
var received = Read();
if (_form.lst_BarcodeScan.InvokeRequired)
{
_form.lst_BarcodeScan.Invoke(new MethodInvoker(delegate { _form.lst_BarcodeScan.Items.Add(received + Environment.NewLine); }));
}
}
CloseConnection();
}
public string BarcodeRead()
{
var reading = Read();
return reading;
}
public string Read()
{
var data = new byte[1024];
var received = "";
var size = _networkStream.Read(data, 0, data.Length);
received = Encoding.ASCII.GetString(data, 0, size);
return received;
}
public void CloseConnection()
{
Console.WriteLine(@"Closed Connection");
_networkStream.Close();
_client.Close();
}
}
}
Also, I have been searching on google and also on stack overflow something similar to question and I could not find anything that will help my issue.
You should change your loop to stop automatically when the boolean condition changes. Here a small change you can do. You will need to create a new method to call the closing plus changing a bit the ReadWrite
method
private bool isExiting = false;
public void Exit()
{
isExiting = true;
}
public void ReadWrite()
{
do
{
var received = Read();
if (_form.lst_BarcodeScan.InvokeRequired)
{
_form.lst_BarcodeScan.Invoke(new MethodInvoker(delegate { _form.lst_BarcodeScan.Items.Add(received + Environment.NewLine); }));
}
} while (!isExiting)
CloseConnection();
}
Now calling connection.Exit();
will close everything But you still have an issue. You did not keep the instance of the class in the form for the connection. In the form you need to change the connect and close to use the same object. here are the small changes to both method
private TelnetConnection connection;
private void btn_ConnectT_Click(object sender, EventArgs e)
{
connection = new TelnetConnection(Hostname, Port);
connection.ServerSocket(Hostname, Port, this);
}
private void btn_StopConnection_Click(object sender, EventArgs e)
{
connection.Exit();
}
Now they both use the same object so it should work properly.