Вопрос:

Вставить символ в позиции курсора в VUE JS

javascript vue.js vuejs2

2954 просмотра

3 ответа

802 Репутация автора

Я пытался вставить Emoji в textarea именно там, где курсор находится. Я посмотрел вокруг how tosв Интернете, не мог найти ничего конкретного в VUE JS. Большинство из них в простом JS.

У меня есть этот код

<div class="picker" v-show="showPicker">
    <click-outside :handler="handleClickOutside">
        <picker
            set ="messenger"
            title="Pick your emoji…"
            emoji="point_up"
            @click="addEmoji"
            :emoji-size="16"
        >
        </picker> 
    </click-outside>
</div>

<textarea id="greeting_text_input" class="form-control"
    type="text" 
    v-model="greeting_text"
    rows="8"
    required
    placeholder="Hi {first-name}! Welcome to our bot. Click on the ‘Get 
    Started’ button to begin
">
</textarea>

Мой метод

addEmoji(emoji){
        this.greeting_text += emoji.native;
        this.showPicker = !this.showPicker;
    }

Очевидно, этот код добавит символ (в моем случае, эмодзи) к последней строке. Мне нужно чистое решение vuejs для этого. Какова будет лучшая практика для такой проблемы в Vue? поскольку в сети есть несколько решений, основанных либо на vanilla JS, либо на Jquery.

Автор: Genius in trouble Источник Размещён: 08.01.2018 07:10

Ответы (3)


9 плюса

367 Репутация автора

Решение

Два шага:

1 получить textareaэлемент, используя vue-way:

1.1 Добавьте refатрибут к textareaтегу в коде вашего шаблона:

<textarea ref="ta"></textarea>

1.2 получить этот элемент после mountedхука этого компонента:

let textarea = this.$refs.ta

2 получить позицию курсора textareaэлемента.

let cursorPosition = textarea.selectionStart

Вот ссылка: ref

Автор: grantonzhuang Размещён: 08.01.2018 11:12

4 плюса

219 Репутация автора

<!-- tag -->
<textarea ref="yourTextarea" v-model.trim="txtContent" ......></textarea>

// methods:
insertSomething: function(insert) {
  const self = this;
  var tArea = this.$refs.yourTextarea;
  // filter:
  if (0 == insert) {
    return;
  }
  if (0 == cursorPos) {
    return;
  }

  // get cursor's position:
  var startPos = tArea.selectionStart,
    endPos = tArea.selectionEnd,
    cursorPos = startPos,
    tmpStr = tArea.value;

  // insert:
  self.txtContent = tmpStr.substring(0, startPos) + insert + tmpStr.substring(endPos, tmpStr.length);

  // move cursor:
  setTimeout(() => {
    cursorPos += insert.length;
    tArea.selectionStart = tArea.selectionEnd = cursorPos;
  }, 10);
}

Автор: PHPJungle Размещён: 16.04.2018 08:12

1 плюс

4397 Репутация автора

Я узнал об этом setSelectionRangeиз другого вопроса и использовал его для обработки ввода номера кредитной карты. Я покажу свое решение здесь, чтобы человек, возможно, вдохновился им.

шаблон:

<input
    ref="input"
    v-model="value"
    @input="handleChange"
>

методы экземпляра:

data() {
    return {
        lastValue: '',
    }
},

methods: {
    setCursorPosition(el, pos) {
        el.focus();
        el.setSelectionRange(pos, pos);
    },
    handleChange() {
        // handle backspace event
        if (this.value.length < this.lastValue.length) {
            this.lastValue = this.value;
            this.$emit('input-changed', this.value);
            return;
        }
        // handle value-edit event
        if (this.$refs.input.selectionStart < this.value.length) {
            const startPos = this.$refs.input.selectionStart;
            this.value = this.value.replace(/\W/gi, '').replace(/(.{4})/g, '$1 ').trim();
            this.$nextTick(() => this.setCursorPosition(this.$refs.input, startPos));
            this.lastValue = this.value;
            this.$emit('input-changed', this.value);
            return;
        }
        // handle everything else
        this.value = this.value.replace(/\W/gi, '').replace(/(.{4})/g, '$1 ').trim();
        this.lastValue = this.value;
        this.$emit('input-changed', this.value);
    },
},

Цель приведенного выше кода - добавить пробелы во входные данные кредитной карты, поэтому они 1234123412341234автоматически переформатируются в 1234 1234 1234 1234. Человек, рискнувший на эту территорию, заметит, что проблемы возникают при редактировании входного значения.

Вы можете видеть три условия в моем примере выше. Последнее является значением по умолчанию, которое просто переформатирует текущее значение с помощью двухэтапного комбо: удалите все пробелы, затем добавьте пробел каждый 4-й символ.

Если вы закомментируете два ifблока, вы можете наблюдать, как возникают проблемы.

Первый ifблок обрабатывает событие возврата. Как вы можете видеть, каждый раз, когда изменяется вход, значение фиксируется как this.lastValue. Когда вы нажимаете клавишу Backspace, цель первого условия - НЕ запускать регулярное выражение. На мой взгляд, это лучше UX. Если вы закомментируете это условие, вы увидите.

Второй ifблок обрабатывает события редактирования. Хороший способ проверить это - ввести действительный CC, но пропустить 3-й символ, чтобы все было выключено одним. Затем добавьте персонажа. Все должно быть хорошо. Точно так же, если вы возвращаете несколько символов. Цель второго условия - правильно управлять положением курсора (или позицией каретки, если вы предпочитаете эту номенклатуру).

Вы можете безопасно удалить первое условие, и все ссылки lastValueи код будут работать. Это возможно проще, но хуже UX.

Автор: agm1984 Размещён: 19.02.2019 11:29
Вопросы из категории :
32x32