BatteryManager.java revision 928167e04475d45413bef579b6b03c6c3eca591f
1/*
2 * Copyright (C) 2008 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
17package android.os;
18
19import android.annotation.SystemApi;
20import android.annotation.SystemService;
21import android.content.Context;
22import android.content.Intent;
23import android.hardware.health.V1_0.Constants;
24
25import com.android.internal.app.IBatteryStats;
26
27/**
28 * The BatteryManager class contains strings and constants used for values
29 * in the {@link android.content.Intent#ACTION_BATTERY_CHANGED} Intent, and
30 * provides a method for querying battery and charging properties.
31 */
32@SystemService(Context.BATTERY_SERVICE)
33public class BatteryManager {
34    /**
35     * Extra for {@link android.content.Intent#ACTION_BATTERY_CHANGED}:
36     * integer containing the current status constant.
37     */
38    public static final String EXTRA_STATUS = "status";
39
40    /**
41     * Extra for {@link android.content.Intent#ACTION_BATTERY_CHANGED}:
42     * integer containing the current health constant.
43     */
44    public static final String EXTRA_HEALTH = "health";
45
46    /**
47     * Extra for {@link android.content.Intent#ACTION_BATTERY_CHANGED}:
48     * boolean indicating whether a battery is present.
49     */
50    public static final String EXTRA_PRESENT = "present";
51
52    /**
53     * Extra for {@link android.content.Intent#ACTION_BATTERY_CHANGED}:
54     * integer field containing the current battery level, from 0 to
55     * {@link #EXTRA_SCALE}.
56     */
57    public static final String EXTRA_LEVEL = "level";
58
59    /**
60     * Extra for {@link android.content.Intent#ACTION_BATTERY_CHANGED}:
61     * Boolean field indicating whether the battery is currently considered to be
62     * low, that is whether a {@link Intent#ACTION_BATTERY_LOW} broadcast
63     * has been sent.
64     */
65    public static final String EXTRA_BATTERY_LOW = "battery_low";
66
67    /**
68     * Extra for {@link android.content.Intent#ACTION_BATTERY_CHANGED}:
69     * integer containing the maximum battery level.
70     */
71    public static final String EXTRA_SCALE = "scale";
72
73    /**
74     * Extra for {@link android.content.Intent#ACTION_BATTERY_CHANGED}:
75     * integer containing the resource ID of a small status bar icon
76     * indicating the current battery state.
77     */
78    public static final String EXTRA_ICON_SMALL = "icon-small";
79
80    /**
81     * Extra for {@link android.content.Intent#ACTION_BATTERY_CHANGED}:
82     * integer indicating whether the device is plugged in to a power
83     * source; 0 means it is on battery, other constants are different
84     * types of power sources.
85     */
86    public static final String EXTRA_PLUGGED = "plugged";
87
88    /**
89     * Extra for {@link android.content.Intent#ACTION_BATTERY_CHANGED}:
90     * integer containing the current battery voltage level.
91     */
92    public static final String EXTRA_VOLTAGE = "voltage";
93
94    /**
95     * Extra for {@link android.content.Intent#ACTION_BATTERY_CHANGED}:
96     * integer containing the current battery temperature.
97     */
98    public static final String EXTRA_TEMPERATURE = "temperature";
99
100    /**
101     * Extra for {@link android.content.Intent#ACTION_BATTERY_CHANGED}:
102     * String describing the technology of the current battery.
103     */
104    public static final String EXTRA_TECHNOLOGY = "technology";
105
106    /**
107     * Extra for {@link android.content.Intent#ACTION_BATTERY_CHANGED}:
108     * Int value set to nonzero if an unsupported charger is attached
109     * to the device.
110     * {@hide}
111     */
112    public static final String EXTRA_INVALID_CHARGER = "invalid_charger";
113
114    /**
115     * Extra for {@link android.content.Intent#ACTION_BATTERY_CHANGED}:
116     * Int value set to the maximum charging current supported by the charger in micro amperes.
117     * {@hide}
118     */
119    public static final String EXTRA_MAX_CHARGING_CURRENT = "max_charging_current";
120
121    /**
122     * Extra for {@link android.content.Intent#ACTION_BATTERY_CHANGED}:
123     * Int value set to the maximum charging voltage supported by the charger in micro volts.
124     * {@hide}
125     */
126    public static final String EXTRA_MAX_CHARGING_VOLTAGE = "max_charging_voltage";
127
128    /**
129     * Extra for {@link android.content.Intent#ACTION_BATTERY_CHANGED}:
130     * integer containing the charge counter present in the battery.
131     * {@hide}
132     */
133     public static final String EXTRA_CHARGE_COUNTER = "charge_counter";
134
135    /**
136     * Extra for {@link android.content.Intent#ACTION_BATTERY_CHANGED}:
137     * Current int sequence number of the update.
138     * {@hide}
139     */
140    public static final String EXTRA_SEQUENCE = "seq";
141
142    /**
143     * Extra for {@link android.content.Intent#ACTION_BATTERY_LEVEL_CHANGED}:
144     * Contains list of Bundles representing battery events
145     * @hide
146     */
147    @SystemApi
148    public static final String EXTRA_EVENTS = "android.os.extra.EVENTS";
149
150    /**
151     * Extra for event in {@link android.content.Intent#ACTION_BATTERY_LEVEL_CHANGED}:
152     * Long value representing time when event occurred as returned by
153     * {@link android.os.SystemClock#elapsedRealtime()}
154     * @hide
155     */
156    @SystemApi
157    public static final String EXTRA_EVENT_TIMESTAMP = "android.os.extra.EVENT_TIMESTAMP";
158
159    // values for "status" field in the ACTION_BATTERY_CHANGED Intent
160    public static final int BATTERY_STATUS_UNKNOWN = Constants.BATTERY_STATUS_UNKNOWN;
161    public static final int BATTERY_STATUS_CHARGING = Constants.BATTERY_STATUS_CHARGING;
162    public static final int BATTERY_STATUS_DISCHARGING = Constants.BATTERY_STATUS_DISCHARGING;
163    public static final int BATTERY_STATUS_NOT_CHARGING = Constants.BATTERY_STATUS_NOT_CHARGING;
164    public static final int BATTERY_STATUS_FULL = Constants.BATTERY_STATUS_FULL;
165
166    // values for "health" field in the ACTION_BATTERY_CHANGED Intent
167    public static final int BATTERY_HEALTH_UNKNOWN = Constants.BATTERY_HEALTH_UNKNOWN;
168    public static final int BATTERY_HEALTH_GOOD = Constants.BATTERY_HEALTH_GOOD;
169    public static final int BATTERY_HEALTH_OVERHEAT = Constants.BATTERY_HEALTH_OVERHEAT;
170    public static final int BATTERY_HEALTH_DEAD = Constants.BATTERY_HEALTH_DEAD;
171    public static final int BATTERY_HEALTH_OVER_VOLTAGE = Constants.BATTERY_HEALTH_OVER_VOLTAGE;
172    public static final int BATTERY_HEALTH_UNSPECIFIED_FAILURE = Constants.BATTERY_HEALTH_UNSPECIFIED_FAILURE;
173    public static final int BATTERY_HEALTH_COLD = Constants.BATTERY_HEALTH_COLD;
174
175    // values of the "plugged" field in the ACTION_BATTERY_CHANGED intent.
176    // These must be powers of 2.
177    /** Power source is an AC charger. */
178    public static final int BATTERY_PLUGGED_AC = OsProtoEnums.BATTERY_PLUGGED_AC; // = 1
179    /** Power source is a USB port. */
180    public static final int BATTERY_PLUGGED_USB = OsProtoEnums.BATTERY_PLUGGED_USB; // = 2
181    /** Power source is wireless. */
182    public static final int BATTERY_PLUGGED_WIRELESS = OsProtoEnums.BATTERY_PLUGGED_WIRELESS; // = 4
183
184    /** @hide */
185    public static final int BATTERY_PLUGGED_ANY =
186            BATTERY_PLUGGED_AC | BATTERY_PLUGGED_USB | BATTERY_PLUGGED_WIRELESS;
187
188    /**
189     * Sent when the device's battery has started charging (or has reached full charge
190     * and the device is on power).  This is a good time to do work that you would like to
191     * avoid doing while on battery (that is to avoid draining the user's battery due to
192     * things they don't care enough about).
193     *
194     * This is paired with {@link #ACTION_DISCHARGING}.  The current state can always
195     * be retrieved with {@link #isCharging()}.
196     */
197    public static final String ACTION_CHARGING = "android.os.action.CHARGING";
198
199    /**
200     * Sent when the device's battery may be discharging, so apps should avoid doing
201     * extraneous work that would cause it to discharge faster.
202     *
203     * This is paired with {@link #ACTION_CHARGING}.  The current state can always
204     * be retrieved with {@link #isCharging()}.
205     */
206    public static final String ACTION_DISCHARGING = "android.os.action.DISCHARGING";
207
208    /*
209     * Battery property identifiers.  These must match the values in
210     * frameworks/native/include/batteryservice/BatteryService.h
211     */
212    /** Battery capacity in microampere-hours, as an integer. */
213    public static final int BATTERY_PROPERTY_CHARGE_COUNTER = 1;
214
215    /**
216     * Instantaneous battery current in microamperes, as an integer.  Positive
217     * values indicate net current entering the battery from a charge source,
218     * negative values indicate net current discharging from the battery.
219     */
220    public static final int BATTERY_PROPERTY_CURRENT_NOW = 2;
221
222    /**
223     * Average battery current in microamperes, as an integer.  Positive
224     * values indicate net current entering the battery from a charge source,
225     * negative values indicate net current discharging from the battery.
226     * The time period over which the average is computed may depend on the
227     * fuel gauge hardware and its configuration.
228     */
229    public static final int BATTERY_PROPERTY_CURRENT_AVERAGE = 3;
230
231    /**
232     * Remaining battery capacity as an integer percentage of total capacity
233     * (with no fractional part).
234     */
235    public static final int BATTERY_PROPERTY_CAPACITY = 4;
236
237    /**
238     * Battery remaining energy in nanowatt-hours, as a long integer.
239     */
240    public static final int BATTERY_PROPERTY_ENERGY_COUNTER = 5;
241
242    /**
243     * Battery charge status, from a BATTERY_STATUS_* value.
244     */
245    public static final int BATTERY_PROPERTY_STATUS = 6;
246
247    private final Context mContext;
248    private final IBatteryStats mBatteryStats;
249    private final IBatteryPropertiesRegistrar mBatteryPropertiesRegistrar;
250
251    /**
252     * @removed Was previously made visible by accident.
253     */
254    public BatteryManager() {
255        mContext = null;
256        mBatteryStats = IBatteryStats.Stub.asInterface(
257                ServiceManager.getService(BatteryStats.SERVICE_NAME));
258        mBatteryPropertiesRegistrar = IBatteryPropertiesRegistrar.Stub.asInterface(
259                ServiceManager.getService("batteryproperties"));
260    }
261
262    /** {@hide} */
263    public BatteryManager(Context context,
264            IBatteryStats batteryStats,
265            IBatteryPropertiesRegistrar batteryPropertiesRegistrar) {
266        mContext = context;
267        mBatteryStats = batteryStats;
268        mBatteryPropertiesRegistrar = batteryPropertiesRegistrar;
269    }
270
271    /**
272     * Return true if the battery is currently considered to be charging.  This means that
273     * the device is plugged in and is supplying sufficient power that the battery level is
274     * going up (or the battery is fully charged).  Changes in this state are matched by
275     * broadcasts of {@link #ACTION_CHARGING} and {@link #ACTION_DISCHARGING}.
276     */
277    public boolean isCharging() {
278        try {
279            return mBatteryStats.isCharging();
280        } catch (RemoteException e) {
281            throw e.rethrowFromSystemServer();
282        }
283    }
284
285    /**
286     * Query a battery property from the batteryproperties service.
287     *
288     * Returns the requested value, or Long.MIN_VALUE if property not
289     * supported on this system or on other error.
290     */
291    private long queryProperty(int id) {
292        long ret;
293
294        if (mBatteryPropertiesRegistrar == null) {
295            return Long.MIN_VALUE;
296        }
297
298        try {
299            BatteryProperty prop = new BatteryProperty();
300
301            if (mBatteryPropertiesRegistrar.getProperty(id, prop) == 0)
302                ret = prop.getLong();
303            else
304                ret = Long.MIN_VALUE;
305        } catch (RemoteException e) {
306            throw e.rethrowFromSystemServer();
307        }
308
309        return ret;
310    }
311
312    /**
313     * Return the value of a battery property of integer type.
314     *
315     * @param id identifier of the requested property
316     *
317     * @return the property value. If the property is not supported or there is any other error,
318     *    return (a) 0 if {@code targetSdkVersion < VERSION_CODES.P} or (b) Integer.MIN_VALUE
319     *    if {@code targetSdkVersion >= VERSION_CODES.P}.
320     */
321    public int getIntProperty(int id) {
322        long value = queryProperty(id);
323        if (value == Long.MIN_VALUE && mContext != null
324                && mContext.getApplicationInfo().targetSdkVersion
325                    >= android.os.Build.VERSION_CODES.P) {
326            return Integer.MIN_VALUE;
327        }
328
329        return (int) value;
330    }
331
332    /**
333     * Return the value of a battery property of long type If the
334     * platform does not provide the property queried, this value will
335     * be Long.MIN_VALUE.
336     *
337     * @param id identifier of the requested property
338     *
339     * @return the property value, or Long.MIN_VALUE if not supported.
340     */
341    public long getLongProperty(int id) {
342        return queryProperty(id);
343    }
344
345    /**
346     * Return true if the plugType given is wired
347     * @param plugType {@link #BATTERY_PLUGGED_AC}, {@link #BATTERY_PLUGGED_USB},
348     *        or {@link #BATTERY_PLUGGED_WIRELESS}
349     *
350     * @return true if plugType is wired
351     * @hide
352     */
353    public static boolean isPlugWired(int plugType) {
354        return plugType == BATTERY_PLUGGED_USB || plugType == BATTERY_PLUGGED_AC;
355    }
356
357    /**
358     * Compute an approximation for how much time (in milliseconds) remains until the battery is
359     * fully charged. Returns -1 if no time can be computed: either there is not enough current
360     * data to make a decision or the battery is currently discharging.
361     *
362     * @return how much time is left, in milliseconds, until the battery is fully charged or -1 if
363     *         the computation fails
364     */
365    public long computeChargeTimeRemaining() {
366        try {
367            return mBatteryStats.computeChargeTimeRemaining();
368        } catch (RemoteException e) {
369            throw e.rethrowFromSystemServer();
370        }
371    }
372}
373