This app uses wireless network to connect your PC and then sends commands to control your player software. Now, it only supports UPMOST net-TV3 (network TV-BOX).
Development tool:
- Server: Embarcadero C++ Builder XE3
- Client: Eclipse with Android SDK
- Testing Platform: HTC Desire HD (Android 2.3.4)
Scenario:
Server side:
Client side partial source code:
package com.dhd.remotecontrol; import java.io.BufferedReader; import java.io.BufferedWriter; import java.io.IOException; import java.io.OutputStreamWriter; import java.io.PrintWriter; import java.net.InetAddress; import java.net.NetworkInterface; import java.net.Socket; import java.net.SocketException; import java.net.UnknownHostException; import java.util.Enumeration; import java.util.Vector; import android.os.Bundle; import android.app.Activity; import android.util.Log; import android.view.Menu; import android.view.View; import android.widget.AdapterView; import android.widget.AdapterView.OnItemSelectedListener; import android.widget.ArrayAdapter; import android.widget.Button; import android.widget.EditText; import android.widget.ImageButton; import android.widget.ImageView; import android.widget.Spinner; import android.widget.TabHost; import android.widget.TabHost.TabSpec; import android.widget.TextView; import android.widget.Toast; public class MainActivity extends Activity { private Button Btn_Connection; private Spinner Spinner_ProcessList; private String[] lists= {"net-TV 2012", "AVerTV 3D"}; public EditText textView_IP; public EditText textView_Port; public Socket socket; public InetAddress serverAddr; public static String hostip; public String selectProcess; private Button Btn_1, Btn_2, Btn_3, Btn_4, Btn_5, Btn_6, Btn_7, Btn_8, Btn_9, Btn_0, Btn_100, Btn_last; private ImageButton Btn_vol_up, Btn_vol_down, Btn_ch_up, Btn_ch_down, Btn_power, Btn_mute; private TextView textView_Channel; private TabHost tabHost; private TabSpec tabSpec; int currentChannel; int prevChannel; private String sendMessage; //private String connectInfo; private String info[]; private boolean connected; private boolean hundredClicked; private boolean muteClicked; private PrintWriter out; BufferedReader in; Vector<String> channelVector = new Vector<String>(); @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); setViewComponent(); } @Override public boolean onCreateOptionsMenu(Menu menu) { // Inflate the menu; this adds items to the action bar if it is present. getMenuInflater().inflate(R.menu.main, menu); return true; } private void setViewComponent() { // TabHost Initializer tabHost = (TabHost)findViewById(R.id.tabHost); tabHost.setup(); tabSpec = tabHost.newTabSpec("tag1"); tabSpec.setContent(R.id.tab_connection); tabSpec.setIndicator("Connection", getResources().getDrawable(R.drawable.ic_launcher_wireless2)); tabHost.addTab(tabSpec); tabSpec = tabHost.newTabSpec("tag2"); tabSpec.setContent(R.id.tab_pad); tabSpec.setIndicator("Pad"); tabHost.addTab(tabSpec); tabSpec = tabHost.newTabSpec("tag3"); tabSpec.setContent(R.id.tab_vol_ch); tabSpec.setIndicator("Remote"); tabHost.addTab(tabSpec); // Button and ImageButton Btn_Connection = (Button) this.findViewById(R.id.Btn_connect); Btn_1 = (Button)findViewById(R.id.Btn_1); Btn_2 = (Button)findViewById(R.id.Btn_2); Btn_3 = (Button)findViewById(R.id.Btn_3); Btn_4 = (Button)findViewById(R.id.Btn_4); Btn_5 = (Button)findViewById(R.id.Btn_5); Btn_6 = (Button)findViewById(R.id.Btn_6); Btn_7 = (Button)findViewById(R.id.Btn_7); Btn_8 = (Button)findViewById(R.id.Btn_8); Btn_9 = (Button)findViewById(R.id.Btn_9); Btn_0 = (Button)findViewById(R.id.Btn_0); Btn_100 = (Button)findViewById(R.id.Btn_100); Btn_last = (Button)findViewById(R.id.Btn_Last); Btn_power = (ImageButton)findViewById(R.id.imageBtn_Power); Btn_mute = (ImageButton)findViewById(R.id.imageBtn_Mute); Btn_vol_up = (ImageButton)findViewById(R.id.imageBtn_Vol_Up); Btn_vol_down = (ImageButton)findViewById(R.id.imageBtn_Vol_Down); Btn_ch_up = (ImageButton)findViewById(R.id.imageBtn_Ch_Up); Btn_ch_down = (ImageButton)findViewById(R.id.imageBtn_Ch_Down); //TextView textView_IP = (EditText)findViewById(R.id.editText_IP); textView_Port = (EditText)findViewById(R.id.editText_Port); textView_Channel = (TextView)findViewById(R.id.textView_CurrentChannel); // Initialize Spinner Context Spinner_ProcessList = (Spinner) this.findViewById(R.id.spinner_ProcessList); ArrayAdapter<String> item = new ArrayAdapter<String>(this,android.R.layout.simple_spinner_dropdown_item,lists); Spinner_ProcessList.setAdapter(item); Spinner_ProcessList.setOnItemSelectedListener(new SpinnerSelectedListener()); selectProcess = lists[0]; //Default try { hostip = getLocalIpAddress(); textView_IP.setText(hostip.subSequence(0, hostip.lastIndexOf(".")+1)); textView_Port.setText("7788"); } catch(Exception e1) { String connectInfo = "Connection Fails. Please set your remote ip/port again."; Toast.makeText(this, connectInfo, Toast.LENGTH_LONG).show(); } //Variable Initialization sendMessage = ""; currentChannel = -1; prevChannel = -1; connected = false; hundredClicked = false; muteClicked = false; info = new String[3]; info[2] = selectProcess; // Button Listener Btn_Connection.setOnClickListener(Btn_ConnectionOnClick); Btn_1.setOnClickListener(Btn_1OnClick); Btn_2.setOnClickListener(Btn_2OnClick); Btn_3.setOnClickListener(Btn_3OnClick); Btn_4.setOnClickListener(Btn_4OnClick); Btn_5.setOnClickListener(Btn_5OnClick); Btn_6.setOnClickListener(Btn_6OnClick); Btn_7.setOnClickListener(Btn_7OnClick); Btn_8.setOnClickListener(Btn_8OnClick); Btn_9.setOnClickListener(Btn_9OnClick); Btn_0.setOnClickListener(Btn_0OnClick); Btn_100.setOnClickListener(Btn_100OnClick); Btn_last.setOnClickListener(Btn_lastOnClick); Btn_power.setOnClickListener(Btn_powerOnClick); Btn_mute.setOnClickListener(Btn_muteOnClick); Btn_vol_up.setOnClickListener(Btn_vol_upOnClick); Btn_vol_down.setOnClickListener(Btn_vol_downOnClick); Btn_ch_up.setOnClickListener(Btn_ch_upOnClick); Btn_ch_down.setOnClickListener(Btn_ch_downOnClick); } private void setChannel(String channel) { sendMessage += channel; textView_Channel.setText("Channel:" + sendMessage); try { if(sendMessage.length() == 2 && !sendMessage.substring(0, 1).equals("+")) { channelVector.add(sendMessage); currentChannel = Integer.parseInt(sendMessage); out = new PrintWriter( new BufferedWriter( new OutputStreamWriter(socket.getOutputStream())),true); out.println(info[2]+","+sendMessage); out.flush(); sendMessage = ""; } else if(sendMessage.length() == 3 && sendMessage.substring(0, 1).equals("+")) { String hundChannel = ""; hundChannel = "1" + sendMessage.substring(1,3); channelVector.add(sendMessage); currentChannel = Integer.parseInt(hundChannel); out = new PrintWriter( new BufferedWriter( new OutputStreamWriter(socket.getOutputStream())),true); out.println(info[2]+","+sendMessage); out.flush(); sendMessage = ""; hundredClicked = false; } } catch (IOException e) { e.printStackTrace(); } } private Button.OnClickListener Btn_1OnClick = new Button.OnClickListener() { public void onClick(View v) { if(connected) { setChannel("1"); } } }; private Button.OnClickListener Btn_2OnClick = new Button.OnClickListener() { public void onClick(View v) { if(connected) { setChannel("2"); } } }; private Button.OnClickListener Btn_3OnClick = new Button.OnClickListener() { public void onClick(View v) { if(connected) { setChannel("3"); } } }; private Button.OnClickListener Btn_4OnClick = new Button.OnClickListener() { public void onClick(View v) { if(connected) { setChannel("4"); } } }; private Button.OnClickListener Btn_5OnClick = new Button.OnClickListener() { public void onClick(View v) { if(connected) { setChannel("5"); } } }; private Button.OnClickListener Btn_6OnClick = new Button.OnClickListener() { public void onClick(View v) { if(connected) { setChannel("6"); } } }; private Button.OnClickListener Btn_7OnClick = new Button.OnClickListener() { public void onClick(View v) { if(connected) { setChannel("7"); } } }; private Button.OnClickListener Btn_8OnClick = new Button.OnClickListener() { public void onClick(View v) { if(connected) { setChannel("8"); } } }; private Button.OnClickListener Btn_9OnClick = new Button.OnClickListener() { public void onClick(View v) { if(connected) { setChannel("9"); } } }; private Button.OnClickListener Btn_0OnClick = new Button.OnClickListener() { public void onClick(View v) { if(connected) { setChannel("0"); } } }; private Button.OnClickListener Btn_100OnClick = new Button.OnClickListener() { public void onClick(View v) { if(connected) { if(!hundredClicked && sendMessage.length() == 0) { sendMessage += "+"; textView_Channel.setText("Channel:" + sendMessage); hundredClicked = true; } } } }; private Button.OnClickListener Btn_lastOnClick = new Button.OnClickListener() { public void onClick(View v) { try { if(connected) { if(channelVector.size() >= 2) { sendMessage = channelVector.get(channelVector.size()-2).toString(); textView_Channel.setText("Channel:" + sendMessage); if(!sendMessage.substring(0, 1).equals("+")) { channelVector.add(sendMessage); currentChannel = Integer.parseInt(sendMessage); out = new PrintWriter( new BufferedWriter( new OutputStreamWriter(socket.getOutputStream())),true); out.println(info[2]+","+sendMessage); out.flush(); sendMessage = ""; } else if(sendMessage.length() == 3 && sendMessage.substring(0, 1).equals("+")) { String hundChannel = ""; hundChannel = "1" + sendMessage.substring(1,3); channelVector.add(sendMessage); currentChannel = Integer.parseInt(hundChannel); out = new PrintWriter( new BufferedWriter( new OutputStreamWriter(socket.getOutputStream())),true); out.println(info[2]+","+sendMessage); out.flush(); sendMessage = ""; hundredClicked = false; } } else { out = new PrintWriter( new BufferedWriter( new OutputStreamWriter(socket.getOutputStream())),true); out.println(info[2]+",L"); out.flush(); sendMessage = ""; } } } catch (IOException e) { e.printStackTrace(); } } }; private void sendCommand(String cmd) { if(connected) { try { out = new PrintWriter( new BufferedWriter( new OutputStreamWriter(socket.getOutputStream())),true); out.println(info[2] + "," + cmd); out.flush(); } catch (IOException e) { e.printStackTrace(); } } } private Button.OnClickListener Btn_powerOnClick = new Button.OnClickListener() { public void onClick(View v) { sendCommand("CMD.POWERONOFF"); } }; private Button.OnClickListener Btn_muteOnClick = new Button.OnClickListener() { public void onClick(View v) { if(connected) { if(muteClicked) { Btn_mute.setImageResource(R.drawable.ic_launcher_mute); //un-mute muteClicked = !muteClicked; } else { Btn_mute.setImageResource(R.drawable.ic_launcher_mute2); muteClicked = !muteClicked; } sendCommand("CMD.MUTE"); } } }; private Button.OnClickListener Btn_vol_upOnClick = new Button.OnClickListener() { public void onClick(View v) { sendCommand("CMD.VOLUP"); } }; private Button.OnClickListener Btn_vol_downOnClick = new Button.OnClickListener() { public void onClick(View v) { sendCommand("CMD.VOLDOWN"); } }; private Button.OnClickListener Btn_ch_upOnClick = new Button.OnClickListener() { public void onClick(View v) { sendCommand("CMD.CHNEXT"); } }; private Button.OnClickListener Btn_ch_downOnClick = new Button.OnClickListener() { public void onClick(View v) { sendCommand("CMD.CHBACK"); } }; private Button.OnClickListener Btn_ConnectionOnClick = new Button.OnClickListener() { public void onClick(View v) { if(Btn_Connection.getText().toString().equals("Connect")) { try { serverAddr = InetAddress.getByName(textView_IP.getText().toString()); try { socket = new Socket(serverAddr, Integer.parseInt(textView_Port.getText().toString())); connected = true; Btn_Connection.setText("Disconnect"); info[0] = textView_IP.getText().toString(); info[1] = textView_Port.getText().toString(); View mView = tabHost.getTabWidget().getChildAt(0); ImageView imageView = (ImageView)mView.findViewById(android.R.id.icon); imageView.setImageDrawable(getResources().getDrawable(R.drawable.ic_launcher_connected)); tabHost.setCurrentTab(1); } catch (NumberFormatException e) { e.printStackTrace(); Toast.makeText(MainActivity.this, "Connection Failed!", Toast.LENGTH_LONG).show(); Disconnection(); } catch (IOException e) { e.printStackTrace(); Toast.makeText(MainActivity.this, "Connection Failed!", Toast.LENGTH_LONG).show(); Disconnection(); } } catch (UnknownHostException e) { e.printStackTrace(); Toast.makeText(MainActivity.this, "Connection Failed!", Toast.LENGTH_LONG).show(); Disconnection(); } } else if(Btn_Connection.getText().toString().equals("Disconnect")) { Btn_Connection.setText("Connect"); try { socket.close(); Disconnection(); } catch (IOException e) { e.printStackTrace(); connected = false; } } } }; private void Disconnection() { connected = false; View mView = tabHost.getTabWidget().getChildAt(0); ImageView imageView = (ImageView)mView.findViewById(android.R.id.icon); imageView.setImageDrawable(getResources().getDrawable(R.drawable.ic_launcher_wireless2)); } class SpinnerSelectedListener implements OnItemSelectedListener { public void onItemSelected(AdapterView<?> arg0, View arg1, int arg2, long arg3) { selectProcess = lists[arg2]; info[2] = selectProcess; } public void onNothingSelected(AdapterView<?> arg0) { selectProcess = lists[0]; info[2] = selectProcess; } } public String getLocalIpAddress() { try { for (Enumeration<NetworkInterface> en = NetworkInterface.getNetworkInterfaces(); en.hasMoreElements();) { NetworkInterface intf = en.nextElement(); for (Enumeration<InetAddress> enumIpAddr = intf .getInetAddresses(); enumIpAddr.hasMoreElements();) { InetAddress inetAddress = enumIpAddr.nextElement(); if (!inetAddress.isLoopbackAddress()) { return inetAddress.getHostAddress().toString(); } } } } catch (SocketException ex) { Log.e("WifiPreference IpAddress", ex.toString()); } return null; } }
Server side source code:
//--------------------------------------------------------------------------- #include <vcl.h> #include <stdio.h> #include <winsock2.h> #include <vector> #include <algorithm> #pragma hdrstop #include "main.h" //--------------------------------------------------------------------------- #pragma package(smart_init) #pragma resource "*.dfm" TForm_RemoteControl *Form_RemoteControl; using namespace std; TInitCommonControlsEx ICC; HWND hIpEdit_ServerIP; int iServerIP, iServerPort; AnsiString strServerIP; TListItem *LogItem; vector <AnsiString> clientList; int iMuteCount = 0; AnsiString receiveMessage; //[ProcessName], [Command] //--------------------------------------------------------------------------- __fastcall TForm_RemoteControl::TForm_RemoteControl(TComponent* Owner) : TForm(Owner) { } //--------------------------------------------------------------------------- void __fastcall TForm_RemoteControl::FormCreate(TObject *Sender) { ICC.dwSize = sizeof(TInitCommonControlsEx); ICC.dwICC = ICC_INTERNET_CLASSES; if(!InitCommonControlsEx(&ICC)) return; strServerIP = IdIPWatch_Server->LocalIP(); hIpEdit_ServerIP =CreateWindow(WC_IPADDRESS,NULL,WS_CHILD|WS_VISIBLE,95,13,140,20,Panel_Network->Handle,0,HInstance,NULL); iServerIP=ntohl(inet_addr(strServerIP.c_str())); SendMessage(hIpEdit_ServerIP,IPM_SETADDRESS,0,iServerIP); iServerPort = Edit_LocalPort->Text.ToInt(); } //--------------------------------------------------------------------------- void __fastcall TForm_RemoteControl::ToolButton_ConnectionClick(TObject *Sender) { if(ToolButton_Connection->ImageIndex == 0) //connection { ToolButton_Connection->ImageIndex = 1; ToolButton_Connection->Caption = " Disconnect "; LogItem=ListView_Log->Items->Insert(0); LogItem->Caption=Now().CurrentTime().FormatString("hh:nn:ss"); LogItem->SubItems->Add("Server Online"); IdTCPServer_Remote->DefaultPort = iServerPort; IdTCPServer_Remote->Active = true; } else if(ToolButton_Connection->ImageIndex == 1) { ToolButton_Connection->ImageIndex = 0; ToolButton_Connection->Caption = " Connect "; LogItem=ListView_Log->Items->Insert(0); LogItem->Caption=Now().CurrentTime().FormatString("hh:nn:ss"); LogItem->SubItems->Add("Server Offline"); IdTCPServer_Remote->Active = false; } } //--------------------------------------------------------------------------- void __fastcall TForm_RemoteControl::ChangeChannel(AnsiString strProcess, char *key) { //http://msdn.microsoft.com/en-us/library/windows/desktop/dd375731(v=vs.85).aspx Application->ProcessMessages(); HWND netTV = FindWindow(NULL,strProcess.c_str()); if (ShowWindow(netTV,SW_SHOWNORMAL)) { Application->ProcessMessages(); HWND hFrgWnd = ::GetForegroundWindow(); AttachThreadInput( GetWindowThreadProcessId(hFrgWnd, NULL), GetCurrentThreadId(), TRUE ); ::SetForegroundWindow(netTV); ::BringWindowToTop(netTV); for(int i=0;i<strlen(key);i++) { keybd_event(key[i], 0, 0, 0); int iStart = GetTickCount(); while (GetTickCount() - iStart <= 200) Application->ProcessMessages(); } } else { if(key[0] == 0x58) { WinExec("C:\\Program Files (x86)\\net-TV\\net-TV 2012\\net-TV 2012.exe",SW_SHOW); } else ShowMessage("Open " + strProcess + " first!"); } } //--------------------------------------------------------------------------- void __fastcall TForm_RemoteControl::IdTCPServer_RemoteExecute(TIdContext *AContext) { AnsiString cmd = AContext->Connection->IOHandler->ReadLn().Trim(); TStringList *msgList = new TStringList(); TSysCharSet sepChars; sepChars = TSysCharSet() << ','; ExtractStrings(sepChars, sepChars, WideString(cmd).c_bstr(), msgList); char *keyValue = new char[msgList->Strings[1].Length()]; if(msgList->Strings[1].Pos("CMD") == 0) { if(msgList->Strings[1].SubString(1,1) != "+" && msgList->Strings[1].Length() >0) { for(int i=0;i<msgList->Strings[1].Length();i++) if(msgList->Strings[1].SubString(i+1,1).ToInt() >= 0 && msgList->Strings[1].SubString(i+1,1).ToInt() <=9) keyValue[i] = msgList->Strings[1].SubString(i+1,1).ToInt()+0x30; } if(msgList->Strings[1].SubString(1,1) == "+" && msgList->Strings[1].Length() >0) { keyValue[0] = VK_ADD; for(int i=1;i<msgList->Strings[1].Length();i++) keyValue[i] = msgList->Strings[1].SubString(i+1,1).ToInt()+0x30; } if(keyValue[0] != VK_ADD) { if(keyValue[0] >= '0' && keyValue[0]<='9' && keyValue[1]>='0' && keyValue[1]<='9') ChangeChannel(msgList->Strings[0], keyValue); } else if(keyValue[0] == VK_ADD) { if(keyValue[1] >= '0' && keyValue[1]<='9' && keyValue[2]>='0' && keyValue[2]<='9') ChangeChannel(msgList->Strings[0], keyValue); } LogItem=ListView_Log->Items->Insert(0); LogItem->Caption=Now().CurrentTime().FormatString("hh:nn:ss"); LogItem->SubItems->Add("Channel: " + msgList->Strings[1]); LogItem->SubItems->Add(AContext->Connection->Socket->Binding->PeerIP); LogItem->SubItems->Add(msgList->Strings[0]); } else { AnsiString sysCMD = msgList->Strings[1].SubString(5,msgList->Strings[1].Length()-4); if(sysCMD == "POWERONOFF") { keyValue[0] = 0x58; // X ChangeChannel(msgList->Strings[0], keyValue); Application->ProcessMessages(); AnsiString strProcessName = msgList->Strings[0]; HWND netTV = FindWindow(NULL,strProcessName.c_str()); if (ShowWindow(netTV,SW_SHOWNORMAL)) { LogItem=ListView_Log->Items->Insert(0); LogItem->Caption=Now().CurrentTime().FormatString("hh:nn:ss"); LogItem->SubItems->Add("Power Off"); LogItem->SubItems->Add(AContext->Connection->Socket->Binding->PeerIP); LogItem->SubItems->Add(msgList->Strings[0]); } else { LogItem=ListView_Log->Items->Insert(0); LogItem->Caption=Now().CurrentTime().FormatString("hh:nn:ss"); LogItem->SubItems->Add("Power On"); LogItem->SubItems->Add(AContext->Connection->Socket->Binding->PeerIP); LogItem->SubItems->Add(msgList->Strings[0]); } } if(sysCMD == "MUTE") { keyValue[0] = 0x4D; // M ChangeChannel(msgList->Strings[0], keyValue); if (iMuteCount%2 == 0) { LogItem=ListView_Log->Items->Insert(0); LogItem->Caption=Now().CurrentTime().FormatString("hh:nn:ss"); LogItem->SubItems->Add("Mute"); LogItem->SubItems->Add(AContext->Connection->Socket->Binding->PeerIP); LogItem->SubItems->Add(msgList->Strings[0]); iMuteCount++; } else { LogItem=ListView_Log->Items->Insert(0); LogItem->Caption=Now().CurrentTime().FormatString("hh:nn:ss"); LogItem->SubItems->Add("Unmute"); LogItem->SubItems->Add(AContext->Connection->Socket->Binding->PeerIP); LogItem->SubItems->Add(msgList->Strings[0]); iMuteCount++; } } if(sysCMD == "VOLUP") { keyValue[0] = VK_RIGHT; // -> ChangeChannel(msgList->Strings[0], keyValue); LogItem=ListView_Log->Items->Insert(0); LogItem->Caption=Now().CurrentTime().FormatString("hh:nn:ss"); LogItem->SubItems->Add("Vol Up"); LogItem->SubItems->Add(AContext->Connection->Socket->Binding->PeerIP); LogItem->SubItems->Add(msgList->Strings[0]); } if(sysCMD == "VOLDOWN") { keyValue[0] = VK_LEFT; // <- ChangeChannel(msgList->Strings[0], keyValue); LogItem=ListView_Log->Items->Insert(0); LogItem->Caption=Now().CurrentTime().FormatString("hh:nn:ss"); LogItem->SubItems->Add("Vol Down"); LogItem->SubItems->Add(AContext->Connection->Socket->Binding->PeerIP); LogItem->SubItems->Add(msgList->Strings[0]); } if(sysCMD == "CHNEXT") { keyValue[0] = VK_UP; // -> ChangeChannel(msgList->Strings[0], keyValue); LogItem=ListView_Log->Items->Insert(0); LogItem->Caption=Now().CurrentTime().FormatString("hh:nn:ss"); LogItem->SubItems->Add("Vol Up"); LogItem->SubItems->Add(AContext->Connection->Socket->Binding->PeerIP); LogItem->SubItems->Add(msgList->Strings[0]); } if(sysCMD == "CHBACK") { keyValue[0] = VK_DOWN; // <- ChangeChannel(msgList->Strings[0], keyValue); LogItem=ListView_Log->Items->Insert(0); LogItem->Caption=Now().CurrentTime().FormatString("hh:nn:ss"); LogItem->SubItems->Add("Vol Down"); LogItem->SubItems->Add(AContext->Connection->Socket->Binding->PeerIP); LogItem->SubItems->Add(msgList->Strings[0]); } } } //--------------------------------------------------------------------------- void __fastcall TForm_RemoteControl::IdTCPServer_RemoteConnect(TIdContext *AContext) { LogItem=ListView_Log->Items->Insert(0); LogItem->Caption=Now().CurrentTime().FormatString("hh:nn:ss"); LogItem->SubItems->Add("Connect Request"); LogItem->SubItems->Add(AContext->Connection->Socket->Binding->PeerIP); } //--------------------------------------------------------------------------- void __fastcall TForm_RemoteControl::IdTCPServer_RemoteDisconnect(TIdContext *AContext) { LogItem=ListView_Log->Items->Insert(0); LogItem->Caption=Now().CurrentTime().FormatString("hh:nn:ss"); LogItem->SubItems->Add("Client Disconnected"); LogItem->SubItems->Add(AContext->Connection->Socket->Binding->PeerIP); } //---------------------------------------------------------------------------