Is it possible to add animated emoji in android me

2019-07-05 03:42发布

问题:

I am developing an emoji keyboard for android but don't know how to add a animated emoji in currentInputConnection of InputMethodService.

 Edittext content= findVie......
    sb = new SpannableStringBuilder();
            String dummyText = "-";
            sb.append(dummyText);

            try {
                sb.setSpan(anim = new AnimatedImageSpan(new AnimatedGifDrawable(
                        getAssets().open("54.gif"),
                        new AnimatedGifDrawable.UpdateListener() {
                            @Override
                            public void update() {
                                content.requestLayout();
                                content.invalidate();
                            }
                        })), sb.length() - dummyText.length(), sb.length(),
                        Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
            } catch (IOException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }

            content.setText(sb);

here content is an editText view but I don't have any edit text view. All I have is currentInputConnection return by InputMethodService.getCurrentInputConnection().

回答1:

If I understand you correctly, you're trying to send a "animated image" (sth like a gif) to EditText right? As far as I know, that may be impossible. If you have read the documentation of InputConnection, you should know that it doesn't provide any API to do this.

Actually I'm working on an Android IME project in which we implement an static Emoji input keyboard. All we do is to simply send the encoded bytes of emoji through InputConnection then the smiling face appears in the edit box.

If you have used WeChat, you may notice that its client has implemented a custom emoji keyboard(including static and dynamic content). That's because they know exactly what they're doing.



回答2:

I am also trying to do the same thing. then i got my answer that .

If you want to implement within your app and sent message to your own app.

Then you can map each image pattern to some value.

////////

public class ViewsUtils {

    private static final Map<Pattern, Integer> emoticons = new HashMap<Pattern, Integer>();


    static {
        addPattern(emoticons, "\ud83d\udeb6", R.drawable.emot_d83ddeb6);
        ...
    }

    private static void addPattern(Map<Pattern, Integer> map, String smile,
            int resource) {
        map.put(Pattern.compile(Pattern.quote(smile)), resource);
    }

    public static boolean addSmiles(Context context, Spannable spannable) {
        boolean hasChanges = false;
        for (Entry<Pattern, Integer> entry : emoticons.entrySet()) {
            Matcher matcher = entry.getKey().matcher(spannable);
            while (matcher.find()) {
                boolean set = true;
                for (ImageSpan span : spannable.getSpans(matcher.start(),
                        matcher.end(), ImageSpan.class))
                    if (spannable.getSpanStart(span) >= matcher.start()
                            && spannable.getSpanEnd(span) <= matcher.end())
                        spannable.removeSpan(span);
                    else {
                        set = false;
                        break;
                    }
                if (set) {
                    hasChanges = true;
                    spannable.setSpan(new ImageSpan(context, entry.getValue()),
                            matcher.start(), matcher.end(),
                            Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
                }
            }
        }
        return hasChanges;
    }

    public static void setText(TextView view, String text) {
        if (null != view && null != text) {
            Spanned spanned = Html.fromHtml(text);
            SpannableString spannableString = SpannableString.valueOf(spanned);
            addSmiles(view.getContext(), spannableString);
            view.setText(spannableString);
        }
    }

    public static void setText(View parent, int viewId, int resId) {
        if (null != parent) {
            String text = parent.getContext().getString(resId);
            setText(parent, viewId, text);
        }
    }

    public static void setText(View parent, int viewId, String text) {
        if (null != parent) {
            TextView view = (TextView) parent.findViewById(viewId);
            if (null != view && null != text) {
                Spanned spanned = Html.fromHtml(text);
                SpannableString spannableString = SpannableString.valueOf(spanned);
                addSmiles(view.getContext(), spannableString);
                view.setText(spannableString);
            }
        }
    }

    public static void setText(View parent, int viewId, String text,
            int visibility) {
        if (null != parent) {
            TextView view = (TextView) parent.findViewById(viewId);
            if (null != view && null != text) {
                Spanned spanned = Html.fromHtml(text);
                SpannableString spannableString = SpannableString.valueOf(spanned);
                addSmiles(view.getContext(), spannableString);
                view.setText(spannableString);
                view.setVisibility(visibility);
            }
        }
    }

}

You just have to add map entries for the emote icons you want to handle in the static block. Using this class is pretty easy after that - just call some of the setText (or call addSmiles directly) methods. It would handle Html parsing too.