From: Po Lu Date: Fri, 10 Mar 2023 01:40:41 +0000 (+0800) Subject: Port Android battery status to Android 4.4 and earlier X-Git-Url: http://git.eshelyaron.com/gitweb/?a=commitdiff_plain;h=488a75f2e2b73038ff341f3484a8cf8584633eff;p=emacs.git Port Android battery status to Android 4.4 and earlier * java/org/gnu/emacs/EmacsService.java (EmacsService) (queryBattery19): New function. (queryBattery): Call it on old systems. Also, return AC line status and temperature. * lisp/battery.el (battery-android): Implement more format directives. * src/android.c (android_query_battery): Handle new status fields. * src/android.h (struct android_battery_state): Add `plugged' and `temperature'. * src/androidfns.c (Fandroid_query_battery): Return new fields. --- diff --git a/java/org/gnu/emacs/EmacsService.java b/java/org/gnu/emacs/EmacsService.java index 848ad4de789..9c48c56ca26 100644 --- a/java/org/gnu/emacs/EmacsService.java +++ b/java/org/gnu/emacs/EmacsService.java @@ -40,6 +40,7 @@ import android.content.ClipboardManager; import android.content.Context; import android.content.ContentResolver; import android.content.Intent; +import android.content.IntentFilter; import android.content.pm.ApplicationInfo; import android.content.pm.PackageManager.ApplicationInfoFlags; import android.content.pm.PackageManager; @@ -738,6 +739,36 @@ public final class EmacsService extends Service } } + private long[] + queryBattery19 () + { + IntentFilter filter; + Intent battery; + long capacity, chargeCounter, currentAvg, currentNow; + long status, remaining, plugged, temp; + + filter = new IntentFilter (Intent.ACTION_BATTERY_CHANGED); + battery = registerReceiver (null, filter); + + if (battery == null) + return null; + + capacity = battery.getIntExtra (BatteryManager.EXTRA_LEVEL, 0); + chargeCounter + = (battery.getIntExtra (BatteryManager.EXTRA_SCALE, 0) + / battery.getIntExtra (BatteryManager.EXTRA_LEVEL, 100) * 100); + currentAvg = 0; + currentNow = 0; + status = battery.getIntExtra (BatteryManager.EXTRA_STATUS, 0); + remaining = -1; + plugged = battery.getIntExtra (BatteryManager.EXTRA_PLUGGED, 0); + temp = battery.getIntExtra (BatteryManager.EXTRA_TEMPERATURE, 0); + + return new long[] { capacity, chargeCounter, currentAvg, + currentNow, remaining, status, plugged, + temp, }; + } + /* Return the status of the battery. See struct android_battery_status for the order of the elements returned. @@ -750,14 +781,16 @@ public final class EmacsService extends Service Object tem; BatteryManager manager; long capacity, chargeCounter, currentAvg, currentNow; - long status, remaining; + long status, remaining, plugged, temp; int prop; + IntentFilter filter; + Intent battery; - /* Android 4.4 or earlier require applications to listen to - changes to the battery instead of querying for its status. */ + /* Android 4.4 or earlier require applications to use a different + API to query the battery status. */ if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) - return null; + return queryBattery19 (); tem = getSystemService (Context.BATTERY_SERVICE); manager = (BatteryManager) tem; @@ -776,7 +809,8 @@ public final class EmacsService extends Service only return ``charging'' or ``discharging''. */ if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) - status = manager.getIntProperty (BatteryManager.BATTERY_PROPERTY_STATUS); + status + = manager.getIntProperty (BatteryManager.BATTERY_PROPERTY_STATUS); else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) status = (manager.isCharging () ? BatteryManager.BATTERY_STATUS_CHARGING @@ -789,8 +823,27 @@ public final class EmacsService extends Service if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) remaining = manager.computeChargeTimeRemaining (); + plugged = -1; + temp = -1; + + /* Now obtain additional information from the battery manager. */ + + filter = new IntentFilter (Intent.ACTION_BATTERY_CHANGED); + battery = registerReceiver (null, filter); + + if (battery != null) + { + plugged = battery.getIntExtra (BatteryManager.EXTRA_PLUGGED, 0); + temp = battery.getIntExtra (BatteryManager.EXTRA_TEMPERATURE, 0); + + /* Make status more reliable. */ + if (Build.VERSION.SDK_INT < Build.VERSION_CODES.M) + status = battery.getIntExtra (BatteryManager.EXTRA_STATUS, 0); + } + return new long[] { capacity, chargeCounter, currentAvg, - currentNow, remaining, status, }; + currentNow, remaining, status, plugged, + temp, }; } /* Display the specified STRING in a small dialog box on the main diff --git a/lisp/battery.el b/lisp/battery.el index a2bbd463c12..a51bc5267b3 100644 --- a/lisp/battery.el +++ b/lisp/battery.el @@ -1089,9 +1089,11 @@ The following %-sequences are provided: The following %-sequences are provided: %c Current capacity (mAh) %r Current rate of charge or discharge (mA) +%L AC line status (verbose). %B Battery status (verbose) %b Battery status, empty means high, `-' means low, `+' means charging and `?' means unknown. +%d Temperature (in degrees Celsius) %p Battery load percentage. %m Remaining time (to charge) in minutes. %h Remaining time (to charge) in hours. @@ -1139,7 +1141,14 @@ The following %-sequences are provided: (cons ?m (or minutes "N/A")) (cons ?h (or hours "N/A")) (cons ?t (or remaining "N/A")) - (cons ?L "N/A"))))) + (cons ?L (cl-case (nth 6 status) + (0 "off-line") + (1 "on-line") + (2 "on-line (dock)") + (3 "on-line (USB)") + (4 "on-line (wireless)") + (t "unknown"))) + (cons ?t (/ (or (nth 7 status) 0) 10.0)))))) ;;; Private functions. diff --git a/src/android.c b/src/android.c index 69c87e731bd..763e17e9430 100644 --- a/src/android.c +++ b/src/android.c @@ -5754,7 +5754,7 @@ android_get_current_api_level (void) } /* Query the status of the battery, and place it in *STATUS. - Value is 1 if the system is too old, else 0. */ + Value is 1 upon failure, else 0. */ int android_query_battery (struct android_battery_state *status) @@ -5783,6 +5783,8 @@ android_query_battery (struct android_battery_state *status) status->current_now = longs[3]; status->remaining = longs[4]; status->status = longs[5]; + status->plugged = longs[6]; + status->temperature = longs[7]; (*android_java_env)->ReleaseLongArrayElements (android_java_env, array, longs, diff --git a/src/android.h b/src/android.h index ed0089ad94e..450f3859df9 100644 --- a/src/android.h +++ b/src/android.h @@ -160,6 +160,18 @@ struct android_battery_state but is not charging either. 1, if the battery state is unknown. */ int status; + + /* The power source of the battery. Value is: + + 0, if on battery power. + 1, for line power. + 8, for dock power. + 2, for USB power. + 4, for wireless power. */ + int plugged; + + /* The temperature of the battery in 10 * degrees centigrade. */ + int temperature; }; extern Lisp_Object android_browse_url (Lisp_Object); diff --git a/src/androidfns.c b/src/androidfns.c index 5a23e8bd196..2724b9595c1 100644 --- a/src/androidfns.c +++ b/src/androidfns.c @@ -2797,11 +2797,13 @@ frame_parm_handler android_frame_parm_handlers[] = DEFUN ("android-query-battery", Fandroid_query_battery, Sandroid_query_battery, 0, 0, 0, doc: /* Perform a query for battery information. -This function will not work before Android 5.0. Value is nil upon failure, or a list of the form: (CAPACITY CHARGE-COUNTER CURRENT-AVERAGE CURRENT-NOW STATUS - REMAINING) + REMAINING PLUGGED TEMP) + +where REMAINING, CURRENT-AVERAGE, and CURRENT-NOW are undefined prior +to Android 5.0. See the documentation at @@ -2822,12 +2824,14 @@ for more details about these values. */) if (android_query_battery (&state)) return Qnil; - return listn (6, make_int (state.capacity), - make_int (state.charge_counter), + return listn (8, make_int (state.capacity), + make_fixnum (state.charge_counter), make_int (state.current_average), make_int (state.current_now), - make_int (state.status), - make_int (state.remaining)); + make_fixnum (state.status), + make_int (state.remaining), + make_fixnum (state.plugged), + make_fixnum (state.temperature)); } #endif