本代码只支持16进制发送与接收,主要参照蓝牙的16进制发送与接收而修改的WiFi客户端。
WiFi的基本的配置方法:https://blog.csdn.net/weixin_44244812/article/details/104303322
我使用Android WiFi客户端时,我的安卓5.0版本的手机能连接WiFi,并能发送和接收数据,然而开发的APP在大老板的高级版(如10.0版本,8.0版本)的安卓里只能连接,不能发送和接收数据,这样辛辛苦苦设计的APP变得毫无用处。巨伤心。
我在找原因,找解决方法,如这位博主的文章https://blog.csdn.net/banzhihuanyu/article/details/81056561,有兴趣的点击看下,我发现WiFi的安卓版本设计要求实在乱,我也不是专业干Android Studio ,我只想当个嵌入式工程师,APP当作上位机而已。网上找了不少的demo,发现水积分的大有人在,应该是各种解决方法应该是当时有效的,现在Android版本的变化太大的原因吧。
终于天道酬勤,功夫不负有心人,终于解决了这个问题。如果你是下载过我的旧WiFi调试助手,私信我,我发最新的给你,如有出现什么问题请一定告诉我,我就一台旧版本手机,需要大家的测试和反馈才能创造更好的WIFI_APP上位机。
WiFi调戏助手2.0下载地址:https://download.csdn.net/download/weixin_44244812/12356294
若你是VIP大佬,请求你支持一下我,送点积分给我,我不是VIP,每次下载有关WiFi的设计demo都让我心疼,你们的亿点点支持,都是我成长的动力,积分支持链:https://download.csdn.net/download/weixin_44244812/12356294
DEMO介绍:
界面如下:
获取IP相关代码:
private WifiManager wifiManager;
// 服务器管理器
private DhcpInfo dhcpInfo;
private int wificonnection=0;
private void wifi_Init() {
// 得到服务器的IP地址
wifiManager = (WifiManager) getApplicationContext(). getSystemService(Context.WIFI_SERVICE);
dhcpInfo = wifiManager.getDhcpInfo();
IPadress = Formatter.formatIpAddress(dhcpInfo.gateway);
ipadress_st.setText(IPadress);
}
我懒了,若无积分的请自行复制粘贴吧:
结构框图:
AndroidManifest.xml
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
package="com.bkrc.car2019.socket_connect">
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE"/>
<uses-permission android:name="android.permission.INTERNET" />
<application
android:allowBackup="true"
android:icon="@mipmap/bkrckj_logo"
android:label="@string/app_name"
android:roundIcon="@mipmap/ic_launcher"
android:supportsRtl="true"
android:theme="@style/AppTheme"
tools:replace="android:icon, android:theme">
<activity android:name="com.bkrc.car2019.socket_connect.MainActivity"
android:screenOrientation="portrait"
android:windowSoftInputMode="stateAlwaysHidden|adjustPan">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>
</manifest>
MainActivity
package com.bkrc.car2019.socket_connect;
import android.content.Context;
import android.content.res.Configuration;
import android.net.DhcpInfo;
import android.net.wifi.WifiManager;
import android.os.Handler;
import android.os.Message;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.text.format.Formatter;
import android.util.Log;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ImageButton;
import android.widget.TextView;
import android.widget.Toast;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
public class MainActivity extends AppCompatActivity {
private byte[] mByte = new byte[11];
private TextView Data_show_st =null;
private EditText ipadress_st = null,ipcom_st=null,Data_send_st=null;
private Button clear_receive_st,getClear_send_st,send_st,get_ip_st,connection_st;
private connect_transport sock_con;
private WifiManager wifiManager;
// 服务器管理器
private DhcpInfo dhcpInfo;
private int wificonnection=0;
static String IPadress;
static ExecutorService executorServicetor = Executors.newCachedThreadPool();
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
control_init();
sock_con =new connect_transport();
}
public static boolean isPad(Context context) {
return (context.getResources().getConfiguration().screenLayout
& Configuration.SCREENLAYOUT_SIZE_MASK)
>= Configuration.SCREENLAYOUT_SIZE_LARGE;
}
//WiFi初始化
private void wifi_Init() {
// 得到服务器的IP地址
wifiManager = (WifiManager) getApplicationContext(). getSystemService(Context.WIFI_SERVICE);
dhcpInfo = wifiManager.getDhcpInfo();
IPadress = Formatter.formatIpAddress(dhcpInfo.gateway);
ipadress_st.setText(IPadress);
}
private void control_init()
{
ipadress_st=(EditText) findViewById(R.id.ipadress);
ipcom_st=(EditText)findViewById(R.id.com);
Data_show_st =(TextView) findViewById(R.id.rvdata);
Data_send_st =(EditText) findViewById(R.id.senddata);
clear_receive_st=(Button)findViewById(R.id.reclear);
getClear_send_st=(Button)findViewById(R.id.sendclear);
send_st=(Button)findViewById(R.id.sendto);
connection_st=(Button)findViewById(R.id.buttonconnection);
get_ip_st=(Button)findViewById(R.id.buttonip);
clear_receive_st.setOnClickListener(new onClickListener());
getClear_send_st.setOnClickListener(new onClickListener());
send_st.setOnClickListener(new onClickListener());
connection_st.setOnClickListener(new onClickListener());
get_ip_st.setOnClickListener(new onClickListener());
}
// 接受显示小车发送的数据
private Handler recvhandler = new Handler() {
public void handleMessage(Message msg) {
if (msg.what == 1) {
// mByte = (byte[]) msg.obj;
String result = msg.getData().get("msg").toString();
result+=" ";
Data_show_st.append(result);
}
}
};
private class onClickListener implements View.OnClickListener
{
@Override
public void onClick(View v) {
switch(v.getId())
{
case R.id.reclear:
Data_show_st.setText(null);
break;
case R.id.sendclear:
Data_send_st.setText(null);
break;
case R.id.sendto:
sock_con.send(Data_send_st.getText().toString());
break;
case R.id.buttonconnection:
if(wificonnection==1){
connection_st.setText("未连接");
sock_con .destory();
wificonnection=0;
}
else {
executorServicetor.execute(new Runnable() {
@Override
public void run() {
if (wificonnection == 0) {
try {
sock_con.connect(recvhandler, ipadress_st.getText().toString(), Integer.valueOf(ipcom_st.getText().toString(), 10));
connection_st.setText("已连接");
wificonnection = 1;
} catch (Exception e) {
//Toast.makeText(MainActivity.this, "提示:连接失败", Toast.LENGTH_SHORT).show();
}
}
}
});
}
break;
case R.id.buttonip:
wifi_Init();
break;
default:
break;
}
}
}
private class onLongClickListener2 implements View.OnLongClickListener {
@Override
public boolean onLongClick(View view) {
return true;
}
}
}
connect_transport
package com.bkrc.car2019.socket_connect;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.util.Log;
import android.widget.Toast;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.Socket;
import java.net.UnknownHostException;
public class connect_transport {
public static DataInputStream bInputStream = null;
public static DataOutputStream bOutputStream =null;
public static Socket socket = null;
private byte[] rbyte = new byte[40];
private Handler reHandler;
public short TYPE=0xAA;
public short MAJOR = 0x00;
public short FIRST = 0x00;
public short SECOND = 0x00;
public short THRID = 0x00;
public short CHECKSUM=0x00;
private byte[] msg = new byte[6000];
public void destory(){
try {
if(socket!=null&&!socket.isClosed()){
socket.close();
bInputStream.close();
bOutputStream.close();
}
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
public void connect(Handler reHandler ,String IP,int port) {
try {
this.reHandler =reHandler;
socket = new Socket(IP, port);
bInputStream = new DataInputStream(socket.getInputStream());
bOutputStream = new DataOutputStream(socket.getOutputStream());
reThread.start();
} catch (UnknownHostException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
private Thread reThread = new Thread(new Runnable() {
@Override
public void run() {
// TODO Auto1-generated method stub
while (socket != null && !socket.isClosed()) {
try{
//////////////////////
String result = bytesToString(readFromInputStream(bInputStream)); //通过从输入流读取数据,返回给result
if (!result.equals("")) {
Message msg = new Message(); //获取�?��消息
msg.what = 1; //设置message的what属�?的�?
msg.obj = rbyte;
Bundle data = new Bundle();
data.putString("msg", result);
msg.setData(data);
reHandler.sendMessage(msg); //发�?消息
}
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
});
/////////////////////////////////////////////////////
public byte[] readFromInputStream(InputStream in) {
int count = 0;
byte[] inDatas = null;
try {
while (count == 0) {
count = in.available();
}
inDatas = new byte[count];
in.read(inDatas);
} catch (Exception e) {
e.printStackTrace();
}
return inDatas ;
}
public String getHexString(String send) {
String s = send;
int i;
StringBuilder sb = new StringBuilder();
for ( i = 0; i < s.length(); i++) {
char c = s.charAt(i);
if (('0' <= c && c <= '9') || ('a' <= c && c <= 'f') ||
('A' <= c && c <= 'F')) {
sb.append(c);
}
}
if ((sb.length() % 2) != 0) {
sb.deleteCharAt(sb.length());
}
return sb.toString();
}
public byte[] stringToBytes(String s) {
byte[] buf = new byte[s.length() / 2];
for (int i = 0; i < buf.length; i++) {
try {
buf[i] = (byte) Integer.parseInt(s.substring(i * 2, i * 2 + 2), 16);
} catch (NumberFormatException e) {
e.printStackTrace();
}
}
return buf;
}
public String bytesToString(byte[] bytes) {
final char[] hexArray = "0123456789ABCDEF".toCharArray();
char[] hexChars = new char[bytes.length * 2];
StringBuilder sb = new StringBuilder();
try{
for (int i = 0; i < bytes.length; i++) {
int v = bytes[i] & 0xFF;
hexChars[i * 2] = hexArray[v >>> 4];
hexChars[i * 2 + 1] = hexArray[v & 0x0F];
sb.append(hexChars[i * 2]);
sb.append(hexChars[i * 2 + 1]);
sb.append(' ');
}}
catch (NumberFormatException e) {
e.printStackTrace();
};
return sb.toString();
}
public void send( String X)
{
CHECKSUM=(short) ((MAJOR+FIRST+SECOND+THRID)%256);
final byte[] sbyte= stringToBytes( getHexString(X));
MainActivity.executorServicetor.execute(new Runnable() { //开启线程,传输数据
@Override
public void run() {
// TODO Auto-generated method stub
try{
if (socket != null && !socket.isClosed()) {
bOutputStream.write(sbyte, 0, sbyte.length);
bOutputStream.flush();
}
} catch (IOException e) {
e.printStackTrace();
}
}
});
}
public void send_voice(final byte [] textbyte) {
MainActivity.executorServicetor.execute(new Runnable() {
@Override
public void run() {
// TODO Auto-generated method stub
try {
if (socket != null && !socket.isClosed()) {
bOutputStream.write(textbyte, 0, textbyte.length);
bOutputStream.flush();
}
} catch (IOException e) {
e.printStackTrace();
}
}
});
}
// 沉睡
public void yanchi(int time) {
try {
Thread.sleep(time);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@color/green"
android:gravity="right"
android:orientation="vertical">
<TextView
android:id="@+id/title"
android:layout_width="match_parent"
android:layout_height="78dp"
android:gravity="center_horizontal"
android:text="socket 客户端十六进制显示实例"
android:textColor="@color/white"
android:textSize="24sp" />
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal">
<TextView
android:id="@+id/textView4"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="IP地址:" />
<EditText
android:id="@+id/ipadress"
android:layout_width="172dp"
android:layout_height="wrap_content"
android:ems="10"
android:hint="格式(192.168.4.1)"
android:inputType="textPersonName" />
<Button
android:id="@+id/buttonip"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="获取IP" />
</LinearLayout>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal">
<TextView
android:id="@+id/textView3"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="端口号:" />
<EditText
android:id="@+id/com"
android:layout_width="171dp"
android:layout_height="wrap_content"
android:ems="10"
android:hint="格式:9999"
android:inputType="textPersonName" />
<Button
android:id="@+id/buttonconnection"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="连接" />
</LinearLayout>
<TextView
android:id="@+id/rvdata"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="2"
android:hint="接收数据(用空格隔开)"
android:textSize="20sp" />
<Button
android:id="@+id/reclear"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center"
android:text="清空" />
<EditText
android:id="@+id/senddata"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="3"
android:hint="发送十六数据(用空格隔开)"/>
<Button
android:id="@+id/sendclear"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="清空" />
<Button
android:id="@+id/sendto"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="发送" />
如果点赞过20或下载积分需求超20,我就写一篇手把手弄智能家居APP,读温湿度,酒精检测,点灯之类的。