EDN Admin
Well-known member
<p style="border-style:initial; border-color:initial; font-family:Segoe UI,Lucida Grande,Verdana,Arial,Helvetica,sans-serif; outline-style:initial; outline-color:initial; padding-right:0px; border-right-style:none; border-bottom-style:none; border-left-style:none; border-width:initial; border-color:initial; list-style-type:none; color:#333333; font-size:13px; line-height:16px; text-align:left
Hello every1 ! I am working for some days at a Client-Server Chat and i want to be able to send an image,for example, from client to server. I tried to combine to different projects, meaning : one the chat room ,and the other one that is able only for sending
an image from client to server, but now i have 2 connect buttons, of course that cant work because it gives a socket error.
<p style="border-style:initial; border-color:initial; font-family:Segoe UI,Lucida Grande,Verdana,Arial,Helvetica,sans-serif; outline-style:initial; outline-color:initial; padding-right:0px; border-right-style:none; border-bottom-style:none; border-left-style:none; border-width:initial; border-color:initial; list-style-type:none; color:#333333; font-size:13px; line-height:16px; text-align:left
This is the connection class :
<pre class="prettyprint class Connection
{
private TcpClient tcpClient;
private Server mainServer;
private BackgroundWorker communicationWorker;
private String userName;
private Data.Data data;
private Serialize.Serialize ser;
private byte[] readBuffer;
private byte[] writeBuffer;
private int bufferSize = 2048;
private IPEndPoint ipep;
private string ipaddress;
public Connection(TcpClient client, Server server)
{
this.readBuffer = new byte[this.bufferSize];
this.writeBuffer = new byte[this.bufferSize];
this.ser = new Serialize.Serialize();
this.tcpClient = client;
this.tcpClient.NoDelay = true;
this.mainServer = server;
this.ipep = (IPEndPoint) this.tcpClient.Client.RemoteEndPoint;
this.ipaddress = this.ipep.Address.ToString();
this.communicationWorker = new BackgroundWorker();
this.communicationWorker.DoWork += new DoWorkEventHandler(this.communicationWorker_DoWork);
// Run backgroundworker for communication
this.communicationWorker.RunWorkerAsync();
}
public string getClientIp()
{
return this.ipaddress;
}
public string getUserName()
{
return this.userName;
}
private void communicationWorker_DoWork(object sender, DoWorkEventArgs e)
{
this.tcpClient.Client.BeginReceive(this.readBuffer, 0, this.readBuffer.Length, SocketFlags.None, new AsyncCallback(this.OnBeginReceive), this.tcpClient);
}
// This method is executed when something is received
// on the current connection
private void OnBeginReceive(IAsyncResult iar)
{
try
{
int ReceiveMessage = this.tcpClient.Client.EndReceive(iar);
// If the size is zero, it means that the client
// somehow closed the connection. So we close ours.
if (ReceiveMessage <= 0)
{
this.CloseConnection(true);
}
else
{
this.data = null;
try
{
// Get the message object from readBuffer deserialization
this.data = (Data.Data)this.ser.getObjectWithByteArray(readBuffer);
// Check if the message contains a user login
// If not, then just send the message
if (this.data.isLogin())
{
if (this.mainServer.getCurrentSize() >= this.mainServer.getMaxSize() && this.mainServer.getUnlimited().Equals(false))
{
this.Send(this.ser.getByteArrayWithObject(new Data.Data("Administrator: This chat-room is full. Please try again later.", true, false, null)));
this.CloseConnection(false);
}
else if(this.mainServer.CheckBan(this.getClientIp(), this.data.getData()))
{
this.Send(this.ser.getByteArrayWithObject(new Data.Data("Administrator: Client IP address or client username is banned!", true, false, null)));
this.CloseConnection(false);
}
// Check if the username already exists
else if (this.mainServer.CheckUser(this.data.getData()))
{
this.Send(this.ser.getByteArrayWithObject(new Data.Data("Administrator: Username already exists", true, false, null)));
this.CloseConnection(false);
}
else
{
this.userName = this.data.getData();
this.Send(this.ser.getByteArrayWithObject(new Data.Data("OK", true, true, null)));
// Add this user to the connection list
this.mainServer.AddConnection(this, this.userName);
}
}
else
{
this.mainServer.SendToAll(this.data);
}
// Listen for new messages (this is kind of a recursive method)
this.tcpClient.Client.BeginReceive(this.readBuffer, 0, this.readBuffer.Length, SocketFlags.None, new AsyncCallback(this.OnBeginReceive), null);
}[/code]
<span style="color:#333333; font-family:Segoe UI,Lucida Grande,Verdana,Arial,Helvetica,sans-serif; font-size:13px; line-height:16px; text-align:left and this is some of the servers class :
<pre class="prettyprint class Server
{
// Our server will listen on any interface
// on port 50000 (unregistered range)
private IPAddress ipLocal = IPAddress.Any;
private int portLocal = 50000;
// This hashtable will hold all the client connections
// and their usernames
private Hashtable connectionList;
private int currentSize;
private int maxSize;
private bool unlimited = false;
//the list to send to the clients
public ArrayList users = new ArrayList();
private ArrayList banusernames = new ArrayList();
private ArrayList banipaddresses = new ArrayList();
// Message Event
public event DataEventHandler NewData;
// UserList Event
public event UserListChangedEventHandler UserListChanged;
// This will be our client listener thread
private BackgroundWorker listenerWorker;
private TcpListener tcpListener;
private Boolean serverRunning = false;
public Server(int maxSize)
{
this.currentSize = 0;
this.maxSize = maxSize;
if (this.maxSize.Equals(0))
{
this.unlimited = true;
}
this.connectionList = new Hashtable(this.maxSize);
}
public bool getUnlimited()
{
return this.unlimited;
}
public int getCurrentSize()
{
return this.currentSize;
}
public void setCurrentSize(int size)
{
this.currentSize = size;
}
public int getMaxSize()
{
return this.maxSize;
}
public void Start()
{
// Update monitor
Data.Data tempData = new Data.Data("Administrator: Server running"
+ Environment.NewLine
+ "Administrator: Listening for new connections",
true, false, null);
DataEventArgs mea = new DataEventArgs(tempData.getData(), tempData.isAdmin());
this.OnNewData(mea);
// Set the listener backgroundworker thread
this.listenerWorker = new BackgroundWorker();
this.listenerWorker.DoWork += new DoWorkEventHandler(listenerWorker_DoWork);
this.serverRunning = true;
// Run our listening thread
this.listenerWorker.RunWorkerAsync();
}[/code]
<span style="color:#333333; font-family:Segoe UI,Lucida Grande,Verdana,Arial,Helvetica,sans-serif; font-size:13px; line-height:16px; text-align:left Now this is the other project of the server receiving an image:
<pre class="prettyprint namespace ImgServer
{
public delegate void MessageReceivedHandler(string message);
public delegate void ImageReceivedHandler(Image returnImage);
public partial class Form1 : Form
{
Thread t;
Socket server;
int flag = 0;
string receivedPath;
public delegate void UpdateStatusDelegate(string message);
public delegate void ResizeDelegate_FlowLayoutPanel(PictureBox pb);
public delegate void ResizeDelegate_PictureBox(Bitmap bm);
public Form1()
{
InitializeComponent();
panelEx1.Controls.Add(pictureBox1);
t = new Thread(new ThreadStart(StartListening));
t.Start();
}
public class StateObject
{
// Client socket.
public Socket workSocket = null;
public const int BufferSize = 1024;
// Receive buffer.
public byte[] buffer = new byte[BufferSize];
}
public static ManualResetEvent allDone = new ManualResetEvent(false);
public void StartListening()
{
byte[] bytes = new Byte[1024];
IPEndPoint ipEnd = new IPEndPoint(IPAddress.Any, 5000);
server = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
try
{
server.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, true); //reuse the socket
server.Bind(ipEnd);
server.Listen(100);
while (true)
{
allDone.Reset();
server.BeginAccept(new AsyncCallback(AcceptConn), server);
allDone.WaitOne();
}
}
catch (Exception ex)
{
UpdateStatus(ex.Message);
}
}
public void AcceptConn(IAsyncResult iar)
{
allDone.Set();
Socket listener = (Socket)iar.AsyncState;
Socket handler = listener.EndAccept(iar);
StateObject state = new StateObject();
state.workSocket = handler;
handler.BeginReceive(state.buffer, 0, StateObject.BufferSize, 0, new AsyncCallback(Received), state);
flag = 0;
}
private void Received(IAsyncResult iar)
{
int fileNameLen = 1;
String content = String.Empty;
StateObject state = (StateObject)iar.AsyncState;
Socket handler = state.workSocket;
int bytesRead = handler.EndReceive(iar);
if (bytesRead > 0)
{
if (flag == 0)
{
try
{
fileNameLen = BitConverter.ToInt32(state.buffer, 0);
string fileName = Encoding.UTF8.GetString(state.buffer, 4, fileNameLen);
receivedPath = @"c:Temp" + fileName;
UpdateStatus("Receiving an image...");
flag++;
}
catch (Exception)
{
//MessageBox.Show(ex.Message, "Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
if (flag >= 1)
{
try
{
BinaryWriter writer = new BinaryWriter(File.Open(receivedPath, FileMode.Append));
if (flag == 1)
{
writer.Write(state.buffer, 4 + fileNameLen, bytesRead - (4 + fileNameLen));
flag++;
}
else writer.Write(state.buffer, 0, bytesRead);
writer.Close();
}
catch (IOException )
{
//MessageBox.Show(ex.Message, "Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
handler.BeginReceive(state.buffer, 0, StateObject.BufferSize, 0, new AsyncCallback(Received), state);
}
}
else
{
try
{
resize(receivedPath);
UpdateStatus("Received successfully!");
}
catch (Exception )
{
//MessageBox.Show(ex.Message, "Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}
private void resize(string path)
{
Bitmap bm = new Bitmap(path); //Create a bitmap from the original image
Bitmap bm1 = new Bitmap(351, 280);
Graphics g = Graphics.FromImage(bm1);
g.SmoothingMode = SmoothingMode.AntiAlias;
g.DrawImage(bm, 0, 0, 351, 280);
Resize_PictureBox(bm1);
PictureBox pic = new PictureBox();
pic.SizeMode = PictureBoxSizeMode.StretchImage;
pic.Width = 65;
pic.Height = 50;
pic.Image = bm;
pic.Cursor = Cursors.Hand;
Resize_FlowLayoutPanel(pic);
pic.Click += new EventHandler(pic_Click);
g.Dispose();
}
private void pic_Click(object sender, EventArgs e)
{
PictureBox pic = (PictureBox)sender;
pictureBox1.Image = pic.Image;
}
private void Resize_PictureBox(Bitmap bm)
{
if (pictureBox1.InvokeRequired)
{
pictureBox1.Invoke(new ResizeDelegate_PictureBox(Resize_PictureBox), new object[] { bm });
}
else
{
pictureBox1.Image = bm;
}
}
private void Resize_FlowLayoutPanel(PictureBox pb)
{
if (flowLayoutPanel1.InvokeRequired)
{
flowLayoutPanel1.Invoke(new ResizeDelegate_FlowLayoutPanel(Resize_FlowLayoutPanel), new object[] { pb });
}
else
{
flowLayoutPanel1.Controls.Add(pb);
}
}
private void UpdateStatus(string msg)
{
if (lbStatus.InvokeRequired)
{
lbStatus.Invoke(new UpdateStatusDelegate(UpdateStatus), new object[] { msg });
}
else
{
lbStatus.Text = msg;
}
}
}
}[/code]
<span style="color:#333333; font-family:Segoe UI,Lucida Grande,Verdana,Arial,Helvetica,sans-serif; font-size:13px; line-height:16px; text-align:left Sorry for the abundence of code but my questionis, how can i implement the "Sending/receiving image" into
the Chat Room project? Now i can do only one of them , or sending/receiving image, or sending/receiving messages in the chat room. I hope no1 will get upset and i appreciate all the replies ! <br/>
<br/>
<p style="text-align:left <span style="color:#333333; font-family:Segoe UI,Lucida Grande,Verdana,Arial,Helvetica,sans-serif; font-size:13px; line-height:16px; text-align:left
<p style="border-style:initial; border-color:initial; font-family:Segoe UI,Lucida Grande,Verdana,Arial,Helvetica,sans-serif; outline-style:initial; outline-color:initial; padding-right:0px; border-right-style:none; border-bottom-style:none; border-left-style:none; border-width:initial; border-color:initial; list-style-type:none; color:#333333; font-size:13px; line-height:16px; text-align:left
View the full article
Hello every1 ! I am working for some days at a Client-Server Chat and i want to be able to send an image,for example, from client to server. I tried to combine to different projects, meaning : one the chat room ,and the other one that is able only for sending
an image from client to server, but now i have 2 connect buttons, of course that cant work because it gives a socket error.
<p style="border-style:initial; border-color:initial; font-family:Segoe UI,Lucida Grande,Verdana,Arial,Helvetica,sans-serif; outline-style:initial; outline-color:initial; padding-right:0px; border-right-style:none; border-bottom-style:none; border-left-style:none; border-width:initial; border-color:initial; list-style-type:none; color:#333333; font-size:13px; line-height:16px; text-align:left
This is the connection class :
<pre class="prettyprint class Connection
{
private TcpClient tcpClient;
private Server mainServer;
private BackgroundWorker communicationWorker;
private String userName;
private Data.Data data;
private Serialize.Serialize ser;
private byte[] readBuffer;
private byte[] writeBuffer;
private int bufferSize = 2048;
private IPEndPoint ipep;
private string ipaddress;
public Connection(TcpClient client, Server server)
{
this.readBuffer = new byte[this.bufferSize];
this.writeBuffer = new byte[this.bufferSize];
this.ser = new Serialize.Serialize();
this.tcpClient = client;
this.tcpClient.NoDelay = true;
this.mainServer = server;
this.ipep = (IPEndPoint) this.tcpClient.Client.RemoteEndPoint;
this.ipaddress = this.ipep.Address.ToString();
this.communicationWorker = new BackgroundWorker();
this.communicationWorker.DoWork += new DoWorkEventHandler(this.communicationWorker_DoWork);
// Run backgroundworker for communication
this.communicationWorker.RunWorkerAsync();
}
public string getClientIp()
{
return this.ipaddress;
}
public string getUserName()
{
return this.userName;
}
private void communicationWorker_DoWork(object sender, DoWorkEventArgs e)
{
this.tcpClient.Client.BeginReceive(this.readBuffer, 0, this.readBuffer.Length, SocketFlags.None, new AsyncCallback(this.OnBeginReceive), this.tcpClient);
}
// This method is executed when something is received
// on the current connection
private void OnBeginReceive(IAsyncResult iar)
{
try
{
int ReceiveMessage = this.tcpClient.Client.EndReceive(iar);
// If the size is zero, it means that the client
// somehow closed the connection. So we close ours.
if (ReceiveMessage <= 0)
{
this.CloseConnection(true);
}
else
{
this.data = null;
try
{
// Get the message object from readBuffer deserialization
this.data = (Data.Data)this.ser.getObjectWithByteArray(readBuffer);
// Check if the message contains a user login
// If not, then just send the message
if (this.data.isLogin())
{
if (this.mainServer.getCurrentSize() >= this.mainServer.getMaxSize() && this.mainServer.getUnlimited().Equals(false))
{
this.Send(this.ser.getByteArrayWithObject(new Data.Data("Administrator: This chat-room is full. Please try again later.", true, false, null)));
this.CloseConnection(false);
}
else if(this.mainServer.CheckBan(this.getClientIp(), this.data.getData()))
{
this.Send(this.ser.getByteArrayWithObject(new Data.Data("Administrator: Client IP address or client username is banned!", true, false, null)));
this.CloseConnection(false);
}
// Check if the username already exists
else if (this.mainServer.CheckUser(this.data.getData()))
{
this.Send(this.ser.getByteArrayWithObject(new Data.Data("Administrator: Username already exists", true, false, null)));
this.CloseConnection(false);
}
else
{
this.userName = this.data.getData();
this.Send(this.ser.getByteArrayWithObject(new Data.Data("OK", true, true, null)));
// Add this user to the connection list
this.mainServer.AddConnection(this, this.userName);
}
}
else
{
this.mainServer.SendToAll(this.data);
}
// Listen for new messages (this is kind of a recursive method)
this.tcpClient.Client.BeginReceive(this.readBuffer, 0, this.readBuffer.Length, SocketFlags.None, new AsyncCallback(this.OnBeginReceive), null);
}[/code]
<span style="color:#333333; font-family:Segoe UI,Lucida Grande,Verdana,Arial,Helvetica,sans-serif; font-size:13px; line-height:16px; text-align:left and this is some of the servers class :
<pre class="prettyprint class Server
{
// Our server will listen on any interface
// on port 50000 (unregistered range)
private IPAddress ipLocal = IPAddress.Any;
private int portLocal = 50000;
// This hashtable will hold all the client connections
// and their usernames
private Hashtable connectionList;
private int currentSize;
private int maxSize;
private bool unlimited = false;
//the list to send to the clients
public ArrayList users = new ArrayList();
private ArrayList banusernames = new ArrayList();
private ArrayList banipaddresses = new ArrayList();
// Message Event
public event DataEventHandler NewData;
// UserList Event
public event UserListChangedEventHandler UserListChanged;
// This will be our client listener thread
private BackgroundWorker listenerWorker;
private TcpListener tcpListener;
private Boolean serverRunning = false;
public Server(int maxSize)
{
this.currentSize = 0;
this.maxSize = maxSize;
if (this.maxSize.Equals(0))
{
this.unlimited = true;
}
this.connectionList = new Hashtable(this.maxSize);
}
public bool getUnlimited()
{
return this.unlimited;
}
public int getCurrentSize()
{
return this.currentSize;
}
public void setCurrentSize(int size)
{
this.currentSize = size;
}
public int getMaxSize()
{
return this.maxSize;
}
public void Start()
{
// Update monitor
Data.Data tempData = new Data.Data("Administrator: Server running"
+ Environment.NewLine
+ "Administrator: Listening for new connections",
true, false, null);
DataEventArgs mea = new DataEventArgs(tempData.getData(), tempData.isAdmin());
this.OnNewData(mea);
// Set the listener backgroundworker thread
this.listenerWorker = new BackgroundWorker();
this.listenerWorker.DoWork += new DoWorkEventHandler(listenerWorker_DoWork);
this.serverRunning = true;
// Run our listening thread
this.listenerWorker.RunWorkerAsync();
}[/code]
<span style="color:#333333; font-family:Segoe UI,Lucida Grande,Verdana,Arial,Helvetica,sans-serif; font-size:13px; line-height:16px; text-align:left Now this is the other project of the server receiving an image:
<pre class="prettyprint namespace ImgServer
{
public delegate void MessageReceivedHandler(string message);
public delegate void ImageReceivedHandler(Image returnImage);
public partial class Form1 : Form
{
Thread t;
Socket server;
int flag = 0;
string receivedPath;
public delegate void UpdateStatusDelegate(string message);
public delegate void ResizeDelegate_FlowLayoutPanel(PictureBox pb);
public delegate void ResizeDelegate_PictureBox(Bitmap bm);
public Form1()
{
InitializeComponent();
panelEx1.Controls.Add(pictureBox1);
t = new Thread(new ThreadStart(StartListening));
t.Start();
}
public class StateObject
{
// Client socket.
public Socket workSocket = null;
public const int BufferSize = 1024;
// Receive buffer.
public byte[] buffer = new byte[BufferSize];
}
public static ManualResetEvent allDone = new ManualResetEvent(false);
public void StartListening()
{
byte[] bytes = new Byte[1024];
IPEndPoint ipEnd = new IPEndPoint(IPAddress.Any, 5000);
server = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
try
{
server.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, true); //reuse the socket
server.Bind(ipEnd);
server.Listen(100);
while (true)
{
allDone.Reset();
server.BeginAccept(new AsyncCallback(AcceptConn), server);
allDone.WaitOne();
}
}
catch (Exception ex)
{
UpdateStatus(ex.Message);
}
}
public void AcceptConn(IAsyncResult iar)
{
allDone.Set();
Socket listener = (Socket)iar.AsyncState;
Socket handler = listener.EndAccept(iar);
StateObject state = new StateObject();
state.workSocket = handler;
handler.BeginReceive(state.buffer, 0, StateObject.BufferSize, 0, new AsyncCallback(Received), state);
flag = 0;
}
private void Received(IAsyncResult iar)
{
int fileNameLen = 1;
String content = String.Empty;
StateObject state = (StateObject)iar.AsyncState;
Socket handler = state.workSocket;
int bytesRead = handler.EndReceive(iar);
if (bytesRead > 0)
{
if (flag == 0)
{
try
{
fileNameLen = BitConverter.ToInt32(state.buffer, 0);
string fileName = Encoding.UTF8.GetString(state.buffer, 4, fileNameLen);
receivedPath = @"c:Temp" + fileName;
UpdateStatus("Receiving an image...");
flag++;
}
catch (Exception)
{
//MessageBox.Show(ex.Message, "Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
if (flag >= 1)
{
try
{
BinaryWriter writer = new BinaryWriter(File.Open(receivedPath, FileMode.Append));
if (flag == 1)
{
writer.Write(state.buffer, 4 + fileNameLen, bytesRead - (4 + fileNameLen));
flag++;
}
else writer.Write(state.buffer, 0, bytesRead);
writer.Close();
}
catch (IOException )
{
//MessageBox.Show(ex.Message, "Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
handler.BeginReceive(state.buffer, 0, StateObject.BufferSize, 0, new AsyncCallback(Received), state);
}
}
else
{
try
{
resize(receivedPath);
UpdateStatus("Received successfully!");
}
catch (Exception )
{
//MessageBox.Show(ex.Message, "Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}
private void resize(string path)
{
Bitmap bm = new Bitmap(path); //Create a bitmap from the original image
Bitmap bm1 = new Bitmap(351, 280);
Graphics g = Graphics.FromImage(bm1);
g.SmoothingMode = SmoothingMode.AntiAlias;
g.DrawImage(bm, 0, 0, 351, 280);
Resize_PictureBox(bm1);
PictureBox pic = new PictureBox();
pic.SizeMode = PictureBoxSizeMode.StretchImage;
pic.Width = 65;
pic.Height = 50;
pic.Image = bm;
pic.Cursor = Cursors.Hand;
Resize_FlowLayoutPanel(pic);
pic.Click += new EventHandler(pic_Click);
g.Dispose();
}
private void pic_Click(object sender, EventArgs e)
{
PictureBox pic = (PictureBox)sender;
pictureBox1.Image = pic.Image;
}
private void Resize_PictureBox(Bitmap bm)
{
if (pictureBox1.InvokeRequired)
{
pictureBox1.Invoke(new ResizeDelegate_PictureBox(Resize_PictureBox), new object[] { bm });
}
else
{
pictureBox1.Image = bm;
}
}
private void Resize_FlowLayoutPanel(PictureBox pb)
{
if (flowLayoutPanel1.InvokeRequired)
{
flowLayoutPanel1.Invoke(new ResizeDelegate_FlowLayoutPanel(Resize_FlowLayoutPanel), new object[] { pb });
}
else
{
flowLayoutPanel1.Controls.Add(pb);
}
}
private void UpdateStatus(string msg)
{
if (lbStatus.InvokeRequired)
{
lbStatus.Invoke(new UpdateStatusDelegate(UpdateStatus), new object[] { msg });
}
else
{
lbStatus.Text = msg;
}
}
}
}[/code]
<span style="color:#333333; font-family:Segoe UI,Lucida Grande,Verdana,Arial,Helvetica,sans-serif; font-size:13px; line-height:16px; text-align:left Sorry for the abundence of code but my questionis, how can i implement the "Sending/receiving image" into
the Chat Room project? Now i can do only one of them , or sending/receiving image, or sending/receiving messages in the chat room. I hope no1 will get upset and i appreciate all the replies ! <br/>
<br/>
<p style="text-align:left <span style="color:#333333; font-family:Segoe UI,Lucida Grande,Verdana,Arial,Helvetica,sans-serif; font-size:13px; line-height:16px; text-align:left
<p style="border-style:initial; border-color:initial; font-family:Segoe UI,Lucida Grande,Verdana,Arial,Helvetica,sans-serif; outline-style:initial; outline-color:initial; padding-right:0px; border-right-style:none; border-bottom-style:none; border-left-style:none; border-width:initial; border-color:initial; list-style-type:none; color:#333333; font-size:13px; line-height:16px; text-align:left
View the full article