DisplayEventDispatcher: add DISPLAY_EVENT_CONFIG_CHANGED
Add a new event for display configuration change. This event
will be sent by SF anytime it changes the display config.
Test: Generate DISPLAY_EVENT_CONFIG_CHANGED and observe the log
Bug: 122905403
Change-Id: Ifa473a34d7b313501e5e4e8a67186fb82754fdcd
diff --git a/core/java/android/view/DisplayEventReceiver.java b/core/java/android/view/DisplayEventReceiver.java
index 3e8002f..60daddd 100644
--- a/core/java/android/view/DisplayEventReceiver.java
+++ b/core/java/android/view/DisplayEventReceiver.java
@@ -156,6 +156,17 @@
}
/**
+ * Called when a display config changed event is received.
+ *
+ * @param timestampNanos The timestamp of the event, in the {@link System#nanoTime()}
+ * timebase.
+ * @param physicalDisplayId Stable display ID that uniquely describes a (display, port) pair.
+ * @param configId The new config Id
+ */
+ public void onConfigChanged(long timestampNanos, long physicalDisplayId, int configId) {
+ }
+
+ /**
* Schedules a single vertical sync pulse to be delivered when the next
* display frame begins.
*/
@@ -182,4 +193,11 @@
private void dispatchHotplug(long timestampNanos, long physicalDisplayId, boolean connected) {
onHotplug(timestampNanos, physicalDisplayId, connected);
}
+
+ // Called from native code.
+ @SuppressWarnings("unused")
+ private void dispatchConfigChanged(long timestampNanos, long physicalDisplayId, int configId) {
+ onConfigChanged(timestampNanos, physicalDisplayId, configId);
+ }
+
}
diff --git a/core/jni/android_view_DisplayEventReceiver.cpp b/core/jni/android_view_DisplayEventReceiver.cpp
index 191472d..8d702d1 100644
--- a/core/jni/android_view_DisplayEventReceiver.cpp
+++ b/core/jni/android_view_DisplayEventReceiver.cpp
@@ -41,6 +41,7 @@
jmethodID dispatchVsync;
jmethodID dispatchHotplug;
+ jmethodID dispatchConfigChanged;
} gDisplayEventReceiverClassInfo;
@@ -61,6 +62,8 @@
void dispatchVsync(nsecs_t timestamp, PhysicalDisplayId displayId, uint32_t count) override;
void dispatchHotplug(nsecs_t timestamp, PhysicalDisplayId displayId, bool connected) override;
+ void dispatchConfigChanged(nsecs_t timestamp, PhysicalDisplayId displayId,
+ int32_t configId) override;
};
@@ -114,6 +117,23 @@
mMessageQueue->raiseAndClearException(env, "dispatchHotplug");
}
+void NativeDisplayEventReceiver::dispatchConfigChanged(nsecs_t timestamp,
+ PhysicalDisplayId displayId,
+ int32_t configId) {
+ JNIEnv* env = AndroidRuntime::getJNIEnv();
+
+ ScopedLocalRef<jobject> receiverObj(env, jniGetReferent(env, mReceiverWeakGlobal));
+ if (receiverObj.get()) {
+ ALOGV("receiver %p ~ Invoking config changed handler.", this);
+ env->CallVoidMethod(receiverObj.get(),
+ gDisplayEventReceiverClassInfo.dispatchConfigChanged,
+ timestamp, displayId, configId);
+ ALOGV("receiver %p ~ Returned from config changed handler.", this);
+ }
+
+ mMessageQueue->raiseAndClearException(env, "dispatchConfigChanged");
+}
+
static jlong nativeInit(JNIEnv* env, jclass clazz, jobject receiverWeak,
jobject messageQueueObj, jint vsyncSource) {
@@ -180,6 +200,8 @@
gDisplayEventReceiverClassInfo.clazz, "dispatchVsync", "(JJI)V");
gDisplayEventReceiverClassInfo.dispatchHotplug = GetMethodIDOrDie(env,
gDisplayEventReceiverClassInfo.clazz, "dispatchHotplug", "(JJZ)V");
+ gDisplayEventReceiverClassInfo.dispatchConfigChanged = GetMethodIDOrDie(env,
+ gDisplayEventReceiverClassInfo.clazz, "dispatchConfigChanged", "(JJI)V");
return res;
}
diff --git a/libs/androidfw/DisplayEventDispatcher.cpp b/libs/androidfw/DisplayEventDispatcher.cpp
index 3b9a348..6606148 100644
--- a/libs/androidfw/DisplayEventDispatcher.cpp
+++ b/libs/androidfw/DisplayEventDispatcher.cpp
@@ -135,6 +135,9 @@
case DisplayEventReceiver::DISPLAY_EVENT_HOTPLUG:
dispatchHotplug(ev.header.timestamp, ev.header.displayId, ev.hotplug.connected);
break;
+ case DisplayEventReceiver::DISPLAY_EVENT_CONFIG_CHANGED:
+ dispatchConfigChanged(ev.header.timestamp, ev.header.displayId, ev.config.configId);
+ break;
default:
ALOGW("dispatcher %p ~ ignoring unknown event type %#x", this, ev.header.type);
break;
diff --git a/libs/androidfw/include/androidfw/DisplayEventDispatcher.h b/libs/androidfw/include/androidfw/DisplayEventDispatcher.h
index d2addba..5381c01 100644
--- a/libs/androidfw/include/androidfw/DisplayEventDispatcher.h
+++ b/libs/androidfw/include/androidfw/DisplayEventDispatcher.h
@@ -40,6 +40,8 @@
virtual void dispatchVsync(nsecs_t timestamp, PhysicalDisplayId displayId, uint32_t count) = 0;
virtual void dispatchHotplug(nsecs_t timestamp, PhysicalDisplayId displayId,
bool connected) = 0;
+ virtual void dispatchConfigChanged(nsecs_t timestamp, PhysicalDisplayId displayId,
+ int32_t configId) = 0;
virtual int handleEvent(int receiveFd, int events, void* data);
bool processPendingEvents(nsecs_t* outTimestamp, PhysicalDisplayId* outDisplayId,
diff --git a/native/android/choreographer.cpp b/native/android/choreographer.cpp
index 2db575b..3fecd53 100644
--- a/native/android/choreographer.cpp
+++ b/native/android/choreographer.cpp
@@ -70,6 +70,8 @@
void dispatchVsync(nsecs_t timestamp, PhysicalDisplayId displayId, uint32_t count) override;
void dispatchHotplug(nsecs_t timestamp, PhysicalDisplayId displayId, bool connected) override;
+ void dispatchConfigChanged(nsecs_t timestamp, PhysicalDisplayId displayId,
+ int32_t configId) override;
void scheduleCallbacks();
@@ -164,6 +166,13 @@
this, displayId, toString(connected));
}
+void Choreographer::dispatchConfigChanged(nsecs_t, PhysicalDisplayId displayId,
+ int32_t configId) {
+ ALOGV("choreographer %p ~ received config changed event (displayId=%"
+ ANDROID_PHYSICAL_DISPLAY_ID_FORMAT ", configId=%s), ignoring.",
+ this, displayId, toString(configId));
+}
+
void Choreographer::handleMessage(const Message& message) {
switch (message.what) {
case MSG_SCHEDULE_CALLBACKS:
diff --git a/services/core/java/com/android/server/display/LocalDisplayAdapter.java b/services/core/java/com/android/server/display/LocalDisplayAdapter.java
index 4891947..77df10b 100644
--- a/services/core/java/com/android/server/display/LocalDisplayAdapter.java
+++ b/services/core/java/com/android/server/display/LocalDisplayAdapter.java
@@ -65,7 +65,8 @@
new LongSparseArray<LocalDisplayDevice>();
@SuppressWarnings("unused") // Becomes active at instantiation time.
- private HotplugDisplayEventReceiver mHotplugReceiver;
+ private PhysicalDisplayEventReceiver mPhysicalDisplayEventReceiver;
+
// Called with SyncRoot lock held.
public LocalDisplayAdapter(DisplayManagerService.SyncRoot syncRoot,
@@ -77,7 +78,7 @@
public void registerLocked() {
super.registerLocked();
- mHotplugReceiver = new HotplugDisplayEventReceiver(getHandler().getLooper());
+ mPhysicalDisplayEventReceiver = new PhysicalDisplayEventReceiver(getHandler().getLooper());
for (long physicalDisplayId : SurfaceControl.getPhysicalDisplayIds()) {
tryConnectDisplayLocked(physicalDisplayId);
@@ -727,8 +728,8 @@
}
}
- private final class HotplugDisplayEventReceiver extends DisplayEventReceiver {
- public HotplugDisplayEventReceiver(Looper looper) {
+ private final class PhysicalDisplayEventReceiver extends DisplayEventReceiver {
+ PhysicalDisplayEventReceiver(Looper looper) {
super(looper, VSYNC_SOURCE_APP);
}
@@ -742,5 +743,15 @@
}
}
}
+
+ @Override
+ public void onConfigChanged(long timestampNanos, long physicalDisplayId, int configId) {
+ if (DEBUG) {
+ Slog.d(TAG, "onConfigChanged("
+ + "timestampNanos=" + timestampNanos
+ + ", builtInDisplayId=" + physicalDisplayId
+ + ", configId=" + configId + ")");
+ }
+ }
}
}