服务端
package com.jay.msgapp2;

import android.app.Service;
import android.content.Intent;
import android.os.Bundle;
import android.os.Handler;
import android.os.IBinder;
import android.os.Looper;
import android.os.Message;
import android.os.Messenger;
import android.os.RemoteException;
import android.util.Log;

public class BService extends Service {
    //记录下客户端发过来的 Messenger
    Messenger clientMessenger;
    //接受客户端发过来的消息
    Messenger messenger = new Messenger(new Handler(Looper.myLooper()) {
        @Override
        public void handleMessage(Message msg) {
            //客户端发送来的数据 msg 中还有齐他参数,客户端发送过来都可以拿到
            String clientData = msg.getData().getString("data");
            //客户端的 Messenger 对象
            clientMessenger = msg.replyTo;
            //发送数据返回给客户端
            sendMsgToClient();
            super.handleMessage(msg);
        }
    });
    //服务端绑定器
    @Override
    public IBinder onBind(Intent intent) {
        //绑定成功
        return messenger.getBinder();
    }
    //发送数据返回给客户端
    private void sendMsgToClient(){
        Message message = Message.obtain();
        Bundle bundle = new Bundle();
        bundle.putString("data","成功返回给客户端数据...");
        message.setData(bundle);
        try {
            clientMessenger.send(message);
        } catch (RemoteException e) {
            e.printStackTrace();
        }
    }
}

服务端AndroidManifest.xml在application节点下,把上面的服务配置一下:<service android:name=".BService" android:enabled="true" android:exported="true"></service>
服务端的MainActivity中启动服务

package com.jay.msgapp2;

import androidx.appcompat.app.AppCompatActivity;

import android.content.Intent;
import android.os.Bundle;

public class MainActivity extends AppCompatActivity {

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

        Intent intent1 = new Intent(this, BService.class);
        startService(intent1);
    }
}


客户端

package com.jay.myapplication;

import androidx.appcompat.app.AppCompatActivity;

import android.content.ComponentName;
import android.content.Intent;
import android.content.ServiceConnection;
import android.os.Bundle;
import android.os.Handler;
import android.os.IBinder;
import android.os.Looper;
import android.os.Message;
import android.os.Messenger;
import android.os.RemoteException;
import android.util.Log;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;

public class MainActivity extends AppCompatActivity {

    public TextView mtxtMsg;
    public Messenger sendMessenger;

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

        mtxtMsg = findViewById(R.id.txtMsg);
        //一个按钮来发消息
        Button btnPlay = (Button) findViewById(R.id.btn1);
        try {
            connectService();//建立连接,构建 sendMessenger
        } catch (Exception ex) {
            mtxtMsg.setText("连接异常:" + ex.getMessage());
        }
        btnPlay.setOnClickListener(view -> {
            try {
                Message message = Message.obtain(null, 1);
                //把自己的Messenger带进去 服务端拿到之后 可以直接通过这个对象发数据过来
                //就是服务端的 clientMessenger
                message.replyTo = replyMessenger;
                Bundle bundle = new Bundle();
                bundle.putString("data", "服务器你好");//key和服务端的一致
                message.setData(bundle);
                //发送消息的方法
                sendMessenger.send(message);
            } catch (RemoteException ex) {
                mtxtMsg.setText("远程异常:" + ex.getMessage());
            } catch (Exception exception) {
                mtxtMsg.setText("发送异常:" + exception.getMessage());
            }
        });
    }

    /**
     * 和服务器建立连接 连接成功之后 sendMessenger 就是发消息的对象。
     **/
    private void connectService() throws Exception {
        ServiceConnection serviceConnection = new ServiceConnection() {
            @Override
            public void onServiceConnected(ComponentName name, IBinder service) {
                sendMessenger = new Messenger(service);//连接成功
            }

            @Override
            public void onServiceDisconnected(ComponentName name) {
//                Log.e("kk", "链接断开!");
            }
        };
        Intent intent = new Intent();
        //需要在AndroidManifest.xml中配置包名的可见性com.jay.msgapp2
        intent.setComponent(new ComponentName("com.jay.msgapp2", "com.jay.msgapp2.BService"));
        boolean res = getApplicationContext().bindService(intent, serviceConnection, BIND_AUTO_CREATE);
        if (!res) {
            throw new Exception("连接失败");
        }
    }

    //客户端的Messenger
    Messenger replyMessenger = new Messenger(new Handler(Looper.myLooper()) {
        @Override
        public void handleMessage(Message msg) {
            String data = msg.getData().getString("data");//服务端返回的数据
            mtxtMsg.setText("返回:" + data);
            super.handleMessage(msg);
        }
    });
}

客户端连接服务端的时候调用bindService方法,要加上 getApplicationContext().bindService(intent, serviceConnection, BIND_AUTO_CREATE);
build.gradle中要配置 compileSdk 31  minSdk 31  targetSdk 31,至少30,因为我的手机是Android12,所以我配置的是31。AndroidManifest.xml中配置<application tools:targetApi="31"...
客户端的AndroidManifest.xml中配置包可见性,或者配置权限可发现所有包<uses-permission android:name="android.permission.QUERY_ALL_PACKAGES" />

<queries>
    <package android:name="com.jay.msgapp2" />
</queries>

总的来说和网上大部分文章差不多,只是很多文章没有写 服务端的版本配置,启动服务。客户端的软件包可见性配置,连接服务使用getApplicationContext().bindService()
另外,gradle插件的版本也不能太低,具体是多少我也没试,看别人说不能太低,我的 Android Gradle Plugin Version 7.3.0  /  Gradle Version 7.4。
参考文章:
https://blog.csdn.net/qq379454816/article/details/52573476
https://www.jb51.net/article/76470.htm 
https://www.jb51.net/article/76474.htm 
https://www.jianshu.com/p/b2c86d4aa366
软件包可见性 https://blog.csdn.net/yang_study_first/article/details/119787421

posted on 2022-11-08 17:21  邢帅杰  阅读(455)  评论(0编辑  收藏  举报