mirror of https://github.com/Squidex/squidex.git
9 changed files with 192 additions and 14 deletions
@ -1,22 +1,30 @@ |
|||||
@import '_vars'; |
@import '_vars'; |
||||
@import '_mixins'; |
@import '_mixins'; |
||||
|
|
||||
.languages-buttons { |
|
||||
margin-right: 2rem; |
|
||||
} |
|
||||
|
|
||||
.content { |
.content { |
||||
cursor: pointer; |
cursor: pointer; |
||||
} |
} |
||||
|
|
||||
.btn-group { |
|
||||
margin-left: 1rem; |
|
||||
} |
|
||||
|
|
||||
.icon-plus { |
.icon-plus { |
||||
font-size: .8rem; |
font-size: .8rem; |
||||
} |
} |
||||
|
|
||||
.form-control { |
.form-control { |
||||
width: 15rem; |
width: 20rem; |
||||
} |
} |
||||
|
|
||||
|
.form-inline { |
||||
|
position: relative; |
||||
|
} |
||||
|
|
||||
|
.form-control-expandable { |
||||
|
padding-right: 1.5rem; |
||||
|
} |
||||
|
|
||||
|
.expand-search { |
||||
|
@include absolute(8px, 8px, auto, auto); |
||||
|
color: $color-border-dark !important; |
||||
|
font-size: .9rem; |
||||
|
font-weight: normal; |
||||
|
cursor: pointer !important; |
||||
|
} |
||||
|
|||||
@ -0,0 +1,29 @@ |
|||||
|
<div [formGroup]="searchForm" class="form-horizontal"> |
||||
|
<div class="form-group row"> |
||||
|
<label class="col col-2 col-form-label" for="odataSearch">Text</label> |
||||
|
|
||||
|
<div class="col col-10"> |
||||
|
<input type="input" class="form-control" id="search" (blur)="updateQuery()" formControlName="odataSearch" placeholder="Fulltext search" /> |
||||
|
</div> |
||||
|
</div> |
||||
|
|
||||
|
<div class="form-group row"> |
||||
|
<label class="col col-2 col-form-label" for="filter">Filter</label> |
||||
|
|
||||
|
<div class="col col-10"> |
||||
|
<input type="input" class="form-control" id="filter" (blur)="updateQuery()" formControlName="odataFilter" placeholder="data/[MY_FIELD]/iv eq 100" /> |
||||
|
</div> |
||||
|
</div> |
||||
|
|
||||
|
<div class="form-group row"> |
||||
|
<label class="col col-2 col-form-label" for="orderBy">Order</label> |
||||
|
|
||||
|
<div class="col col-10"> |
||||
|
<input type="input" class="form-control" id="orderBy" (blur)="updateQuery()" formControlName="odataOrderBy" placeholder="data/[MY_FIELD]/iv desc" /> |
||||
|
</div> |
||||
|
</div> |
||||
|
|
||||
|
<div class="link"> |
||||
|
Read more about filtering in the <a href="https://docs.squidex.io/04-guides/02-api.html" target="_blank">Documentation</a>. |
||||
|
</div> |
||||
|
</div> |
||||
@ -0,0 +1,18 @@ |
|||||
|
@import '_vars'; |
||||
|
@import '_mixins'; |
||||
|
|
||||
|
.form-horizontal { |
||||
|
padding: 1rem 1.5rem; |
||||
|
min-width: 25rem; |
||||
|
max-width: 25rem; |
||||
|
} |
||||
|
|
||||
|
.link { |
||||
|
margin-top: 1.5rem; |
||||
|
font-size: .8rem; |
||||
|
font-weight: normal; |
||||
|
} |
||||
|
|
||||
|
.col-form-label { |
||||
|
text-align: left; |
||||
|
} |
||||
@ -0,0 +1,109 @@ |
|||||
|
/* |
||||
|
* Squidex Headless CMS |
||||
|
* |
||||
|
* @license |
||||
|
* Copyright (c) Sebastian Stehle. All rights reserved |
||||
|
*/ |
||||
|
|
||||
|
import { Component, EventEmitter, Input, OnChanges, Output } from '@angular/core'; |
||||
|
import { FormBuilder } from '@angular/forms'; |
||||
|
|
||||
|
@Component({ |
||||
|
selector: 'sqx-search-form', |
||||
|
styleUrls: ['./search-form.component.scss'], |
||||
|
templateUrl: './search-form.component.html' |
||||
|
}) |
||||
|
export class SearchFormComponent implements OnChanges { |
||||
|
private queryValue = ''; |
||||
|
|
||||
|
@Input() |
||||
|
public query = ''; |
||||
|
|
||||
|
@Output() |
||||
|
public queryChanged = new EventEmitter(); |
||||
|
|
||||
|
public searchForm = |
||||
|
this.formBuilder.group({ |
||||
|
odataOrderBy: '', |
||||
|
odataFilter: '', |
||||
|
odataSearch: '' |
||||
|
}); |
||||
|
|
||||
|
constructor( |
||||
|
private readonly formBuilder: FormBuilder |
||||
|
) { |
||||
|
} |
||||
|
|
||||
|
public ngOnChanges() { |
||||
|
if (this.query === this.queryValue) { |
||||
|
return; |
||||
|
} |
||||
|
|
||||
|
let odataOrderBy = ''; |
||||
|
let odataFilter = ''; |
||||
|
let odataSearch = ''; |
||||
|
|
||||
|
const parts = this.query.split('&'); |
||||
|
|
||||
|
if (parts.length === 1 && parts[0][0] !== '$') { |
||||
|
odataSearch = parts[0]; |
||||
|
} else { |
||||
|
for (let part of parts) { |
||||
|
const kvp = part.split('='); |
||||
|
|
||||
|
if (kvp.length === 2) { |
||||
|
const key = kvp[0].toLowerCase(); |
||||
|
|
||||
|
if (key === '$filter') { |
||||
|
odataFilter = kvp[1]; |
||||
|
} else if (key === '$orderby') { |
||||
|
odataOrderBy = kvp[1]; |
||||
|
} else if (key === '$search') { |
||||
|
odataSearch = kvp[1]; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
this.searchForm.setValue({ |
||||
|
odataFilter, |
||||
|
odataSearch, |
||||
|
odataOrderBy |
||||
|
}, { emitEvent: false }); |
||||
|
|
||||
|
this.queryValue = this.query; |
||||
|
} |
||||
|
|
||||
|
public updateQuery() { |
||||
|
const odataOrderBy = this.searchForm.controls['odataOrderBy'].value; |
||||
|
const odataFilter = this.searchForm.controls['odataFilter'].value; |
||||
|
const odataSearch = this.searchForm.controls['odataSearch'].value; |
||||
|
|
||||
|
let query = ''; |
||||
|
|
||||
|
if (odataSearch && !odataOrderBy && !odataFilter) { |
||||
|
query = odataSearch; |
||||
|
} else { |
||||
|
const parts: string[] = []; |
||||
|
|
||||
|
if (odataSearch) { |
||||
|
parts.push(`$search=${odataSearch}`); |
||||
|
} |
||||
|
|
||||
|
if (odataFilter) { |
||||
|
parts.push(`$filter=${odataFilter}`); |
||||
|
} |
||||
|
|
||||
|
if (odataOrderBy) { |
||||
|
parts.push(`$orderby=${odataOrderBy}`); |
||||
|
} |
||||
|
|
||||
|
query = parts.join('&'); |
||||
|
} |
||||
|
|
||||
|
if (query !== this.query) { |
||||
|
this.queryValue = query; |
||||
|
this.queryChanged.emit(query); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
Loading…
Reference in new issue