-1

I'm sorry if it's not proper English because I'm using a translator.

I downloaded a program from github that can control the mouse over the Android phone. There is no problem connecting to the server, But an error occurs when touching the textview to control the mouse.

Uniquely, when running a program with a virtual device, no error occurs and works well.

I've seen many examples and answers, but I can't solve them, so I'm re-posting. ;_; I'd really appreciate it if you could tell me which parts to modify.

public class MainActivity extends ActionBarActivity implements View.OnClickListener {

Context context;
Button playPauseButton;
Button nextButton;
Button previousButton;
TextView mousePad;

private boolean isConnected=false;
private boolean mouseMoved=false;
private Socket socket;
private PrintWriter out;

private float initX =0;
private float initY =0;
private float disX =0;
private float disY =0;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);

    context = this;

    playPauseButton = (Button)findViewById(R.id.playPauseButton);
    nextButton = (Button)findViewById(R.id.nextButton);
    previousButton = (Button)findViewById(R.id.previousButton);


    playPauseButton.setOnClickListener(this);
    nextButton.setOnClickListener(this);
    previousButton.setOnClickListener(this);

    mousePad = (TextView)findViewById(R.id.mousePad);


    mousePad.setOnTouchListener(new View.OnTouchListener() {
        @Override
        public boolean onTouch(View v, MotionEvent event) {
            if(isConnected && out!=null){
                switch(event.getAction()){
                    case MotionEvent.ACTION_DOWN:
                        initX =event.getX();
                        initY =event.getY();
                        mouseMoved=false;
                        break;
                    case MotionEvent.ACTION_MOVE:
                        disX = event.getX()- initX;
                        disY = event.getY()- initY;

                        initX = event.getX();
                        initY = event.getY();
                        if(disX !=0|| disY !=0){
                            out.println(disX +","+ disY);
                        }
                        mouseMoved=true;
                        break;
                    case MotionEvent.ACTION_UP:
                        if(!mouseMoved){
                            out.println(Constants.MOUSE_LEFT_CLICK);
                        }
                }
            }
            return true;
        }
    });
}

@Override
public boolean onCreateOptionsMenu(Menu menu) {
    getMenuInflater().inflate(R.menu.menu_main, menu);
    return true;
}

@Override
public boolean onOptionsItemSelected(MenuItem item) {

    int id = item.getItemId();

    if(id == R.id.action_connect) {
        ConnectPhoneTask connectPhoneTask = new ConnectPhoneTask();
        connectPhoneTask.execute(Constants.SERVER_IP); //try to connect to server in another thread
        return true;
    }
    return super.onOptionsItemSelected(item);
}

@Override
public void onClick(View v) {
    switch (v.getId()) {
        case R.id.playPauseButton:
            if (isConnected && out!=null) {
                out.println(Constants.PLAY);//send "play" to server
            }
            break;
        case R.id.nextButton:
            if (isConnected && out!=null) {
                out.println(Constants.NEXT); //send "next" to server
            }
            break;
        case R.id.previousButton:
            if (isConnected && out!=null) {
                out.println(Constants.PREVIOUS); //send "previous"
            }
            break;
    }

}

@Override
public void onDestroy()
{
    super.onDestroy();
    if(isConnected && out!=null) {
        try {
            out.println("exit"); //tell server to exit
            socket.close(); //close socket
        } catch (IOException e) {
            Log.e("remotedroid", "Error in closing socket", e);
        }
    }
}

public class ConnectPhoneTask extends AsyncTask<String,Void,Boolean> {

    @Override
    protected Boolean doInBackground(String... params) {
        boolean result = true;
        try {
            InetAddress serverAddr = InetAddress.getByName(params[0]);
            socket = new Socket(serverAddr, Constants.SERVER_PORT);//Open socket on server IP and port
        } catch (IOException e) {
            Log.e("remotedroid", "Error while connecting", e);
            result = false;
        }
        return result;
    }

    @Override
    protected void onPostExecute(Boolean result)
    {
        isConnected = result;
        Toast.makeText(context,isConnected?"Connected to server!":"Error while connecting",Toast.LENGTH_LONG).show();
        try {
            if(isConnected) {
                out = new PrintWriter(new BufferedWriter(new OutputStreamWriter(socket
                        .getOutputStream())), true); //create output stream to send data to server
            }
        }catch (IOException e){
            Log.e("remotedroid", "Error while creating OutWriter", e);
            Toast.makeText(context,"Error while connecting",Toast.LENGTH_LONG).show();
        }
    }
}

}

layout xml :

<TextView
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:layout_above="@+id/playPauseButton"
    android:clickable="true"
    android:background="@android:color/holo_blue_dark"
    android:id="@+id/mousePad"/>

<Button
    android:id="@+id/playPauseButton"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_alignParentBottom="true"
    android:layout_centerHorizontal="true"
    android:text="Button3" />

<Button
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:text="Left"
    android:id="@+id/previousButton"
    android:layout_alignParentBottom="true"
    android:layout_alignParentLeft="true"
    android:layout_alignParentStart="true" />

<Button
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:text="Right"
    android:id="@+id/nextButton"
    android:layout_alignParentBottom="true"
    android:layout_alignParentRight="true"
    android:layout_alignParentEnd="true" />

error :

05-01 03:53:09.768 8768-8768/samcox.remotedroid E/InputEventReceiver: Exception dispatching input event.
05-01 03:53:09.775 8768-8768/samcox.remotedroid E/AndroidRuntime: FATAL EXCEPTION: main
    Process: samcox.remotedroid, PID: 8768
    android.os.NetworkOnMainThreadException
        at android.os.StrictMode$AndroidBlockGuardPolicy.onNetwork(StrictMode.java:1513)
        at java.net.SocketOutputStream.socketWrite(SocketOutputStream.java:116)
        at java.net.SocketOutputStream.write(SocketOutputStream.java:161)
        at sun.nio.cs.StreamEncoder.writeBytes(StreamEncoder.java:221)
        at sun.nio.cs.StreamEncoder.implFlushBuffer(StreamEncoder.java:291)
        at sun.nio.cs.StreamEncoder.implFlush(StreamEncoder.java:295)
        at sun.nio.cs.StreamEncoder.flush(StreamEncoder.java:141)
        at java.io.OutputStreamWriter.flush(OutputStreamWriter.java:229)
        at java.io.BufferedWriter.flush(BufferedWriter.java:254)
        at java.io.PrintWriter.newLine(PrintWriter.java:482)
        at java.io.PrintWriter.println(PrintWriter.java:629)
        at java.io.PrintWriter.println(PrintWriter.java:740)
        at samcox.remotedroid.MainActivity$1.onTouch(MainActivity.java:77)
        at android.view.View.dispatchTouchEvent(View.java:13468)
        at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:3222)
        at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2904)
        at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:3222)
        at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2904)
        at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:3222)
        at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2904)
        at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:3222)
        at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2904)
        at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:3222)
        at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2904)
        at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:3222)
        at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:2904)
        at com.android.internal.policy.DecorView.superDispatchTouchEvent(DecorView.java:731)
        at com.android.internal.policy.PhoneWindow.superDispatchTouchEvent(PhoneWindow.java:1869)
        at android.app.Activity.dispatchTouchEvent(Activity.java:3487)
        at android.support.v7.internal.view.WindowCallbackWrapper.dispatchTouchEvent(WindowCallbackWrapper.java:59)
        at com.android.internal.policy.DecorView.dispatchTouchEvent(DecorView.java:689)
        at android.view.View.dispatchPointerEvent(View.java:13720)
        at android.view.ViewRootImpl$ViewPostImeInputStage.processPointerEvent(ViewRootImpl.java:6125)
        at android.view.ViewRootImpl$ViewPostImeInputStage.onProcess(ViewRootImpl.java:5903)
        at android.view.ViewRootImpl$InputStage.deliver(ViewRootImpl.java:5352)
        at android.view.ViewRootImpl$InputStage.onDeliverToNext(ViewRootImpl.java:5405)
        at android.view.ViewRootImpl$InputStage.forward(ViewRootImpl.java:5371)
        at android.view.ViewRootImpl$AsyncInputStage.forward(ViewRootImpl.java:5530)
        at android.view.ViewRootImpl$InputStage.apply(ViewRootImpl.java:5379)
        at android.view.ViewRootImpl$AsyncInputStage.apply(ViewRootImpl.java:5587)
        at android.view.ViewRootImpl$InputStage.deliver(ViewRootImpl.java:5352)
        at android.view.ViewRootImpl$InputStage.onDeliverToNext(ViewRootImpl.java:5405)
        at android.view.ViewRootImpl$InputStage.forward(ViewRootImpl.java:5371)
        at android.view.ViewRootImpl$InputStage.apply(ViewRootImpl.java:5379)
        at android.view.ViewRootImpl$InputStage.deliver(ViewRootImpl.java:5352)
        at android.view.ViewRootImpl.deliverInputEvent(ViewRootImpl.java:8412)
        at android.view.ViewRootImpl.doProcessInputEvents(ViewRootImpl.java:8345)
        at android.view.ViewRootImpl.enqueueInputEvent(ViewRootImpl.java:8298)
        at android.view.ViewRootImpl$WindowInputEventReceiver.onInputEvent(ViewRootImpl.java:8527)
        at android.view.InputEventReceiver.dispatchInputEvent(InputEventReceiver.java:198)
        at android.view.InputEventReceiver.nativeConsumeBatchedInputEvents(Native Method)
        at android.view.InputEventReceiver.consumeBatchedInputEvents(InputEventReceiver.java:187)
        at android.view.ViewRootImpl.doConsumeBatchedInput(ViewRootImpl.java:8486)
05-01 03:53:09.776 8768-8768/samcox.remotedroid E/AndroidRuntime:     at android.view.ViewRootImpl$ConsumeBatchedInputRunnable.run(ViewRootImpl.java:8554)
        at android.view.Choreographer$CallbackRecord.run(Choreographer.java:949)
        at android.view.Choreographer.doCallbacks(Choreographer.java:761)
        at android.view.Choreographer.doFrame(Choreographer.java:690)
        at android.view.Choreographer$FrameDisplayEventReceiver.run(Choreographer.java:935)
        at android.os.Handler.handleCallback(Handler.java:873)
        at android.os.Handler.dispatchMessage(Handler.java:99)
        at android.os.Looper.loop(Looper.java:214)
        at android.app.ActivityThread.main(ActivityThread.java:7073)
        at java.lang.reflect.Method.invoke(Native Method)
        at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:493)
        at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:964)

I am a beginner in programming, so please excuse my errors

Zoe
  • 27,060
  • 21
  • 118
  • 148
Seung Ju
  • 1
  • 2
  • That means that you are doing networking op on the main thread. In postExecute you are send network stream on your main thread. OnPostExecute always gets called on the main thread. – Taseer Apr 30 '19 at 19:04
  • Possible duplicate of [how to fix FATAL EXCEPTION:main android.os.NetworkOnMainThreadException](https://stackoverflow.com/questions/55910366/how-to-fix-fatal-exceptionmain-android-os-networkonmainthreadexception) – Morrison Chang Apr 30 '19 at 19:15
  • 2
    Please don't repost the same question. Edit the old question with your new data. – Morrison Chang Apr 30 '19 at 19:15
  • I'm sorry. I'll do that from now on. – Seung Ju Apr 30 '19 at 19:29
  • Duplicate of https://stackoverflow.com/questions/6343166/how-do-i-fix-android-os-networkonmainthreadexception – Zoe Apr 30 '19 at 19:39
  • 2
    Possible duplicate of [How do I fix android.os.NetworkOnMainThreadException?](https://stackoverflow.com/questions/6343166/how-do-i-fix-android-os-networkonmainthreadexception) – SimonC Apr 30 '19 at 23:00

2 Answers2

0

The issue is that inside the AsyncTask's onPostExecute you call the following:

socket.getOutputStream() 

This happens on the MainThread and therefore the exception is thrown. Move it to the doInBackground inside the try catch block so it looks like this:

public class ConnectPhoneTask extends AsyncTask<String,Void,Boolean> {

    @Override
    protected Boolean doInBackground(String... params) {
        boolean result = true;
        try {
            InetAddress serverAddr = InetAddress.getByName(params[0]);
            socket = new Socket(serverAddr, Constants.SERVER_PORT);//Open socket on server IP and port
            if(isConnected) {
                out = new PrintWriter(new BufferedWriter(new OutputStreamWriter(socket
                        .getOutputStream())), true); //create output stream to send data to server
            }
        } catch (IOException e) {
            Log.e("remotedroid", "Error while connecting", e);
            result = false;
        }
        return result;
    }

    @Override
    protected void onPostExecute(Boolean result)
    {
        isConnected = result;
        Toast.makeText(context,isConnected?"Connected to server!":"Error while connecting",Toast.LENGTH_LONG).show();
    }
}
Rene Ferrari
  • 4,096
  • 3
  • 22
  • 28
  • Thank you for your answer, but I moved socket.getOutputStream() into doInBackground, and the same error occurred. Is there any problem with the other part? – Seung Ju Apr 30 '19 at 20:15
  • The part that transmits data to the server was operating on the mainthread. Thank you. It was really helpful. – Seung Ju Apr 30 '19 at 20:42
0

I recommend that when you get errors you are unsure of what is causing it, you should break down complex instructions into simple instructions and set a breakpoint so you can walk through them and see exactly which instruction is resulting in the runtime error. So, in the code above, you could maybe simplify as so:

 OutputStream os = socket.getOutputStream();
 OutputStreamWriter ow = new OutputStreamWriter(os);
 out = new PrintWriter(ow, true); //create output stream to send data to server
Michael Dougan
  • 1,698
  • 1
  • 9
  • 13