【发布时间】:2022-06-14 23:48:54
【问题描述】:
让我快速描述一下我的设置和目标。我有一个运行 Android 版本 7.1.2 的 android 平板显示器
我有一个通过以太网连接到 Android 平板电脑的电机控制器。在我控制电机控制器的 Android 应用程序中,我使用 Wifi 与一些提供/存储数据的服务器进行通信。目前,我可以使用 Android 模拟器(在 Android Studio 中),它允许我与电机控制器通信,同时还可以使用 wifi 调用服务器。当我在 Android 平板电脑上运行该应用程序时,我只能同时启用 WifiOR 以太网。
根据this post,这是 Android 本身的硬限制。它还详细介绍了一些可能的修复方法,但它已经很老了,老实说,我对他们模糊说明所描述的所需步骤没有任何经验。
谁能为这个问题提供一个更新的解决方案,最好是对像我这样的新手来说更详细一点的解决方案?即使只是一个指向学习如何执行解决此问题的必要步骤的指针也会很棒,我已经坚持了一段时间!感谢您的帮助!
编辑:这是关于 AlwaysLearning 答案的一些相关信息...
我用来管理从 Modbus 读取的类
public class ModbusRead {
private static final String TAG = "MODBUS READ";
ModbusClient mClientReadAll;
public ModbusRead()
{
// IP = "192.168.124.2";
// port = 502;
mClientReadAll = new ModbusClient(Modbus.IP, Integer.valueOf(Modbus.port));
mClientReadAll.setUnitIdentifier((byte)255);
}
public Runnable readAll()
{
return () -> {
ReadAllFromModbus mReadAll = new ReadAllFromModbus();
mReadAll.execute();
};
}
public class ReadAllFromModbus extends AsyncTask<String, Void, String> {
private final String TAG = "READ ALL FROM MODBUS";
@Override
protected String doInBackground(String... params) {
try
{
mClientReadAll.Connect();
// get all registers
int[] registerBlock = mClientReadAll.ReadHoldingRegisters(Constants.RegisterRead.HR_MODE.getRegister()- 1, 16);
int[] wideRegisters = new int[] {
Modbus.convertWideRegister(mClientReadAll.ReadHoldingRegisters(Constants.RegisterRead.HR_ACTUAL_POSITION.getRegister() - 1, 2)),
Modbus.convertWideRegister(mClientReadAll.ReadHoldingRegisters(Constants.RegisterRead.HR_TARGET_POSITION.getRegister() - 1, 2)),
Modbus.convertWideRegister(mClientReadAll.ReadHoldingRegisters(Constants.RegisterRead.HR_ROM_DELTA.getRegister() - 1, 2)),
Modbus.convertWideRegister(mClientReadAll.ReadHoldingRegisters(Constants.RegisterRead.HR_REWIND_ZERO.getRegister() - 1, 2))
};
int[] tensionRegister = mClientReadAll.ReadHoldingRegisters(Constants.RegisterRead.HR_ACTUAL_TENSION.getRegister() - 1, 1);
Modbus.updateAllRegisters(registerBlock, wideRegisters, tensionRegister);
}
catch (Exception e)
{
Log.i(TAG, "ERROR IN GETTING ALL REGISTERS LOOP: " + e.getMessage());
e.printStackTrace();
}
return null;
}
@Override
protected void onPostExecute(String s) {
super.onPostExecute(s);
try
{
mClientReadAll.Disconnect();
}
catch(Exception e)
{
Log.i(TAG, "ERROR IN DISCONNECTING");
}
}
}
}
我的仪表板类的相关部分将处理启动执行所有 modbus 读取的线程
modbusRead = new ModbusRead();
final ConnectivityManager connectivityManager = (ConnectivityManager) this.getApplicationContext().getSystemService(Context.CONNECTIVITY_SERVICE);
final NetworkRequest requestEthernet = new NetworkRequest.Builder() .addTransportType(NetworkCapabilities.TRANSPORT_ETHERNET)
.build();
final ConnectivityManager.NetworkCallback cbEthernet = new ConnectivityManager.NetworkCallback() {
@Override
public void onAvailable(Network network) {
// Triggers when this network is available so you can bind to it.
}
};
connectivityManager.requestNetwork(requestEthernet, cbEthernet);
// the thread I am using to read from the modbus over ethernet every 250 milliseconds
ScheduledExecutorService executorService = Executors.newSingleThreadScheduledExecutor();
executorService.scheduleAtFixedRate(modbusRead.readAll(), 0, 250, TimeUnit.MILLISECONDS);
我将如何强制 ModbusRead 类在此处使用以太网?
【问题讨论】:
-
这是可能的。但应用程序本身需要明确请求特定的网络类型。即,如果您的电机控制器应用程序想要使用 Wifi 进行某些特定操作,它需要通过专门为 Wifi 发出请求来让 Android 知道这一点。这是一个示例解决方案供参考:stackoverflow.com/a/67081087/2267817
-
@AlwaysLearning,谢谢你的回答!您是否知道我将如何将您的解决方案集成到我的项目中(使用上面提供的代码)?
标签: java android networking