Merge "Introduce PrecomputedText version of MessagingTextMessage" into udc-qpr-dev
diff --git a/core/java/com/android/internal/widget/ConversationLayout.java b/core/java/com/android/internal/widget/ConversationLayout.java
index 7dda91d..5b6b360 100644
--- a/core/java/com/android/internal/widget/ConversationLayout.java
+++ b/core/java/com/android/internal/widget/ConversationLayout.java
@@ -410,9 +410,11 @@
// convert MessagingStyle.Message to MessagingMessage, re-using ones from a previous binding
// if they exist
final List<MessagingMessage> newMessagingMessages =
- createMessages(newMessages, false /* isHistoric */);
+ createMessages(newMessages, /* isHistoric= */false,
+ /* usePrecomputedText= */false);
final List<MessagingMessage> newHistoricMessagingMessages =
- createMessages(newHistoricMessages, true /* isHistoric */);
+ createMessages(newHistoricMessages, /* isHistoric= */true,
+ /* usePrecomputedText= */false);
// bind it, baby
bindViews(user, showSpinner, unreadCount,
newMessagingMessages,
@@ -981,15 +983,17 @@
* @param newMessages the messages to parse.
*/
private List<MessagingMessage> createMessages(
- List<Notification.MessagingStyle.Message> newMessages, boolean historic) {
+ List<Notification.MessagingStyle.Message> newMessages, boolean isHistoric,
+ boolean usePrecomputedText) {
List<MessagingMessage> result = new ArrayList<>();
for (int i = 0; i < newMessages.size(); i++) {
Notification.MessagingStyle.Message m = newMessages.get(i);
MessagingMessage message = findAndRemoveMatchingMessage(m);
if (message == null) {
- message = MessagingMessage.createMessage(this, m, mImageResolver);
+ message = MessagingMessage.createMessage(this, m,
+ mImageResolver, usePrecomputedText);
}
- message.setIsHistoric(historic);
+ message.setIsHistoric(isHistoric);
result.add(message);
}
return result;
diff --git a/core/java/com/android/internal/widget/MessagingImageMessage.java b/core/java/com/android/internal/widget/MessagingImageMessage.java
index 098bce1..c132d6a 100644
--- a/core/java/com/android/internal/widget/MessagingImageMessage.java
+++ b/core/java/com/android/internal/widget/MessagingImageMessage.java
@@ -93,8 +93,9 @@
}
@Override
- public boolean setMessage(Notification.MessagingStyle.Message message) {
- MessagingMessage.super.setMessage(message);
+ public boolean setMessage(Notification.MessagingStyle.Message message,
+ boolean usePrecomputedText) {
+ MessagingMessage.super.setMessage(message, usePrecomputedText);
Drawable drawable;
try {
Uri uri = message.getDataUri();
@@ -114,32 +115,42 @@
}
mDrawable = drawable;
mAspectRatio = ((float) mDrawable.getIntrinsicWidth()) / intrinsicHeight;
- setImageDrawable(drawable);
- setContentDescription(message.getText());
+ if (!usePrecomputedText) {
+ finalizeInflate();
+ }
return true;
}
static MessagingMessage createMessage(IMessagingLayout layout,
- Notification.MessagingStyle.Message m, ImageResolver resolver) {
+ Notification.MessagingStyle.Message m, ImageResolver resolver,
+ boolean usePrecomputedText) {
MessagingLinearLayout messagingLinearLayout = layout.getMessagingLinearLayout();
MessagingImageMessage createdMessage = sInstancePool.acquire();
if (createdMessage == null) {
createdMessage = (MessagingImageMessage) LayoutInflater.from(
layout.getContext()).inflate(
- R.layout.notification_template_messaging_image_message,
- messagingLinearLayout,
- false);
+ R.layout.notification_template_messaging_image_message,
+ messagingLinearLayout,
+ false);
createdMessage.addOnLayoutChangeListener(MessagingLayout.MESSAGING_PROPERTY_ANIMATOR);
}
createdMessage.setImageResolver(resolver);
- boolean created = createdMessage.setMessage(m);
- if (!created) {
+ // MessagingImageMessage does not use usePrecomputedText.
+ boolean populated = createdMessage.setMessage(m, /* usePrecomputedText= */false);
+ if (!populated) {
createdMessage.recycle();
- return MessagingTextMessage.createMessage(layout, m);
+ return MessagingTextMessage.createMessage(layout, m, usePrecomputedText);
}
return createdMessage;
}
+
+ @Override
+ public void finalizeInflate() {
+ setImageDrawable(mDrawable);
+ setContentDescription(getMessage().getText());
+ }
+
private void setImageResolver(ImageResolver resolver) {
mImageResolver = resolver;
}
diff --git a/core/java/com/android/internal/widget/MessagingLayout.java b/core/java/com/android/internal/widget/MessagingLayout.java
index 8345c5c..83557cd 100644
--- a/core/java/com/android/internal/widget/MessagingLayout.java
+++ b/core/java/com/android/internal/widget/MessagingLayout.java
@@ -178,9 +178,9 @@
extras.getBoolean(Notification.EXTRA_SHOW_REMOTE_INPUT_SPINNER, false);
final List<MessagingMessage> historicMessagingMessages = createMessages(newHistoricMessages,
- true /* isHistoric */);
+ /* isHistoric= */true, /* usePrecomputedText= */ false);
final List<MessagingMessage> newMessagingMessages =
- createMessages(newMessages, false /* isHistoric */);
+ createMessages(newMessages, /* isHistoric= */false, /* usePrecomputedText= */false);
bindViews(user, showSpinner, historicMessagingMessages, newMessagingMessages);
}
@@ -518,15 +518,17 @@
* @param newMessages the messages to parse.
*/
private List<MessagingMessage> createMessages(
- List<Notification.MessagingStyle.Message> newMessages, boolean historic) {
+ List<Notification.MessagingStyle.Message> newMessages, boolean isHistoric,
+ boolean usePrecomputedText) {
List<MessagingMessage> result = new ArrayList<>();
for (int i = 0; i < newMessages.size(); i++) {
Notification.MessagingStyle.Message m = newMessages.get(i);
MessagingMessage message = findAndRemoveMatchingMessage(m);
if (message == null) {
- message = MessagingMessage.createMessage(this, m, mImageResolver);
+ message = MessagingMessage.createMessage(this, m,
+ mImageResolver, usePrecomputedText);
}
- message.setIsHistoric(historic);
+ message.setIsHistoric(isHistoric);
result.add(message);
}
return result;
diff --git a/core/java/com/android/internal/widget/MessagingMessage.java b/core/java/com/android/internal/widget/MessagingMessage.java
index 5ecd3b8..ad90a63 100644
--- a/core/java/com/android/internal/widget/MessagingMessage.java
+++ b/core/java/com/android/internal/widget/MessagingMessage.java
@@ -34,11 +34,12 @@
String IMAGE_MIME_TYPE_PREFIX = "image/";
static MessagingMessage createMessage(IMessagingLayout layout,
- Notification.MessagingStyle.Message m, ImageResolver resolver) {
+ Notification.MessagingStyle.Message m, ImageResolver resolver,
+ boolean usePrecomputedText) {
if (hasImage(m) && !ActivityManager.isLowRamDeviceStatic()) {
- return MessagingImageMessage.createMessage(layout, m, resolver);
+ return MessagingImageMessage.createMessage(layout, m, resolver, usePrecomputedText);
} else {
- return MessagingTextMessage.createMessage(layout, m);
+ return MessagingTextMessage.createMessage(layout, m, usePrecomputedText);
}
}
@@ -55,9 +56,11 @@
/**
* Set a message for this view.
+ *
* @return true if setting the message worked
*/
- default boolean setMessage(Notification.MessagingStyle.Message message) {
+ default boolean setMessage(Notification.MessagingStyle.Message message,
+ boolean usePrecomputedText) {
getState().setMessage(message);
return true;
}
@@ -151,4 +154,10 @@
void setVisibility(int visibility);
int getVisibility();
+
+ /**
+ * Finalize inflation of the MessagingMessages, which should be called on Main Thread.
+ * @hide
+ */
+ void finalizeInflate();
}
diff --git a/core/java/com/android/internal/widget/MessagingTextMessage.java b/core/java/com/android/internal/widget/MessagingTextMessage.java
index 19791db..bd62aad 100644
--- a/core/java/com/android/internal/widget/MessagingTextMessage.java
+++ b/core/java/com/android/internal/widget/MessagingTextMessage.java
@@ -23,7 +23,9 @@
import android.app.Notification;
import android.content.Context;
import android.text.Layout;
+import android.text.PrecomputedText;
import android.util.AttributeSet;
+import android.util.Log;
import android.view.LayoutInflater;
import android.widget.RemoteViews;
@@ -35,10 +37,13 @@
@RemoteViews.RemoteView
public class MessagingTextMessage extends ImageFloatingTextView implements MessagingMessage {
+ private static final String TAG = "MessagingTextMessage";
private static final MessagingPool<MessagingTextMessage> sInstancePool =
new MessagingPool<>(20);
private final MessagingMessageState mState = new MessagingMessageState(this);
+ private PrecomputedText mPrecomputedText = null;
+
public MessagingTextMessage(@NonNull Context context) {
super(context);
}
@@ -63,25 +68,32 @@
}
@Override
- public boolean setMessage(Notification.MessagingStyle.Message message) {
- MessagingMessage.super.setMessage(message);
- setText(message.getText());
+ public boolean setMessage(Notification.MessagingStyle.Message message,
+ boolean usePrecomputedText) {
+ MessagingMessage.super.setMessage(message, usePrecomputedText);
+ if (usePrecomputedText) {
+ mPrecomputedText = PrecomputedText.create(message.getText(), getTextMetricsParams());
+ } else {
+ setText(message.getText());
+ mPrecomputedText = null;
+ }
+
return true;
}
static MessagingMessage createMessage(IMessagingLayout layout,
- Notification.MessagingStyle.Message m) {
+ Notification.MessagingStyle.Message m, boolean usePrecomputedText) {
MessagingLinearLayout messagingLinearLayout = layout.getMessagingLinearLayout();
MessagingTextMessage createdMessage = sInstancePool.acquire();
if (createdMessage == null) {
createdMessage = (MessagingTextMessage) LayoutInflater.from(
layout.getContext()).inflate(
- R.layout.notification_template_messaging_text_message,
- messagingLinearLayout,
- false);
+ R.layout.notification_template_messaging_text_message,
+ messagingLinearLayout,
+ false);
createdMessage.addOnLayoutChangeListener(MessagingLayout.MESSAGING_PROPERTY_ANIMATOR);
}
- createdMessage.setMessage(m);
+ createdMessage.setMessage(m, usePrecomputedText);
return createdMessage;
}
@@ -135,4 +147,20 @@
public void setColor(int color) {
setTextColor(color);
}
+
+ @Override
+ public void finalizeInflate() {
+ try {
+ setText(mPrecomputedText != null ? mPrecomputedText
+ : getState().getMessage().getText());
+ } catch (IllegalArgumentException exception) {
+ Log.wtf(
+ /* tag = */ TAG,
+ /* msg = */ "PrecomputedText setText failed for TextView:" + this,
+ /* tr = */ exception
+ );
+ mPrecomputedText = null;
+ setText(getState().getMessage().getText());
+ }
+ }
}