1 /* 2 * Copyright (C) 2014 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package android.telecom; 18 19 import android.os.Parcel; 20 import android.os.Parcelable; 21 22 import java.util.Locale; 23 24 /** 25 * Encapsulates the telecom audio state, including the current audio routing, supported audio 26 * routing and mute. 27 */ 28 public final class CallAudioState implements Parcelable { 29 /** Direct the audio stream through the device's earpiece. */ 30 public static final int ROUTE_EARPIECE = 0x00000001; 31 32 /** Direct the audio stream through Bluetooth. */ 33 public static final int ROUTE_BLUETOOTH = 0x00000002; 34 35 /** Direct the audio stream through a wired headset. */ 36 public static final int ROUTE_WIRED_HEADSET = 0x00000004; 37 38 /** Direct the audio stream through the device's speakerphone. */ 39 public static final int ROUTE_SPEAKER = 0x00000008; 40 41 /** 42 * Direct the audio stream through the device's earpiece or wired headset if one is 43 * connected. 44 */ 45 public static final int ROUTE_WIRED_OR_EARPIECE = ROUTE_EARPIECE | ROUTE_WIRED_HEADSET; 46 47 /** Bit mask of all possible audio routes. */ 48 private static final int ROUTE_ALL = ROUTE_EARPIECE | ROUTE_BLUETOOTH | ROUTE_WIRED_HEADSET | 49 ROUTE_SPEAKER; 50 51 private final boolean isMuted; 52 private final int route; 53 private final int supportedRouteMask; 54 55 /** 56 * Constructor for a {@link CallAudioState} object. 57 * 58 * @param muted {@code true} if the call is muted, {@code false} otherwise. 59 * @param route The current audio route being used. 60 * Allowed values: 61 * {@link #ROUTE_EARPIECE} 62 * {@link #ROUTE_BLUETOOTH} 63 * {@link #ROUTE_WIRED_HEADSET} 64 * {@link #ROUTE_SPEAKER} 65 * @param supportedRouteMask Bit mask of all routes supported by this call. This should be a 66 * bitwise combination of the following values: 67 * {@link #ROUTE_EARPIECE} 68 * {@link #ROUTE_BLUETOOTH} 69 * {@link #ROUTE_WIRED_HEADSET} 70 * {@link #ROUTE_SPEAKER} 71 */ 72 public CallAudioState(boolean muted, int route, int supportedRouteMask) { 73 this.isMuted = muted; 74 this.route = route; 75 this.supportedRouteMask = supportedRouteMask; 76 } 77 78 /** @hide */ 79 public CallAudioState(CallAudioState state) { 80 isMuted = state.isMuted(); 81 route = state.getRoute(); 82 supportedRouteMask = state.getSupportedRouteMask(); 83 } 84 85 /** @hide */ 86 @SuppressWarnings("deprecation") 87 public CallAudioState(AudioState state) { 88 isMuted = state.isMuted(); 89 route = state.getRoute(); 90 supportedRouteMask = state.getSupportedRouteMask(); 91 } 92 93 @Override 94 public boolean equals(Object obj) { 95 if (obj == null) { 96 return false; 97 } 98 if (!(obj instanceof CallAudioState)) { 99 return false; 100 } 101 CallAudioState state = (CallAudioState) obj; 102 return isMuted() == state.isMuted() && getRoute() == state.getRoute() && 103 getSupportedRouteMask() == state.getSupportedRouteMask(); 104 } 105 106 @Override 107 public String toString() { 108 return String.format(Locale.US, 109 "[AudioState isMuted: %b, route: %s, supportedRouteMask: %s]", 110 isMuted, 111 audioRouteToString(route), 112 audioRouteToString(supportedRouteMask)); 113 } 114 115 /** 116 * @return {@code true} if the call is muted, {@code false} otherwise. 117 */ 118 public boolean isMuted() { 119 return isMuted; 120 } 121 122 /** 123 * @return The current audio route being used. 124 */ 125 public int getRoute() { 126 return route; 127 } 128 129 /** 130 * @return Bit mask of all routes supported by this call. 131 */ 132 public int getSupportedRouteMask() { 133 return supportedRouteMask; 134 } 135 136 /** 137 * Converts the provided audio route into a human readable string representation. 138 * 139 * @param route to convert into a string. 140 * 141 * @return String representation of the provided audio route. 142 */ 143 public static String audioRouteToString(int route) { 144 if (route == 0 || (route & ~ROUTE_ALL) != 0x0) { 145 return "UNKNOWN"; 146 } 147 148 StringBuffer buffer = new StringBuffer(); 149 if ((route & ROUTE_EARPIECE) == ROUTE_EARPIECE) { 150 listAppend(buffer, "EARPIECE"); 151 } 152 if ((route & ROUTE_BLUETOOTH) == ROUTE_BLUETOOTH) { 153 listAppend(buffer, "BLUETOOTH"); 154 } 155 if ((route & ROUTE_WIRED_HEADSET) == ROUTE_WIRED_HEADSET) { 156 listAppend(buffer, "WIRED_HEADSET"); 157 } 158 if ((route & ROUTE_SPEAKER) == ROUTE_SPEAKER) { 159 listAppend(buffer, "SPEAKER"); 160 } 161 162 return buffer.toString(); 163 } 164 165 /** 166 * Responsible for creating AudioState objects for deserialized Parcels. 167 */ 168 public static final Parcelable.Creator<CallAudioState> CREATOR = 169 new Parcelable.Creator<CallAudioState> () { 170 171 @Override 172 public CallAudioState createFromParcel(Parcel source) { 173 boolean isMuted = source.readByte() == 0 ? false : true; 174 int route = source.readInt(); 175 int supportedRouteMask = source.readInt(); 176 return new CallAudioState(isMuted, route, supportedRouteMask); 177 } 178 179 @Override 180 public CallAudioState[] newArray(int size) { 181 return new CallAudioState[size]; 182 } 183 }; 184 185 /** 186 * {@inheritDoc} 187 */ 188 @Override 189 public int describeContents() { 190 return 0; 191 } 192 193 /** 194 * Writes AudioState object into a serializeable Parcel. 195 */ 196 @Override 197 public void writeToParcel(Parcel destination, int flags) { 198 destination.writeByte((byte) (isMuted ? 1 : 0)); 199 destination.writeInt(route); 200 destination.writeInt(supportedRouteMask); 201 } 202 203 private static void listAppend(StringBuffer buffer, String str) { 204 if (buffer.length() > 0) { 205 buffer.append(", "); 206 } 207 buffer.append(str); 208 } 209 } 210