Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit dd69a067 authored by TreeHugger Robot's avatar TreeHugger Robot Committed by Android (Google) Code Review
Browse files

Merge "PhonePolicy: Only auto connect to the last active A2DP device" into pi-dev

parents cca18d56 0d3afb25
Loading
Loading
Loading
Loading
+149 −102
Original line number Diff line number Diff line
@@ -78,10 +78,10 @@ class PhonePolicy {
    private static final int MESSAGE_PROFILE_INIT_PRIORITIES = 2;
    private static final int MESSAGE_CONNECT_OTHER_PROFILES = 3;
    private static final int MESSAGE_ADAPTER_STATE_TURNED_ON = 4;
    private static final int MESSAGE_PROFILE_ACTIVE_DEVICE_CHANGED = 5;

    // Timeouts
    @VisibleForTesting
    static int sConnectOtherProfilesTimeoutMillis = 6000; // 6s
    @VisibleForTesting static int sConnectOtherProfilesTimeoutMillis = 6000; // 6s

    private final AdapterService mAdapterService;
    private final ServiceFactory mFactory;
@@ -110,6 +110,11 @@ class PhonePolicy {
                            BluetoothProfile.A2DP, -1, // No-op argument
                            intent).sendToTarget();
                    break;
                case BluetoothA2dp.ACTION_ACTIVE_DEVICE_CHANGED:
                    mHandler.obtainMessage(MESSAGE_PROFILE_ACTIVE_DEVICE_CHANGED,
                            BluetoothProfile.A2DP, -1, // No-op argument
                            intent).sendToTarget();
                    break;
                case BluetoothAdapter.ACTION_STATE_CHANGED:
                    // Only pass the message on if the adapter has actually changed state from
                    // non-ON to ON. NOTE: ON is the state depicting BREDR ON and not just BLE ON.
@@ -169,6 +174,14 @@ class PhonePolicy {
                }
                break;

                case MESSAGE_PROFILE_ACTIVE_DEVICE_CHANGED: {
                    Intent intent = (Intent) msg.obj;
                    BluetoothDevice activeDevice =
                            intent.getParcelableExtra(BluetoothDevice.EXTRA_DEVICE);
                    processProfileActiveDeviceChanged(activeDevice, msg.arg1);
                }
                break;

                case MESSAGE_CONNECT_OTHER_PROFILES: {
                    // Called when we try connect some profiles in processConnectOtherProfiles but
                    // we send a delayed message to try connecting the remaining profiles
@@ -195,6 +208,7 @@ class PhonePolicy {
        filter.addAction(BluetoothA2dp.ACTION_CONNECTION_STATE_CHANGED);
        filter.addAction(BluetoothDevice.ACTION_UUID);
        filter.addAction(BluetoothAdapter.ACTION_STATE_CHANGED);
        filter.addAction(BluetoothA2dp.ACTION_ACTIVE_DEVICE_CHANGED);
        mAdapterService.registerReceiver(mReceiver, filter);
    }

@@ -246,9 +260,9 @@ class PhonePolicy {
            panService.setPriority(device, BluetoothProfile.PRIORITY_ON);
        }

        if ((hearingAidService != null)
                && BluetoothUuid.isUuidPresent(uuids, BluetoothUuid.HearingAid)
                && (hearingAidService.getPriority(device) == BluetoothProfile.PRIORITY_UNDEFINED)) {
        if ((hearingAidService != null) && BluetoothUuid.isUuidPresent(uuids,
                BluetoothUuid.HearingAid) && (hearingAidService.getPriority(device)
                == BluetoothProfile.PRIORITY_UNDEFINED)) {
            debugLog("setting hearing aid profile priority for device " + device);
            hearingAidService.setPriority(device, BluetoothProfile.PRIORITY_ON);
        }
@@ -269,13 +283,46 @@ class PhonePolicy {
                        break;
                }
                connectOtherProfile(device);
                setProfileAutoConnectionPriority(device, profileId, true);
            }
            if (prevState == BluetoothProfile.STATE_CONNECTING
                    && nextState == BluetoothProfile.STATE_DISCONNECTED) {
                setProfileAutoConnectionPriority(device, profileId, false);
                HeadsetService hsService = mFactory.getHeadsetService();
                boolean hsDisconnected = hsService == null || hsService.getConnectionState(device)
                        == BluetoothProfile.STATE_DISCONNECTED;
                A2dpService a2dpService = mFactory.getA2dpService();
                boolean a2dpDisconnected = a2dpService == null
                        || a2dpService.getConnectionState(device)
                        == BluetoothProfile.STATE_DISCONNECTED;
                debugLog("processProfileStateChanged, device=" + device + ", a2dpDisconnected="
                        + a2dpDisconnected + ", hsDisconnected=" + hsDisconnected);
                if (hsDisconnected && a2dpDisconnected) {
                    removeAutoConnectFromA2dpSink(device);
                    removeAutoConnectFromHeadset(device);
                }
            }
        }
    }

    private void processProfileActiveDeviceChanged(BluetoothDevice activeDevice, int profileId) {
        debugLog("processProfileActiveDeviceChanged, activeDevice=" + activeDevice + ", profile="
                + profileId);
        switch (profileId) {
            // Tracking active device changed intent only for A2DP so that we always connect to a
            // single device after toggling Bluetooth
            case BluetoothProfile.A2DP:
                // Ignore null active device since we don't know if the change is triggered by
                // normal device disconnection during Bluetooth shutdown or user action
                if (activeDevice == null) {
                    warnLog("processProfileActiveDeviceChanged: ignore null A2DP active device");
                    return;
                }
                for (BluetoothDevice device : mAdapterService.getBondedDevices()) {
                    removeAutoConnectFromA2dpSink(device);
                    removeAutoConnectFromHeadset(device);
                }
                setAutoConnectForA2dpSink(activeDevice);
                setAutoConnectForHeadset(activeDevice);
                break;
        }
    }

@@ -286,68 +333,56 @@ class PhonePolicy {

    private void autoConnect() {
        if (mAdapterService.getState() != BluetoothAdapter.STATE_ON) {
            errorLog("autoConnect() - BT is not ON. Exiting autoConnect");
            errorLog("autoConnect: BT is not ON. Exiting autoConnect");
            return;
        }

        if (!mAdapterService.isQuietModeEnabled()) {
            debugLog("autoConnect() - Initiate auto connection on BT on...");
            // Phone profiles.
            autoConnectHeadset();
            autoConnectA2dp();
        } else {
            debugLog("autoConnect() - BT is in quiet mode. Not initiating auto connections");
        }
    }

    private void autoConnectHeadset() {
        final HeadsetService hsService = mFactory.getHeadsetService();
        if (hsService == null) {
            errorLog("autoConnectHeadset, service is null");
            return;
        }
            debugLog("autoConnect: Initiate auto connection on BT on...");
            final BluetoothDevice[] bondedDevices = mAdapterService.getBondedDevices();
            if (bondedDevices == null) {
            errorLog("autoConnectHeadset, bondedDevices are null");
                errorLog("autoConnect: bondedDevices are null");
                return;
            }
            for (BluetoothDevice device : bondedDevices) {
            int priority = hsService.getPriority(device);
            debugLog("autoConnectHeadset, attempt auto-connect with device " + device
                     + " priority " + priority);
            if (priority == BluetoothProfile.PRIORITY_AUTO_CONNECT) {
                debugLog("autoConnectHeadset, Connecting HFP with " + device);
                hsService.connect(device);
            } else {
                debugLog("autoConnectHeadset, skipped auto-connect with device " + device
                         + " priority " + priority);
                autoConnectHeadset(device);
                autoConnectA2dp(device);
            }
        } else {
            debugLog("autoConnect() - BT is in quiet mode. Not initiating auto connections");
        }
    }

    private void autoConnectA2dp() {
    private void autoConnectA2dp(BluetoothDevice device) {
        final A2dpService a2dpService = mFactory.getA2dpService();
        if (a2dpService == null) {
            errorLog("autoConnectA2dp, service is null");
            return;
        }
        final BluetoothDevice[] bondedDevices = mAdapterService.getBondedDevices();
        if (bondedDevices == null) {
            errorLog("autoConnectA2dp, bondedDevices are null");
            warnLog("autoConnectA2dp: service is null, failed to connect to " + device);
            return;
        }
        for (BluetoothDevice device : bondedDevices) {
            int priority = a2dpService.getPriority(device);
            debugLog("autoConnectA2dp, attempt auto-connect with device " + device
                     + " priority " + priority);
            if (priority == BluetoothProfile.PRIORITY_AUTO_CONNECT) {
                debugLog("autoConnectA2dp, connecting A2DP with " + device);
        int a2dpPriority = a2dpService.getPriority(device);
        if (a2dpPriority == BluetoothProfile.PRIORITY_AUTO_CONNECT) {
            debugLog("autoConnectA2dp: connecting A2DP with " + device);
            a2dpService.connect(device);
        } else {
                debugLog("autoConnectA2dp, skipped auto-connect with device " + device
                         + " priority " + priority);
            debugLog("autoConnectA2dp: skipped auto-connect A2DP with device " + device
                    + " priority " + a2dpPriority);
        }
    }

    private void autoConnectHeadset(BluetoothDevice device) {
        final HeadsetService hsService = mFactory.getHeadsetService();
        if (hsService == null) {
            warnLog("autoConnectHeadset: service is null, failed to connect to " + device);
            return;
        }
        int headsetPriority = hsService.getPriority(device);
        if (headsetPriority == BluetoothProfile.PRIORITY_AUTO_CONNECT) {
            debugLog("autoConnectHeadset: Connecting HFP with " + device);
            hsService.connect(device);
        } else {
            debugLog("autoConnectHeadset: skipped auto-connect HFP with device " + device
                    + " priority " + headsetPriority);
        }
    }

    private void connectOtherProfile(BluetoothDevice device) {
@@ -444,62 +479,74 @@ class PhonePolicy {
        }
    }

    private void setProfileAutoConnectionPriority(BluetoothDevice device, int profileId,
            boolean autoConnect) {
        debugLog("setProfileAutoConnectionPriority: device=" + device + ", profile=" + profileId
                + ", autoConnect=" + autoConnect);
        switch (profileId) {
            case BluetoothProfile.HEADSET: {
    /**
     * Set a device's headset profile priority to PRIORITY_AUTO_CONNECT if device support that
     * profile
     *
     * @param device device whose headset profile priority should be PRIORITY_AUTO_CONNECT
     */
    private void setAutoConnectForHeadset(BluetoothDevice device) {
        HeadsetService hsService = mFactory.getHeadsetService();
        if (hsService == null) {
                    warnLog("setProfileAutoConnectionPriority: HEADSET service is null");
                    break;
            warnLog("setAutoConnectForHeadset: HEADSET service is null");
            return;
        }
                removeAutoConnectFromDisconnectedHeadsets(hsService);
                if (autoConnect) {
        if (hsService.getPriority(device) >= BluetoothProfile.PRIORITY_ON) {
            debugLog("setAutoConnectForHeadset: device " + device + " PRIORITY_AUTO_CONNECT");
            hsService.setPriority(device, BluetoothProfile.PRIORITY_AUTO_CONNECT);
        }
                break;
    }
            case BluetoothProfile.A2DP: {

    /**
     * Set a device's A2DP profile priority to PRIORITY_AUTO_CONNECT if device support that profile
     *
     * @param device device whose headset profile priority should be PRIORITY_AUTO_CONNECT
     */
    private void setAutoConnectForA2dpSink(BluetoothDevice device) {
        A2dpService a2dpService = mFactory.getA2dpService();
        if (a2dpService == null) {
                    warnLog("setProfileAutoConnectionPriority: A2DP service is null");
                    break;
            warnLog("setAutoConnectForA2dpSink: A2DP service is null");
            return;
        }
                removeAutoConnectFromDisconnectedA2dpSinks(a2dpService);
                if (autoConnect) {
        if (a2dpService.getPriority(device) >= BluetoothProfile.PRIORITY_ON) {
            debugLog("setAutoConnectForA2dpSink: device " + device + " PRIORITY_AUTO_CONNECT");
            a2dpService.setPriority(device, BluetoothProfile.PRIORITY_AUTO_CONNECT);
        }
                break;
            }
            default:
                Log.w(TAG, "Tried to set AutoConnect priority on invalid profile " + profileId);
                break;
        }
    }

    private void removeAutoConnectFromDisconnectedHeadsets(HeadsetService hsService) {
        List<BluetoothDevice> connectedDeviceList = hsService.getConnectedDevices();
        for (BluetoothDevice device : mAdapterService.getBondedDevices()) {
            if (hsService.getPriority(device) >= BluetoothProfile.PRIORITY_AUTO_CONNECT
                    && !connectedDeviceList.contains(device)) {
                debugLog("removeAutoConnectFromDisconnectedHeadsets, device " + device
                        + " PRIORITY_ON");
                hsService.setPriority(device, BluetoothProfile.PRIORITY_ON);
    /**
     * Remove PRIORITY_AUTO_CONNECT from all headsets and set headset that used to have
     * PRIORITY_AUTO_CONNECT to PRIORITY_ON
     *
     * @param device device whose PRIORITY_AUTO_CONNECT priority should be removed
     */
    private void removeAutoConnectFromHeadset(BluetoothDevice device) {
        HeadsetService hsService = mFactory.getHeadsetService();
        if (hsService == null) {
            warnLog("removeAutoConnectFromHeadset: HEADSET service is null");
            return;
        }
        if (hsService.getPriority(device) >= BluetoothProfile.PRIORITY_AUTO_CONNECT) {
            debugLog("removeAutoConnectFromHeadset: device " + device + " PRIORITY_ON");
            hsService.setPriority(device, BluetoothProfile.PRIORITY_ON);
        }
    }

    private void removeAutoConnectFromDisconnectedA2dpSinks(A2dpService a2dpService) {
        List<BluetoothDevice> connectedDeviceList = a2dpService.getConnectedDevices();
        for (BluetoothDevice device : mAdapterService.getBondedDevices()) {
            if (a2dpService.getPriority(device) >= BluetoothProfile.PRIORITY_AUTO_CONNECT
                    && !connectedDeviceList.contains(device)) {
                debugLog("removeAutoConnectFromDisconnectedA2dpSinks, device " + device
                        + " PRIORITY_ON");
                a2dpService.setPriority(device, BluetoothProfile.PRIORITY_ON);
    /**
     * Remove PRIORITY_AUTO_CONNECT from all A2DP sinks and set A2DP sink that used to have
     * PRIORITY_AUTO_CONNECT to PRIORITY_ON
     *
     * @param device device whose PRIORITY_AUTO_CONNECT priority should be removed
     */
    private void removeAutoConnectFromA2dpSink(BluetoothDevice device) {
        A2dpService a2dpService = mFactory.getA2dpService();
        if (a2dpService == null) {
            warnLog("removeAutoConnectFromA2dpSink: A2DP service is null");
            return;
        }
        if (a2dpService.getPriority(device) >= BluetoothProfile.PRIORITY_AUTO_CONNECT) {
            debugLog("removeAutoConnectFromA2dpSink: device " + device + " PRIORITY_ON");
            a2dpService.setPriority(device, BluetoothProfile.PRIORITY_ON);
        }
    }

+40 −37

File changed.

Preview size limit exceeded, changes collapsed.