Список поиска Vuejs Навигация по списку с помощью клавиш со стрелками

vue.js

#vue.js

Вопрос:

 const app = new Vue({
    el: '#app',
    data: {
        searchText: '',
        listShow: true,
        newDiv:false,
        searcList:[],
        list: {}
    },
   
    methods: {
        handleBlur(e) {
        console.log("inputOutClick");
          if (this.listShow == false) {
            console.log("mousedown was fired first");
          }
          this.listShow = false
        },
        selecteds(list) {
        console.log("selecteds");
            this.listShow = false;
            this.searchText = list.name;
        },
        
        async search() {
            this.listShow = true;
            this.searcList = ['aeaeg', 'tdthtdht', 'srgsr'];
            this.list.name = "TEST"
        }

    }

}); 
 .dropdown-toggle-none::after {
    content: none;
}

.select {
    width: 100%;
    max-height: 420px;
    overflow-y: auto;
    background: linear-gradient(#fdfdfd 30%, rgba(253, 253, 253, 0)), linear-gradient(rgba(253, 253, 253, 0), #fdfdfd 70%) 0 100%, linear-gradient(rgba(64, 54, 55, .1) 0, rgba(64, 54, 55, 0)) 100% 0, linear-gradient(rgba(64, 54, 55, 0) 0, rgba(64, 54, 55, .1)) 0 100%;
    background-repeat: no-repeat;
    background-size: 100% 50px, 100% 50px, 100% 6px, 100% 6px;
    background-attachment: local, local, scroll, scroll;
    border-top: 1px solid #e8e7e7;
    border-bottom: 1px solid #e8e7e7;
    background-color: #fdfdfd;
}

.select {
    z-index: 1;
    top: 50px;
    padding: 3px 0;
    border: 1px solid #c5c4c2;
    background-color: #fdfdfd;
    -webkit-box-shadow: 0 3px 6px #c5c4c2;
    -moz-box-shadow: 0 3px 6px #c5c4c2;

}

.select {
    position: absolute;
    border-radius: .357rem !important;
    box-shadow: 0 3px 6px #c5c4c2;
    -webkit-border-radius: 3px;
    -moz-border-radius: 3px;
    line-height: 1.45;
}

.select ul {
    padding: 0;
    margin: 0;
}

.select li {
    display: block;
    cursor: pointer;
    line-height: 20px;
    color: #403637;
}

.select li a {
    display: block;
    padding: 5px 15px;
    -webkit-transition-property: color, background-color;
    -webkit-transition-duration: .66s;
    -webkit-transition-timing-function: cubic-bezier(.25, 1, .25, 1);
    -moz-transition-duration: .66s;
    -ms-transition-duration: .66s;
    -ms-transition-timing-function: cubic-bezier(.25, 1, .25, 1);
    -o-transition-property: color, background-color;
    -o-transition-timing-function: cubic-bezier(.25, 1, .25, 1);
    transition-property: color, background-color;
    transition-duration: .66s;
    transition-timing-function: cubic-bezier(.25, 1, .25, 1);
}

.select li a:hover {
    color: #22c39e;
    background-color: #e8e7e7;
} 
 <link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.4.1/css/bootstrap.min.css">

<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.4.2/vue.js"></script>
    <div id="app">
        <div>
            <input
                type="text"
                class="form-control"
                v-model="searchText"
                @keyup="search"
                @blur="handleBlur"
                />
            <div v-if="listShow" style="background:red">
                <ul>
                    <li v-for="(list, index) in searcList">
                        <a @mousedown.prevent @click="selecteds(list)">{{ list}}</a>
                    </li>
                </ul>
            </div>
           <div v-if="newDiv">
           <p>hello</p>
           </div>
        </div>
    </div> 

Я пытаюсь позвонить с помощью vuejs, есть тема, с которой я просто застрял. например; Я хочу перемещаться по данным, возвращаемым из get data, с помощью стрелок «с помощью клавиши alt или клавиши up», но я не совсем понял, как это сделатьсделайте это.

If it is a second issue, I want the color of whichever is selected in the list to be clear.

 new Vue({
  el: '#app',
  data: {
   type: "sales_invoices",
            SearcListed: {
                searchText: '',
                listShow: false,
                searcList: [],
            },
  },
  methods: {
  selecteds(list) {
            this.SearcListed.listShow = false;
            this.SearcListed.searchText = list.name;
        },
        async search() {
            if (this.SearcListed.searchText !== '') {
                const res = await this.callApi('get', 'getir'   '?filter='   this.SearcListed.searchText)
                if (res.status === 200) {
                    this.SearcListed.searcList = res.data;
                    if (res.data.length > 0) {
                        this.SearcListed.listShow = true;
                    } else {
                        this.SearcListed.listShow = false;
                    }
                }
            } else {
                this.SearcListed.listShow = false;
            }
        },
  }
}); 
 .dropdown-toggle-none::after {
    content: none;
}

.select {
    width: 100%;
    max-height: 420px;
    overflow-y: auto;
    background: linear-gradient(#fdfdfd 30%, rgba(253, 253, 253, 0)), linear-gradient(rgba(253, 253, 253, 0), #fdfdfd 70%) 0 100%, linear-gradient(rgba(64, 54, 55, .1) 0, rgba(64, 54, 55, 0)) 100% 0, linear-gradient(rgba(64, 54, 55, 0) 0, rgba(64, 54, 55, .1)) 0 100%;
    background-repeat: no-repeat;
    background-size: 100% 50px, 100% 50px, 100% 6px, 100% 6px;
    background-attachment: local, local, scroll, scroll;
    border-top: 1px solid #e8e7e7;
    border-bottom: 1px solid #e8e7e7;
    background-color: #fdfdfd;
}

.select {
    z-index: 1;
    top: 50px;
    padding: 3px 0;
    border: 1px solid #c5c4c2;
    background-color: #fdfdfd;
    -webkit-box-shadow: 0 3px 6px #c5c4c2;
    -moz-box-shadow: 0 3px 6px #c5c4c2;

}

.select {
    position: absolute;
    border-radius: .357rem !important;
    box-shadow: 0 3px 6px #c5c4c2;
    -webkit-border-radius: 3px;
    -moz-border-radius: 3px;
    line-height: 1.45;
}

.select ul {
    padding: 0;
    margin: 0;
}

.select li {
    display: block;
    cursor: pointer;
    line-height: 20px;
    color: #403637;
}

.select li a {
    display: block;
    padding: 5px 15px;
    -webkit-transition-property: color, background-color;
    -webkit-transition-duration: .66s;
    -webkit-transition-timing-function: cubic-bezier(.25, 1, .25, 1);
    -moz-transition-duration: .66s;
    -ms-transition-duration: .66s;
    -ms-transition-timing-function: cubic-bezier(.25, 1, .25, 1);
    -o-transition-property: color, background-color;
    -o-transition-timing-function: cubic-bezier(.25, 1, .25, 1);
    transition-property: color, background-color;
    transition-duration: .66s;
    transition-timing-function: cubic-bezier(.25, 1, .25, 1);
}

.select li a:hover {
    color: #22c39e;
    background-color: #e8e7e7;
} 
 <div id="app">
  <div class="container">
    <div class="col-sm-6">
      <div class="input-group input-group-merge mb-1">
        <input type="text" class="form-control" placeholder="Search..." aria-label="Search..." aria-describedby="basic-addon-search2" v-model.trim="SearcListed.searchText" @keyup="search" autocomplete="off" />
        <span class="input-group-text">
          <i class="fas fa-search"></i>
        </span>
        <div class="select" v-if="SearcListed.listShow">
          <ul>
            <li v-for="(list, index) in SearcListed.searcList" :key="list.id">
              <a @mousedown.prevent @click="selecteds(list)">{{ list.name }}</a>
            </li>
          </ul>
        </div>
      </div>
    </div>
  </div>
</div>
<link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.4.1/css/bootstrap.min.css" integrity="sha384-Vkoo8x4CGsO3 Hhxv8T/Q5PaXtkKtu6ug5TOeNV6gBiFeWPGFN9MuhOf23Q9Ifjh" crossorigin="anonymous">
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.0.0-beta2/css/all.min.css">
<script src="https://cdn.jsdelivr.net/npm/vue@2.6.14/dist/vue.js"></script> 

Комментарии:

1. «но я не совсем понял, как это сделать». В чем конкретная проблема?

Ответ №1:

Чтобы использовать события клавиш со стрелками, вы можете использовать что-то вроде:

 @keyup.up="nextListItem"
@keyup.down="previousListItem"
 

Вы, вероятно, применили бы его к следующему div:

 <div @keyup.up="nextSearchList" @keyup.down="previousSearchList" class="input-group input-group-merge mb-1">...</div>
 

(Обратите внимание, что нажатия клавиш будут приниматься только тогда, когда div находится в фокусе.)

Вам нужно будет добавить индекс или объект в свой data() , чтобы отслеживать выбранный элемент в списке, а затем перейти к следующему или предыдущему с nextListItem помощью и previousListItem .

Вы можете добавить a :class="{ active: index == selectedItemIndex}" к каждому li v-for из них, чтобы присвоить выбранному в данный момент li active классу, а затем вы можете оформить его так, как хотите, например:

 .active {
 background-color: grey;
}
 

Кроме того, здесь приведена дополнительная информация для модификаторов ключевых событий vue2 и vue3:

Комментарии:

1. Я ничего не понимаю, пожалуйста, можете ли вы применить это к приложению

2. Вот статья, в которой вы узнаете больше об использовании клавиатуры в Vue2: shubhamjain.co/til/vue-shortcuts

3. Также невозможно попытаться отредактировать фрагмент кода вашего приложения, потому что, если что-то введено в поле поиска, вы получите Error: { "message": "this.callApi is not a function", "filename": undefined, "lineno": undefined, "colno": undefined }