Жирный клик на сенсорном экране

Matt Robertson спросил: 11 июня 2018 в 11:04 в: android

У меня есть TextView, в котором каждое слово является ClickableSpan (фактически пользовательский подкласс ClickableSpan). Когда слово затрагивается, оно должно быть выделено жирным шрифтом. Если я устанавливаю textIsSelectable (false) в TextView, он отлично работает. Слово сразу выделено полужирным. Но если текст можно выбрать, то он не работает. НО - если я коснусь слова, а затем выключите и снова включите экран, когда экранное изображение возвращается на слово, выделено полужирным шрифтом. Я пробовал все, что я могу придумать, чтобы заставить перерисовать (аннулировать TextView, принудительно вызвать Activity onRestart (), refreshDrawableState () в TextView и т. Д.). Что мне не хватает?

Вот мой подкласс ClickableSpan:

public class WordSpan extends ClickableSpan
{
    int id;
    private boolean marking = false;
    TextPaint tp;
    Typeface font;
    int color = Color.BLACK;    public WordSpan(int id, Typeface font, boolean marked) {
        this.id = id;
        marking = marked;
        this.font = font;
    }    @Override
    public void updateDrawState(TextPaint ds) {
        ds.setColor(color);
        ds.setUnderlineText(false);        if (marking)
            ds.setTypeface(Typeface.create(font,Typeface.BOLD));        tp = ds;
    }    @Override
    public void onClick(View v) {
        // Empty here -- overriden in activity
    }    public void setMarking(boolean m) {
        marking = m;
        updateDrawState(tp);
    }    public void setColor(int col) {
        color = col;
    }
}

Вот код экземпляра WordSpan в моей деятельности:

... looping through wordscurSpan = new WordSpan(index,myFont,index==selectedWordId) {
    @Override
    public void onClick(View view) {
        handleWordClick(index,this);
        setMarking(true);
        tvText.invalidate();
    }
};... continue loop code

И вот мой пользовательский MovementMethod:

public static MovementMethod createMovementMethod ( Context context ) {
    final GestureDetector detector = new GestureDetector(context, new GestureDetector.SimpleOnGestureListener() {
        @Override
        public boolean onSingleTapUp ( MotionEvent e ) {
            return true;
        }        @Override
        public boolean onSingleTapConfirmed ( MotionEvent e ) {
            return false;
        }        @Override
        public boolean onDown ( MotionEvent e ) {
            return false;
        }        @Override
        public boolean onDoubleTap ( MotionEvent e ) {
            return false;
        }        @Override
        public void onShowPress ( MotionEvent e ) {
            return;
        }
    });    return new ScrollingMovementMethod() {        @Override
        public boolean canSelectArbitrarily () {
            return true;
        }        @Override
        public void initialize(TextView widget, Spannable text) {
            Selection.setSelection(text, text.length());
        }        @Override
        public void onTakeFocus(TextView view, Spannable text, int dir) {            if ((dir & (View.FOCUS_FORWARD | View.FOCUS_DOWN)) != 0) {
                if (view.getLayout() == null) {
                    // This shouldn't be null, but do something sensible if it is.
                    Selection.setSelection(text, text.length());
                }
            } else {
                Selection.setSelection(text, text.length());
            }
        }        @Override
        public boolean onTouchEvent ( TextView widget, Spannable buffer, MotionEvent event ) {
            // check if event is a single tab
            boolean isClickEvent = detector.onTouchEvent(event);            // detect span that was clicked
            if (isClickEvent) {
                int x = (int) event.getX();
                int y = (int) event.getY();                x -= widget.getTotalPaddingLeft();
                y -= widget.getTotalPaddingTop();                x += widget.getScrollX();
                y += widget.getScrollY();                Layout layout = widget.getLayout();
                int line = layout.getLineForVertical(y);
                int off = layout.getOffsetForHorizontal(line, x);                WordSpan[] link = buffer.getSpans(off, off, WordSpan.class);                if (link.length != 0) {
                    // execute click only for first clickable span
                    // can be a for each loop to execute every one                    if (event.getAction() == MotionEvent.ACTION_UP) {
                        link[0].onClick(widget);
                        return true;
                    }
                    else if (event.getAction() == MotionEvent.ACTION_DOWN) {
                        Selection.setSelection(buffer,
                                               buffer.getSpanStart(link[0]),
                                               buffer.getSpanEnd(link[0]));                        return false;
                    }
                }
                else {                }
            }            // let scroll movement handle the touch
            return super.onTouchEvent(widget, buffer, event);
        }
    };
}

0 ответов