Skip to content

Commit

Permalink
fix(select): using string.match not regexp.test (fixes #57, fixes #54,
Browse files Browse the repository at this point in the history
…fixes #56)

* Using string.match not regexp.test

* Added stripTags to filtering values

* Fixed line breaking on city array

* Backed out child filter change

* fixed highlights and slect value display

* fixed lint errors

* Added RichDemo example
  • Loading branch information
kfbishop authored and valorkin committed Apr 11, 2016
1 parent a9e0370 commit 5c96c2d
Show file tree
Hide file tree
Showing 6 changed files with 175 additions and 16 deletions.
23 changes: 20 additions & 3 deletions components/select/select-pipes.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,12 +11,29 @@ export class HightlightPipe {

let query = args[0];

return query ?
value.replace(new RegExp(this.escapeRegexp(query), 'gi'), '<strong>$&</strong>') :
value;
if ( query ) {
let tagRE = new RegExp('<[^<>]*>', 'ig');
// get ist of tags
let tagList = value.match( tagRE );
// Replace tags with token
let tmpValue = value.replace( tagRE, '$!$');
// Replace search words
value = tmpValue.replace(new RegExp(this.escapeRegexp(query), 'gi'), '<strong>$&</strong>');
// Reinsert HTML
for (let i = 0; value.indexOf('$!$') > -1; i++) {
value = value.replace('$!$', tagList[i]);
}
}
return value;
}

private escapeRegexp(queryToEscape:string) {
return queryToEscape.replace(/([.?*+^$[\]\\(){}|-])/g, '\\$1');
}
}

export function stripTags(input:string) {
let tags = /<\/?([a-z][a-z0-9]*)\b[^>]*>/gi,
commentsAndPhpTags = /<!--[\s\S]*?-->|<\?(?:php)?[\s\S]*?\?>/gi;
return input.replace(commentsAndPhpTags, '').replace(tags, '');
}
20 changes: 15 additions & 5 deletions components/select/select.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,10 @@ import {
NgStyle
} from 'angular2/common';
import {SelectItem} from './select-item';
import {HightlightPipe} from './select-pipes';
import {
HightlightPipe,
stripTags
} from './select-pipes';
import {IOptionsBehavior} from './select-interfaces';

let optionsTemplate = `
Expand Down Expand Up @@ -68,7 +71,8 @@ let optionsTemplate = `
style="outline: 0;">
<span *ngIf="active.length <= 0" class="ui-select-placeholder text-muted">{{placeholder}}</span>
<span *ngIf="active.length > 0" class="ui-select-match-text pull-left"
[ngClass]="{'ui-select-allow-clear': allowClear && active.length > 0}">{{active[0].text}}</span>
[ngClass]="{'ui-select-allow-clear': allowClear && active.length > 0}"
[innerHTML]="active[0].text"></span>
<i class="dropdown-toggle pull-right"></i>
<i class="caret pull-right"></i>
<a *ngIf="allowClear && active.length>0" style="margin-right: 10px; padding: 0;"
Expand Down Expand Up @@ -170,8 +174,10 @@ export class Select {
private focusToInput(value:string = '') {
setTimeout(() => {
let el = this.element.nativeElement.querySelector('div.ui-select-container > input');
el.focus();
el.value = value;
if (el) {
el.focus();
el.value = value;
}
}, 0);
}

Expand Down Expand Up @@ -417,6 +423,7 @@ export class Select {
if (this.multiple === true) {
this.focusToInput('');
} else {
this.focusToInput( stripTags(value.text) );
this.element.nativeElement.querySelector('.ui-select-container').focus();
}
}
Expand Down Expand Up @@ -518,7 +525,7 @@ export class GenericBehavior extends Behavior implements IOptionsBehavior {

public filter(query:RegExp) {
let options = this.actor.itemObjects
.filter(option => query.test(option.text) &&
.filter(option => stripTags(option.text).match(query) &&
(this.actor.multiple === false ||
(this.actor.multiple === true &&
this.actor.active.indexOf(option) < 0)));
Expand All @@ -529,6 +536,7 @@ export class GenericBehavior extends Behavior implements IOptionsBehavior {
super.ensureHighlightVisible();
}
}

}

export class ChildrenBehavior extends Behavior implements IOptionsBehavior {
Expand Down Expand Up @@ -618,3 +626,5 @@ export class ChildrenBehavior extends Behavior implements IOptionsBehavior {
}
}
}


8 changes: 7 additions & 1 deletion demo/components/select-section.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import {TAB_DIRECTIVES} from 'ng2-bootstrap/ng2-bootstrap';
import {SingleDemo} from './select/single-demo';
import {MultipleDemo} from './select/multiple-demo';
import {ChildrenDemo} from './select/children-demo';
import {RichDemo} from './select/rich-demo';

let name = 'Select';
// webpack html imports
Expand All @@ -26,6 +27,11 @@ let tabDesc:Array<any> = [
heading: 'Children',
ts: require('!!prismjs?lang=typescript!./select/children-demo.ts'),
html: require('!!prismjs?lang=markup!./select/children-demo.html')
},
{
heading: 'Rich',
ts: require('!!prismjs?lang=typescript!./select/rich-demo.ts'),
html: require('!!prismjs?lang=markup!./select/rich-demo.html')
}
];

Expand Down Expand Up @@ -80,7 +86,7 @@ tabDesc.forEach(desc => {
</div>
</section>
`,
directives: [SingleDemo, MultipleDemo, ChildrenDemo, TAB_DIRECTIVES, CORE_DIRECTIVES]
directives: [SingleDemo, MultipleDemo, ChildrenDemo, RichDemo, TAB_DIRECTIVES, CORE_DIRECTIVES]
})
export class SelectSection {
public currentHeading:string = 'Single';
Expand Down
21 changes: 21 additions & 0 deletions demo/components/select/rich-demo.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
<div style="width: 300px; margin-bottom: 20px;">
<h3>Select a color</h3>
<ng-select [allowClear]="true"
[items]="items"
[disabled]="disabled"
(data)="refreshValue($event)"
(selected)="selected($event)"
(removed)="removed($event)"
(typed)="typed($event)"
placeholder="No color selected">
</ng-select>
<p></p>
<pre>{{value.text}}</pre>
<div>
<button type="button" class="btn btn-primary"
[(ngModel)]="disabledV" btnCheckbox
btnCheckboxTrue="1" btnCheckboxFalse="0">
{{disabled === '1' ? 'Enable' : 'Disable'}}
</button>
</div>
</div>
104 changes: 104 additions & 0 deletions demo/components/select/rich-demo.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,104 @@
import {
Component,
OnInit,
ViewEncapsulation
} from 'angular2/core';
import {CORE_DIRECTIVES, FORM_DIRECTIVES, NgClass} from 'angular2/common';
import {ButtonCheckbox} from 'ng2-bootstrap/ng2-bootstrap';

import {SELECT_DIRECTIVES} from '../../../ng2-select';

const COLORS = [
{ 'name': 'Blue 10', 'hex': '#C0E6FF' },
{ 'name': 'Blue 20', 'hex': '#7CC7FF' },
{ 'name': 'Blue 30', 'hex': '#5AAAFA' },
{ 'name': 'Blue 40', 'hex': '#5596E6' },
{ 'name': 'Blue 50', 'hex': '#4178BE' },
{ 'name': 'Blue 60', 'hex': '#325C80' },
{ 'name': 'Blue 70', 'hex': '#264A60' },
{ 'name': 'Blue 80', 'hex': '#1D3649' },
{ 'name': 'Blue 90', 'hex': '#152935' },
{ 'name': 'Blue 100', 'hex': '#010205' },
{ 'name': 'Green 10', 'hex': '#C8F08F' },
{ 'name': 'Green 20', 'hex': '#B4E051' },
{ 'name': 'Green 30', 'hex': '#8CD211' },
{ 'name': 'Green 40', 'hex': '#5AA700' },
{ 'name': 'Green 50', 'hex': '#4B8400' },
{ 'name': 'Green 60', 'hex': '#2D660A' },
{ 'name': 'Green 70', 'hex': '#144D14' },
{ 'name': 'Green 80', 'hex': '#0A3C02' },
{ 'name': 'Green 90', 'hex': '#0C2808' },
{ 'name': 'Green 100', 'hex': '#010200' },
{ 'name': 'Red 10', 'hex': '#FFD2DD' },
{ 'name': 'Red 20', 'hex': '#FFA5B4' },
{ 'name': 'Red 30', 'hex': '#FF7D87' },
{ 'name': 'Red 40', 'hex': '#FF5050' },
{ 'name': 'Red 50', 'hex': '#E71D32' },
{ 'name': 'Red 60', 'hex': '#AD1625' },
{ 'name': 'Red 70', 'hex': '#8C101C' },
{ 'name': 'Red 80', 'hex': '#6E0A1E' },
{ 'name': 'Red 90', 'hex': '#4C0A17' },
{ 'name': 'Red 100', 'hex': '#040001' },
{ 'name': 'Yellow 10', 'hex': '#FDE876' },
{ 'name': 'Yellow 20', 'hex': '#FDD600' },
{ 'name': 'Yellow 30', 'hex': '#EFC100' },
{ 'name': 'Yellow 40', 'hex': '#BE9B00' },
{ 'name': 'Yellow 50', 'hex': '#8C7300' },
{ 'name': 'Yellow 60', 'hex': '#735F00' },
{ 'name': 'Yellow 70', 'hex': '#574A00' },
{ 'name': 'Yellow 80', 'hex': '#3C3200' },
{ 'name': 'Yellow 90', 'hex': '#281E00' },
{ 'name': 'Yellow 100', 'hex': '#020100' }
];

// webpack html imports
let template = require('./rich-demo.html');

@Component({
selector: 'rich-demo',
template: template,
styles: [`colorbox,.colorbox { display:inline-block; height:14px; width:14px;margin-right:4px; border:1px solid #000;}`],
directives: [SELECT_DIRECTIVES, NgClass, CORE_DIRECTIVES, FORM_DIRECTIVES, ButtonCheckbox],
encapsulation: ViewEncapsulation.None // Enable dynamic HTML styles
})
export class RichDemo implements OnInit {
private value:any = {};
private _disabledV:string = '0';
private disabled:boolean = false;
private items:Array<any> = [];

ngOnInit() {
COLORS.forEach( c => {
this.items.push( {
id : c.hex,
text: `<colorbox style='background-color:${c.hex};'></colorbox>${c.name} (${c.hex})`
});
});
}

private get disabledV():string {
return this._disabledV;
}

private set disabledV(value:string) {
this._disabledV = value;
this.disabled = this._disabledV === '1';
}

private selected(value:any) {
console.log('Selected value is: ', value);
}

private removed(value:any) {
console.log('Removed value is: ', value);
}

private typed(value:any) {
console.log('New search input: ', value);
}

private refreshValue(value:any) {
this.value = value;
}
}

15 changes: 8 additions & 7 deletions demo/components/select/single-demo.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,13 +18,14 @@ export class SingleDemo {
private disabled:boolean = false;
private items:Array<string> = ['Amsterdam', 'Antwerp', 'Athens', 'Barcelona',
'Berlin', 'Birmingham', 'Bradford', 'Bremen', 'Brussels', 'Bucharest',
'Budapest', 'Cologne', 'Copenhagen', 'Dortmund', 'Dresden', 'Dublin', 'Düsseldorf',
'Essen', 'Frankfurt', 'Genoa', 'Glasgow', 'Gothenburg', 'Hamburg', 'Hannover',
'Helsinki', 'Leeds', 'Leipzig', 'Lisbon', 'Łódź', 'London', 'Kraków', 'Madrid',
'Málaga', 'Manchester', 'Marseille', 'Milan', 'Munich', 'Naples', 'Palermo',
'Paris', 'Poznań', 'Prague', 'Riga', 'Rome', 'Rotterdam', 'Seville', 'Sheffield',
'Sofia', 'Stockholm', 'Stuttgart', 'The Hague', 'Turin', 'Valencia', 'Vienna',
'Vilnius', 'Warsaw', 'Wrocław', 'Zagreb', 'Zaragoza'];
'Budapest', 'Cologne', 'Copenhagen', 'Dortmund', 'Dresden', 'Dublin',
'Düsseldorf', 'Essen', 'Frankfurt', 'Genoa', 'Glasgow', 'Gothenburg',
'Hamburg', 'Hannover', 'Helsinki', 'Kraków', 'Leeds', 'Leipzig', 'Lisbon',
'London', 'Madrid', 'Manchester', 'Marseille', 'Milan', 'Munich', 'Málaga',
'Naples', 'Palermo', 'Paris', 'Poznań', 'Prague', 'Riga', 'Rome',
'Rotterdam', 'Seville', 'Sheffield', 'Sofia', 'Stockholm', 'Stuttgart',
'The Hague', 'Turin', 'Valencia', 'Vienna', 'Vilnius', 'Warsaw', 'Wrocław',
'Zagreb', 'Zaragoza', 'Łódź'];

private get disabledV():string {
return this._disabledV;
Expand Down

0 comments on commit 5c96c2d

Please sign in to comment.