2020-10-13 12:54:14 +00:00
|
|
|
import {Component, Input, OnInit, ViewChild} from '@angular/core';
|
|
|
|
import {IonInput, ModalController} from '@ionic/angular';
|
|
|
|
import {ApiService} from '../../service/api.service';
|
|
|
|
import {BehaviorSubject} from 'rxjs';
|
|
|
|
import {Router} from '@angular/router';
|
|
|
|
|
|
|
|
export interface SearchResult {
|
|
|
|
title: string;
|
|
|
|
short_title: string;
|
2020-10-13 14:25:03 +00:00
|
|
|
type: 'page' | 'node' | 'code';
|
2020-10-13 12:54:14 +00:00
|
|
|
id: string;
|
|
|
|
associated?: {
|
|
|
|
title: string,
|
2020-10-13 14:25:03 +00:00
|
|
|
type: 'page',
|
2020-10-13 12:54:14 +00:00
|
|
|
id: string
|
|
|
|
};
|
|
|
|
}
|
|
|
|
|
|
|
|
@Component({
|
|
|
|
selector: 'noded-search-modal',
|
|
|
|
templateUrl: './Search.component.html',
|
|
|
|
styleUrls: ['./Search.component.scss'],
|
|
|
|
})
|
|
|
|
export class SearchComponent implements OnInit {
|
|
|
|
@ViewChild('ionInput') ionInput: IonInput;
|
|
|
|
@Input() query = '';
|
|
|
|
public results: BehaviorSubject<SearchResult[]> = new BehaviorSubject<SearchResult[]>([]);
|
|
|
|
|
|
|
|
public typeIcons = {
|
|
|
|
node: 'fa fa-quote-left',
|
|
|
|
page: 'fa fa-sticky-note',
|
|
|
|
db: 'fa fa-database',
|
2020-10-13 14:25:03 +00:00
|
|
|
code: 'fa fa-code',
|
2020-10-13 12:54:14 +00:00
|
|
|
};
|
|
|
|
|
|
|
|
constructor(
|
|
|
|
protected modal: ModalController,
|
|
|
|
protected api: ApiService,
|
|
|
|
protected router: Router,
|
|
|
|
) { }
|
|
|
|
|
|
|
|
async dismiss() {
|
|
|
|
await this.modal.dismiss();
|
|
|
|
}
|
|
|
|
|
|
|
|
ngOnInit() {
|
|
|
|
setTimeout(() => {
|
|
|
|
this.ionInput.setFocus();
|
|
|
|
}, 750);
|
|
|
|
}
|
|
|
|
|
|
|
|
async onSearchChange($event) {
|
|
|
|
const query = $event.detail.value;
|
|
|
|
this.results.next(await this.search(query));
|
|
|
|
}
|
|
|
|
|
|
|
|
async search(query): Promise<SearchResult[]> {
|
|
|
|
return new Promise(resolve => {
|
|
|
|
this.api.get(`/search?query=${query}`).subscribe(res => {
|
|
|
|
resolve(res.data.results as SearchResult[]);
|
|
|
|
});
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
|
|
|
async openResult(result: SearchResult) {
|
|
|
|
if ( result.type === 'page' ) {
|
|
|
|
await this.router.navigate(['/editor', { id: result.id }]);
|
|
|
|
await this.dismiss();
|
|
|
|
} else if ( result.type === 'node' ) {
|
|
|
|
await this.router.navigate(['/editor', { id: result.associated.id, node_id: result.id }]);
|
|
|
|
await this.dismiss();
|
2020-10-13 14:25:03 +00:00
|
|
|
} else if ( result.type === 'code' ) {
|
|
|
|
await this.router.navigate(['/editor', { id: result.associated.id, node_id: result.id }]);
|
|
|
|
await this.dismiss();
|
2020-10-13 12:54:14 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
async openRelated(event, result: SearchResult) {
|
|
|
|
event.preventDefault();
|
|
|
|
event.stopPropagation();
|
|
|
|
|
|
|
|
if ( result.associated ) {
|
|
|
|
if ( result.associated.type === 'page' ) {
|
|
|
|
await this.router.navigate(['/editor', { id: result.associated.id }]);
|
|
|
|
await this.dismiss();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|