1
0
mirror of https://github.com/moparisthebest/k-9 synced 2024-12-25 09:08:49 -05:00

Fixed HTML generation in MimeUtility.extractTextAndAttachments()

This commit is contained in:
cketti 2012-02-17 19:40:58 +01:00
parent cf9631d481
commit 8ce78408c2
4 changed files with 68 additions and 31 deletions

View File

@ -2709,7 +2709,7 @@ public class MessageCompose extends K9Activity implements OnClickListener, OnFoc
if (part != null) { if (part != null) {
if (K9.DEBUG) if (K9.DEBUG)
Log.d(K9.LOG_TAG, "getBodyTextFromMessage: HTML requested, text found."); Log.d(K9.LOG_TAG, "getBodyTextFromMessage: HTML requested, text found.");
return HtmlConverter.textToHtml(MimeUtility.getTextFromPart(part)); return HtmlConverter.textToHtml(MimeUtility.getTextFromPart(part), true);
} }
} else if (format == MessageFormat.TEXT) { } else if (format == MessageFormat.TEXT) {
// Text takes precedence, then html. // Text takes precedence, then html.

View File

@ -125,19 +125,41 @@ public class HtmlConverter {
private static final int MAX_SMART_HTMLIFY_MESSAGE_LENGTH = 1024 * 256 ; private static final int MAX_SMART_HTMLIFY_MESSAGE_LENGTH = 1024 * 256 ;
public static final String getHtmlHeader() {
return "<html><head/><body>";
}
public static final String getHtmlFooter() {
return "</body></html>";
}
/** /**
* Naively convert a text string into an HTML document. This method avoids using regular expressions on the entire * Naively convert a text string into an HTML document.
* message body to save memory. *
* @param text Plain text string. * <p>
* This method avoids using regular expressions on the entire message body to save memory.
* </p>
*
* @param text
* Plain text string.
* @param useHtmlTag
* If {@code true} this method adds headers and footers to create a proper HTML
* document.
*
* @return HTML string. * @return HTML string.
*/ */
private static String simpleTextToHtml(String text) { private static String simpleTextToHtml(String text, boolean useHtmlTag) {
// Encode HTML entities to make sure we don't display something evil. // Encode HTML entities to make sure we don't display something evil.
text = TextUtils.htmlEncode(text); text = TextUtils.htmlEncode(text);
StringReader reader = new StringReader(text); StringReader reader = new StringReader(text);
StringBuilder buff = new StringBuilder(text.length() + TEXT_TO_HTML_EXTRA_BUFFER_LENGTH); StringBuilder buff = new StringBuilder(text.length() + TEXT_TO_HTML_EXTRA_BUFFER_LENGTH);
buff.append("<html><head/><body>");
if (useHtmlTag) {
buff.append(getHtmlHeader());
}
buff.append(htmlifyMessageHeader());
int c; int c;
try { try {
@ -159,25 +181,39 @@ public class HtmlConverter {
Log.e(K9.LOG_TAG, "Could not read string to convert text to HTML:", e); Log.e(K9.LOG_TAG, "Could not read string to convert text to HTML:", e);
} }
buff.append("</body></html>"); buff.append(htmlifyMessageFooter());
if (useHtmlTag) {
buff.append(getHtmlFooter());
}
return buff.toString(); return buff.toString();
} }
/** /**
* Convert a text string into an HTML document. Attempts to do smart replacement for large * Convert a text string into an HTML document.
* documents to prevent OOM errors. This method adds headers and footers to create a proper HTML *
* document. To convert to a fragment, use {@link #textToHtmlFragment(String)}. * <p>
* @param text Plain text string. * Attempts to do smart replacement for large documents to prevent OOM errors. This method
* optionally adds headers and footers to create a proper HTML document. To convert to a
* fragment, use {@link #textToHtmlFragment(String)}.
* </p>
*
* @param text
* Plain text string.
* @param useHtmlTag
* If {@code true} this method adds headers and footers to create a proper HTML
* document.
*
* @return HTML string. * @return HTML string.
*/ */
public static String textToHtml(String text) { public static String textToHtml(String text, boolean useHtmlTag) {
// Our HTMLification code is somewhat memory intensive // Our HTMLification code is somewhat memory intensive
// and was causing lots of OOM errors on the market // and was causing lots of OOM errors on the market
// if the message is big and plain text, just do // if the message is big and plain text, just do
// a trivial htmlification // a trivial htmlification
if (text.length() > MAX_SMART_HTMLIFY_MESSAGE_LENGTH) { if (text.length() > MAX_SMART_HTMLIFY_MESSAGE_LENGTH) {
return simpleTextToHtml(text); return simpleTextToHtml(text, useHtmlTag);
} }
StringReader reader = new StringReader(text); StringReader reader = new StringReader(text);
StringBuilder buff = new StringBuilder(text.length() + TEXT_TO_HTML_EXTRA_BUFFER_LENGTH); StringBuilder buff = new StringBuilder(text.length() + TEXT_TO_HTML_EXTRA_BUFFER_LENGTH);
@ -221,11 +257,19 @@ public class HtmlConverter {
text = text.replaceAll("(?m)(\r\n|\n|\r){4,}", "\n\n"); text = text.replaceAll("(?m)(\r\n|\n|\r){4,}", "\n\n");
StringBuffer sb = new StringBuffer(text.length() + TEXT_TO_HTML_EXTRA_BUFFER_LENGTH); StringBuffer sb = new StringBuffer(text.length() + TEXT_TO_HTML_EXTRA_BUFFER_LENGTH);
sb.append("<html><head></head><body>");
if (useHtmlTag) {
sb.append(getHtmlHeader());
}
sb.append(htmlifyMessageHeader()); sb.append(htmlifyMessageHeader());
linkifyText(text, sb); linkifyText(text, sb);
sb.append(htmlifyMessageFooter()); sb.append(htmlifyMessageFooter());
sb.append("</body></html>");
if (useHtmlTag) {
sb.append(getHtmlFooter());
}
text = sb.toString(); text = sb.toString();
return text; return text;

View File

@ -1320,6 +1320,8 @@ public class MimeUtility {
StringBuilder text = new StringBuilder(); StringBuilder text = new StringBuilder();
StringBuilder html = new StringBuilder(); StringBuilder html = new StringBuilder();
html.append(HtmlConverter.getHtmlHeader());
for (Viewable viewable : viewables) { for (Viewable viewable : viewables) {
if (viewable instanceof Textual) { if (viewable instanceof Textual) {
// This is either a text/plain or text/html part. Fill the variables 'text' and // This is either a text/plain or text/html part. Fill the variables 'text' and
@ -1370,6 +1372,8 @@ public class MimeUtility {
} }
} }
html.append(HtmlConverter.getHtmlFooter());
return new ViewableContainer(text.toString(), html.toString(), attachments); return new ViewableContainer(text.toString(), html.toString(), attachments);
} catch (Exception e) { } catch (Exception e) {
throw new MessagingException("Couldn't extract viewable parts", e); throw new MessagingException("Couldn't extract viewable parts", e);
@ -1863,8 +1867,8 @@ public class MimeUtility {
* Use the contents of a {@link Viewable} to create the HTML to be displayed. * Use the contents of a {@link Viewable} to create the HTML to be displayed.
* *
* <p> * <p>
* This will use {@link HtmlConverter#textToHtml(String)} to convert plain text parts to HTML * This will use {@link HtmlConverter#textToHtml(String, boolean)} to convert plain text parts
* if necessary. * to HTML if necessary.
* </p> * </p>
* *
* @param viewable * @param viewable
@ -1886,7 +1890,7 @@ public class MimeUtility {
if (t == null) { if (t == null) {
t = ""; t = "";
} else if (viewable instanceof Text) { } else if (viewable instanceof Text) {
t = HtmlConverter.textToHtml(t); t = HtmlConverter.textToHtml(t, false);
} }
html.append(t); html.append(t);
} else if (viewable instanceof Alternative) { } else if (viewable instanceof Alternative) {

View File

@ -2105,7 +2105,7 @@ public class LocalStore extends Store implements Serializable {
List<Part> attachments = container.attachments; List<Part> attachments = container.attachments;
String text = container.text; String text = container.text;
String html = container.html; String html = HtmlConverter.convertEmoji2Img(container.html);
String preview = calculateContentPreview(text); String preview = calculateContentPreview(text);
@ -2754,17 +2754,6 @@ public class LocalStore extends Store implements Serializable {
} }
public String markupContent(String text, String html) {
if (text.length() > 0 && html.length() == 0) {
html = HtmlConverter.textToHtml(text);
}
html = HtmlConverter.convertEmoji2Img(html);
return html;
}
@Override @Override
public boolean isInTopGroup() { public boolean isInTopGroup() {
return mInTopGroup; return mInTopGroup;