【发布时间】:2016-02-04 23:32:31
【问题描述】:
我正在为我的 arduino 汽车制作遥控应用程序。使用的代码首先在 Eclipse 中使用 Java 进行了测试,现在我正在尝试将相同的代码用于 Android 应用程序。
我使用了jSerialComm库,根据Android Studio,我的代码没有错误,但是当我运行它时,却找不到库?我收到以下错误:
致命异常:主要 进程:com.sahragard.avengrecontroller,PID:11728 java.lang.UnsatisfiedLinkError: dlopen failed: 文件偏移量 图书馆 "/data/user/0/com.sahragard.avengrecontroller/cache/1454627726168-libjSerialComm.so"
= 文件大小:0 >= 0 在 java.lang.Runtime.load(Runtime.java:332) 在 java.lang.System.load(System.java:1069) 在 com.fazecast.jSerialComm.SerialPort.(SerialPort.java:181) 在 com.sahragard.avengrecontroller.Conn.getPorts(Conn.java:19) 在 com.sahragard.avengrecontroller.MainActivity.onCreate(MainActivity.java:25) 在 android.app.Activity.performCreate(Activity.java:6237) 在 android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1107) 在 android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2369) 在 android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2476) 在 android.app.ActivityThread.-wrap11(ActivityThread.java) 在 android.app.ActivityThread$H.handleMessage(ActivityThread.java:1344) 在 android.os.Handler.dispatchMessage(Handler.java:102) 在 android.os.Looper.loop(Looper.java:148) 在 android.app.ActivityThread.main(ActivityThread.java:5417) 在 java.lang.reflect.Method.invoke(本机方法) 在 com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:726) 在 com.android.internal.os.ZygoteInit.main(ZygoteInit.java:616)
我用谷歌搜索了好几个小时,并按照我找到的提示进行操作,但无论我做什么,总是出现同样的错误。我根据这篇文章添加了库: https://stackoverflow.com/a/16628496/4582696
感谢我能得到的任何帮助!提前致谢。
编辑:
MainActivity 类是对包含 Swing 接口的类的改编,其代码添加在此代码下方
public class MainActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
final Spinner conSpinner =(Spinner) findViewById(R.id.spinner);
String[] a = new String[Conn.getPorts().length];
for(int i=0; i<Conn.getPorts().length; i++){
a[i] = Conn.getPorts()[i].getSystemPortName();
}
ArrayAdapter<String> adapter = new ArrayAdapter<String>(this,
android.R.layout.simple_spinner_item, a);
conSpinner.setAdapter(adapter);
final Button disconnectButton = (Button) findViewById(R.id.disconnect);
disconnectButton.setOnClickListener(new Button.OnClickListener() {
public void onClick(View v) {
Conn.disconnect();
}
});
final Button connectButton = (Button) findViewById(R.id.connect);
connectButton.setOnClickListener(new Button.OnClickListener() {
public void onClick(View v) {
Conn.connect(conSpinner.getSelectedItemPosition());
Runnable run = new Runnable() {
public void run() {
Conn.listen();
}
};
Conn.listen = new Thread(run);
Conn.listen.start();
}
});
final Button up = (Button) findViewById(R.id.upButton);
up.setOnClickListener(new Button.OnClickListener() {
public void onClick(View v) {
Conn.sendMsg("w");
}
});
final Button down = (Button) findViewById(R.id.downButton);
down.setOnClickListener(new Button.OnClickListener() {
public void onClick(View v) {
Conn.sendMsg("s");
}
});
final Button left = (Button) findViewById(R.id.leftButton);
left.setOnClickListener(new Button.OnClickListener() {
public void onClick(View v) {
Conn.sendMsg("a");
}
});
final Button right = (Button) findViewById(R.id.rightButton);
right.setOnClickListener(new Button.OnClickListener() {
public void onClick(View v) {
Conn.sendMsg("d");
}
});
}
}
原始 Remote_Interface 类
import java.awt.BorderLayout;
import java.awt.EventQueue;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.border.EmptyBorder;
import com.fazecast.jSerialComm.SerialPort;
import javax.swing.JComboBox;
import javax.swing.JTextField;
import javax.swing.JButton;
import javax.swing.JTextPane;
import java.awt.SystemColor;
import java.awt.event.ActionListener;
import java.awt.event.ActionEvent;
public class Remote_Interface extends JFrame {
private JPanel contentPane;
private JTextField textField;
/**
* Launch the application.
*/
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
public void run() {
try {
Remote_Interface frame = new Remote_Interface();
frame.setVisible(true);
// Conn.listen();
} catch (Exception e) {
e.printStackTrace();
}
}
});
}
/**
* Create the frame.
*/
public Remote_Interface() {
setResizable(false);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setBounds(100, 100, 270, 268);
contentPane = new JPanel();
contentPane.setBorder(new EmptyBorder(5, 5, 5, 5));
setContentPane(contentPane);
contentPane.setLayout(null);
JComboBox<String> comboBox = new JComboBox<String> ();
comboBox.setBounds(20, 46, 214, 20);
for(int i=0; i<Conn.getPorts().length; i++){
comboBox.addItem(Conn.getPorts()[i].getSystemPortName());
}
contentPane.add(comboBox);
textField = new JTextField();
textField.setBounds(20, 131, 214, 20);
contentPane.add(textField);
textField.setColumns(10);
textField.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e){
Conn.sendMsg(e.getActionCommand());
textField.setText("");
}
});
JButton btnNewButton = new JButton("Send");
btnNewButton.setBounds(20, 162, 89, 23);
contentPane.add(btnNewButton);
JTextPane txtpnPleaseSelectA = new JTextPane();
txtpnPleaseSelectA.setBackground(SystemColor.control);
txtpnPleaseSelectA.setText("Please select a port to connect");
txtpnPleaseSelectA.setEditable(false);
txtpnPleaseSelectA.setBounds(10, 11, 214, 20);
contentPane.add(txtpnPleaseSelectA);
btnNewButton.setEnabled(false);
textField.setEnabled(false);
JButton btnNewButton_1 = new JButton("Connect");
btnNewButton_1.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent arg0) {
Conn.connect(comboBox.getSelectedIndex());
btnNewButton.setEnabled(true);
textField.setEnabled(true);
Runnable run = new Runnable(){
public void run(){
Conn.listen();
}
};
Conn.listen = new Thread(run);
Conn.listen.start();
}
});
btnNewButton_1.setBounds(143, 77, 89, 23);
contentPane.add(btnNewButton_1);
JButton btnD = new JButton("Disconnect");
btnD.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent arg0) {
Conn.disconnect();
btnNewButton.setEnabled(false);
textField.setEnabled(false);
}
});
btnD.setBounds(20, 77, 89, 23);
contentPane.add(btnD);
}
}
还有 Conn 类
import com.fazecast.jSerialComm.*;
import java.io.PrintWriter;
import java.util.Scanner;
public class Conn {
static PrintWriter out;
static SerialPort[] ports;
static SerialPort port;
static Scanner in;
static Thread listen;
public static SerialPort[] getPorts(){
ports = SerialPort.getCommPorts();
return ports;
}
public static void sendMsg(String s){
out.println(s);
out.flush();
}
public static void connect(int i){
port = ports[i];
port.openPort();
port.setComPortTimeouts(SerialPort.TIMEOUT_SCANNER, 0, 0);
out = new PrintWriter(port.getOutputStream());
in = new Scanner(port.getInputStream());
}
public static void disconnect(){
port.closePort();
}
public static void listen(){// handle the input from the Arduino chip
while(in.hasNextLine()){
System.out.println(in.nextLine());// just print it out to the console
}
}
}
【问题讨论】:
-
你看过其他 SO 线程吗?这个 - stackoverflow.com/a/28152287/1091286 例如谈论芯片架构的差异,考虑到你正在为 arduino 开发一些东西,这可能是问题....
-
感谢您的回答!我不太明白该问题上发布的答案。但我的问题是,当我在手机或虚拟手机上运行该应用程序时,它会立即崩溃。所以它还没有与 Arduino 芯片建立任何连接
-
at com.fazecast.jSerialComm.SerialPort第 181 行。是库,这意味着它已加载 -
@cricket_007 但为什么它说“dlopen 失败:库的文件偏移量”?
-
根据堆栈跟踪,无论您在第 19 行的
Conn.getPorts处做什么,库都不喜欢那样。我还看到您正在使用模型对象作为静态实用程序类。那只是糟糕的代码......对不起