Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit ce2ca072 authored by pengfeix's avatar pengfeix Committed by Steve Kondik
Browse files

Finer grained character boundaries in computing SMS fragment lengths

The standard Java character iterator has potentially unbounded
distance between character boundaries, meaning that when
breaking an SMS message into fragments it's not safe to assume that
the fragment will contain such a boundary. This patch
special-cases flags (pairs of Regional Indicator Symbols) and also
guarantees some progress in the case of no boundary found.

Change-Id: I35990b44ad72887e1fdd436223808e18b04bd578
CRs-Fixed: 994916
parent b3571da3
Loading
Loading
Loading
Loading
+20 −1
Original line number Diff line number Diff line
@@ -352,6 +352,10 @@ public abstract class SmsMessageBase {
         mIsEmail = Telephony.Mms.isEmailAddress(mEmailFrom);
    }

    //Returns true if the given code point is regional indicator symbol
    private static boolean isRegionalIndicatorSymbol(int codepoint) {
        return (0x1F1E6 <= codepoint && codepoint <= 0x1F1FF);
    }
    /**
     * Find the next position to start a new fragment of a multipart SMS.
     *
@@ -370,7 +374,22 @@ public abstract class SmsMessageBase {
            BreakIterator breakIterator = BreakIterator.getCharacterInstance();
            breakIterator.setText(msgBody.toString());
            if (!breakIterator.isBoundary(nextPos)) {
                nextPos = breakIterator.preceding(nextPos);
                int breakPos = breakIterator.preceding(nextPos);
                while (breakPos + 4 <= nextPos
                    && isRegionalIndicatorSymbol(
                     Character.codePointAt(msgBody, breakPos))
                    && isRegionalIndicatorSymbol(
                     Character.codePointAt(msgBody, breakPos + 2))) {
                   // skip forward over flags (pairs of Regional Indicator Symbol)
                   breakPos += 4;
                }
                if (breakPos > currentPosition) {
                    nextPos = breakPos;
                } else if (Character.isHighSurrogate(msgBody.charAt(nextPos - 1))) {
                  // no character boundary in this fragment, try to at least land on a code point
                    nextPos -= 1;
                }

            }
        }
        return nextPos;