2016-07-15 6 views
0

[Когда я ввожу входные данные (список стран), автозаполнение падает по списку стран, который соответствует моему вводу. Но проблема в том, что я не могу выбрать страну из этого списка с помощью мыши] [1]Угловой 2 Автозаполнение не работает должным образом

Я использую angular2 и при этом в typeahead(autocomplete), я поражен этой ошибки

//app.component.js 

    enter code here 

import {Component, ElementRef} from 'angular2/core'; 

@Component({ 
    selector: 'my-app', 
    host: { 
     '(document:click)': 'handleClick($event)', 
    }, 
    template: ` 
     <div class="container" > 
      <div class="input-field col s12"> 
       <input id="country" type="text" class="validate filter-input" [(ngModel)]=query (keyup)=filter($event) (blur)=handleBlur()> 
       <label for="country">Country</label> 
      </div> 
      <div class="suggestions" *ngIf="filteredList.length > 0"> 
       <ul *ngFor="#item of filteredList;#idx = index" > 
        <li [class.complete-selected]="idx == selectedIdx"> 
         <a (click)="select(item)">{{item}}</a> 
        </li> 
       </ul> 
      </div> 
     </div> 
     ` 
}) 

export class AppComponent { 
    public query = ''; 
    public countries = ["Albania", "Andorra", "Armenia", "Austria", "Azerbaijan", "Belarus", "Belgium", "Bosnia & Herzegovina", 
     "Bulgaria", "Croatia", "Cyprus", "Czech Republic", "Denmark", "Estonia", "Finland", "France", "Georgia", 
     "Germany", "Greece", "Hungary", "Iceland", "Ireland", "Italy", "Kosovo", "Latvia", "Liechtenstein", 
     "Lithuania", "Luxembourg", "Macedonia", "Malta", "Moldova", "Monaco", "Montenegro", "Netherlands", 
     "Norway", "Poland", "Portugal", "Romania", "Russia", "San Marino", "Serbia", "Slovakia", 
     "Slovenia", "Spain", "Sweden", "Switzerland", "Turkey", "Ukraine", "United Kingdom", "Vatican City"]; 
    public filteredList = []; 
    public elementRef; 
    selectedIdx: number; 

    constructor(myElement: ElementRef) { 
     this.elementRef = myElement; 
     this.selectedIdx = -1; 
    } 

    filter(event: any) { 
     if (this.query !== "") { 
      this.filteredList = this.countries.filter(function (el) { 
       return (el.toLowerCase().substr(0,this.query.length) === this.query.toLowerCase()) == true; 
      }.bind(this)); 
      if (event.code == "ArrowDown" && this.selectedIdx < this.filteredList.length) { 
       this.selectedIdx++; 
      } else if (event.code == "ArrowUp" && this.selectedIdx > 0) { 
       this.selectedIdx--; 
      } 
     } else { 
      this.filteredList = []; 
     } 
    } 

    select(item) { 
     this.query = item; 
     this.filteredList = []; 
     this.selectedIdx = -1; 
    } 

    handleBlur() { 
     if (this.selectedIdx > -1) { 
      this.query = this.filteredList[this.selectedIdx]; 
     } 
     this.filteredList = []; 
     this.selectedIdx = -1; 
    } 

    handleClick(event) { 
     var clickedComponent = event.target; 
     var inside = false; 
     do { 
      if (clickedComponent === this.elementRef.nativeElement) { 
       inside = true; 
      } 
      clickedComponent = clickedComponent.parentNode; 
     } while (clickedComponent); 
     if `enter code here`(!inside) { 
      this.filteredList = []; 
     } 
     this.selectedIdx = -1; 
    } 


}` 

____________________________________________________________________________________________________________________________________________________ 
//main.ts 
import {bootstrap} from 'angular2/platform/browser' 
import {AppComponent} from './app.component' 

bootstrap(AppComponent); 

____________________________________________________________________________________________________________________________________________________ 
//index.html 
<html> 
    <head> 
    <title>MasaCafe</title> 
    <meta name="viewport" content="width=device-width, initial-scale=1">  

    <!-- 1. Load libraries --> 
    <!-- IE required polyfills, in this exact order --> 
    <script src="node_modules/core-js/client/shim.min.js"></script> 
    <script src="node_modules/systemjs/dist/system-polyfills.js"></script> 

    <script src="node_modules/angular2/bundles/angular2-polyfills.js"></script> 
    <script src="node_modules/systemjs/dist/system.src.js"></script> 
    <script src="node_modules/rxjs/bundles/Rx.js"></script> 
    <script src="node_modules/angular2/bundles/angular2.dev.js"></script> 

    <script src="https://code.jquery.com/jquery-2.2.1.min.js" ></script> 
    <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/materialize/0.97.5/css/materialize.min.css"> 
    <script src="https://cdnjs.cloudflare.com/ajax/libs/materialize/0.97.5/js/materialize.min.js"></script> 

    <link rel="stylesheet" href="style.css"></link> 

    <!-- 2. Configure SystemJS --> 
    <script> 
     System.config({ 
     packages: {   
      app: { 
      format: 'register', 
      defaultExtension: 'js' 
      } 
     } 
     }); 
     System.import('app/main') 
      .then(null, console.error.bind(console)); 
    </script> 

    </head> 

    <!-- 3. Display the application --> 
    <body> 
    <my-app>Loading...</my-app> 
    </body> 

</html> 


What did I do wrong? 


    [1]: http://i.stack.imgur.com/i06n3.png 

ответ

2
  1. Элемент ввода имеет обработчик размытия, который имеет приоритет (мое понимание) над событием клика над элементом с элементом li. Когда вы нажмете на подсказки авто, браузер активирует событие onblur, которое сбросит filterList в вашем AppComponent.

  2. Сброс отфильтрованного списка приведет к удалению списка автоматического предложения из dom, поскольку вы использовали * ngIf в шаблоне, тем самым аннулировав событие click. Таким образом, событие click никогда не будет вызываться.

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

  4. Я предлагаю использовать (mousedown) вместо (щелчок) на анкерном элементе. Также в обработчике событий mousedown используйте event.stopPropagation, поэтому ваш список автозапусков не потеряет фокус.

    select(event,item) { 
        this.query = item; 
        this.filteredList = []; 
        this.selectedIdx = -1; 
        event.stopPropagation(); 
        } 
    

<div class="container"> 
 
    <div class="input-field col s12"> 
 
    <input id="country" type="text" class="validate filter-input" [(ngModel)]=query (keyup)=filter($event) (blur)="handleBlur()"> 
 
    <div class="suggestions" *ngIf="filteredList.length > 0"> 
 
     <ul> 
 
     <li *ngFor="let item of filteredList;let idx = index" [class.complete-selected]="idx == selectedIdx" 
 
      (mousedown)="select($event,item)"> 
 
      {{item}} 
 
     </li> 
 
     </ul> 
 
    </div> 
 
    </div> 
 
    <label for="country">Country</label> 
 
</div>

Надеется, что это помогает.

1

Я создал модуль для Angular2 Auto complete. Он принимает Array, URL, массив внутри объекта или массив объектов в качестве входных данных. Вы также можете добавить пользовательский CSS для стилирования элемента управления. Пример использования и ссылка для скачивания можно найти по адресу: ang2-autocomplete

Смежные вопросы