Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -559,6 +559,48 @@ describe('PoComboBaseComponent:', () => {
expect(component.callModelChange).not.toHaveBeenCalled();
expect(component['fromWriteValue']).toBe(false);
});

describe('controlValueWithLabel', () => {
it('should return the object when controlValueWithLabel is true', () => {
const selectedOption = { value: 1, label: 'Xpto' };

component.controlValueWithLabel = true;

expect(component['getValueUpdate'](1, selectedOption)).toEqual(selectedOption);
});

it('should only return the value when controlValueWithLabel is false', () => {
const selectedOption = { value: 1, label: 'Xpto' };

component.controlValueWithLabel = false;

expect(component['getValueUpdate'](1, selectedOption)).toEqual(1);
});

it('should return a {value: any, label: any} object when controlValueWithLabel is true and both fieldValue and fieldLabel are set', () => {
const selectedOption = { value: 1, label: 'Xpto' };

component.controlValueWithLabel = true;
component.fieldValue = 'id';
component.fieldLabel = 'name';

expect(component['getValueUpdate'](null, selectedOption)).toEqual({ value: 1, label: 'Xpto' });
});

it('should only return the value when calling getValueWrite when controlValueWithLabel is true', () => {
component.controlValueWithLabel = true;
const option = { value: 1, label: 'Xpto' };

expect(component['getValueWrite'](option)).toEqual(1);
});

it('should return when calling getValueWrite when controlValueWithLabel is true and the object structure does not contain the value property', () => {
component.controlValueWithLabel = true;
const data = 1;

expect(component['getValueWrite'](data)).toEqual(data);
});
});
});

describe('Methods:', () => {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -334,6 +334,13 @@ export abstract class PoComboBaseComponent implements ControlValueAccessor, OnIn
*/
@Output('p-input-change') inputChange: EventEmitter<string> = new EventEmitter<string>();

/**
* @docsPrivate
*
* Determinar se o valor do compo deve retorna objeto do tipo {value: any, label: any}
*/
@Input({ alias: 'p-control-value-with-label', transform: convertToBoolean }) controlValueWithLabel?: boolean = false;

cacheOptions: Array<any> = [];
defaultService: PoComboFilterService;
firstInWriteValue: boolean = true;
Expand Down Expand Up @@ -936,6 +943,7 @@ export abstract class PoComboBaseComponent implements ControlValueAccessor, OnIn

// Recebe as alterações do model
writeValue(value: any) {
value = this.getValueWrite(value);
this.fromWriteValue = true;

if (validValue(value) && !this.service && this.comboOptionsList && this.comboOptionsList.length) {
Expand Down Expand Up @@ -1067,6 +1075,27 @@ export abstract class PoComboBaseComponent implements ControlValueAccessor, OnIn
};
}

private getValueUpdate(data: any, selectedOption: any) {
const { [this.dynamicValue]: value, [this.dynamicLabel]: label } = selectedOption || {};

if (this.controlValueWithLabel && value) {
return {
value,
label
};
}

return data;
}

private getValueWrite(data: any) {
if (this.controlValueWithLabel && data?.value) {
return data?.value;
}

return data;
}

private hasDuplicatedOption(options: Array<any>, currentOption: string, accumulatedGroupOptions?: Array<any>) {
if (accumulatedGroupOptions) {
return accumulatedGroupOptions.some(option => option[this.dynamicLabel] === currentOption);
Expand Down Expand Up @@ -1180,7 +1209,7 @@ export abstract class PoComboBaseComponent implements ControlValueAccessor, OnIn
private updateModel(value: any): void {
if (value !== this.selectedValue) {
if (!this.fromWriteValue) {
this.callModelChange(value);
this.callModelChange(this.getValueUpdate(value, this.selectedOption));
}

this.change.emit(this.emitObjectValue ? this.selectedOption : value);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -277,7 +277,8 @@ describe('PoMultiselectBaseComponent:', () => {
const fakeThis = {
onModelChange: v => {},
eventChange: v => {},
getValuesFromOptions: v => []
getValuesFromOptions: v => [],
getValueUpdate: v => []
};

spyOn(fakeThis, 'onModelChange');
Expand Down Expand Up @@ -703,4 +704,47 @@ describe('PoMultiselectBaseComponent:', () => {
expect(component.debounceTime).toBe(600);
});
});

describe('controlValueWithLabel', () => {
it('should return the object when controlValueWithLabel is true', () => {
const selectedOptions = [{ value: 1, label: 'Xpto' }];

component.controlValueWithLabel = true;

expect(component['getValueUpdate'](selectedOptions)).toEqual(selectedOptions);
});

it('should only return the value when controlValueWithLabel is false', () => {
const selectedOptions = [{ value: 1, label: 'Xpto' }];

component.controlValueWithLabel = false;

expect(component['getValueUpdate'](selectedOptions)).toEqual([1]);
});

it('should return a {value: any, label: any} object when controlValueWithLabel is true and both fieldValue and fieldLabel are set', () => {
const selectedOptions = [{ id: 1, name: 'Xpto' }];

component.controlValueWithLabel = true;
component.fieldValue = 'id';
component.fieldLabel = 'name';

expect(component['getValueUpdate'](selectedOptions)).toEqual([{ value: 1, label: 'Xpto' }]);
});

it('should only return the value when calling getValueWrite when controlValueWithLabel is true', () => {
component.controlValueWithLabel = true;
const option = [{ value: 1, label: 'Xpto' }];

expect(component['getValueWrite'](option)).toEqual([1]);
});

it('should return when calling getValueWrite when controlValueWithLabel is true and the object structure does not contain the value property', () => {
const option = [{ id: 1, name: 'Xpto' }];

component.controlValueWithLabel = true;

expect(component['getValueWrite'](option)).toEqual(option);
});
});
});
Original file line number Diff line number Diff line change
Expand Up @@ -257,6 +257,13 @@ export abstract class PoMultiselectBaseComponent implements ControlValueAccessor
*/
@Input({ alias: 'p-append-in-body', transform: convertToBoolean }) appendBox?: boolean = false;

/**
* @docsPrivate
*
* Determinar se o valor do compo deve retorna objeto do tipo {value: any, label: any}
*/
@Input({ alias: 'p-control-value-with-label', transform: convertToBoolean }) controlValueWithLabel?: boolean = false;

selectedOptions: Array<PoMultiselectOption | any> = [];
visibleOptionsDropdown: Array<PoMultiselectOption | any> = [];
visibleTags = [];
Expand Down Expand Up @@ -687,7 +694,7 @@ export abstract class PoMultiselectBaseComponent implements ControlValueAccessor

callOnChange(selectedOptions: Array<PoMultiselectOption | any>) {
if (this.onModelChange) {
this.onModelChange(this.getValuesFromOptions(selectedOptions));
this.onModelChange(this.getValueUpdate(selectedOptions));
this.eventChange(selectedOptions);
}
}
Expand Down Expand Up @@ -780,7 +787,7 @@ export abstract class PoMultiselectBaseComponent implements ControlValueAccessor
}

writeValue(values: any): void {
values = values || [];
values = this.getValueWrite(values) || [];

if (this.service && values.length) {
this.getObjectsByValuesSubscription = this.service.getObjectsByValues(values).subscribe(options => {
Expand Down Expand Up @@ -815,6 +822,22 @@ export abstract class PoMultiselectBaseComponent implements ControlValueAccessor
this.validatorChange = fn;
}

private getValueUpdate(selectedOptions: Array<PoMultiselectOption | any>) {
if (this.controlValueWithLabel && selectedOptions?.length) {
return selectedOptions.map(option => ({ value: option[this.fieldValue], label: option[this.fieldLabel] }));
}

return this.getValuesFromOptions(selectedOptions);
}

private getValueWrite(data: any) {
if (this.controlValueWithLabel && data?.length && data.every(x => x?.value !== undefined)) {
return data.map(option => option.value);
}

return data;
}

private setLabelsAndValuesOptions() {
if (this.fieldLabel && this.fieldValue && this.options) {
this.options.map(option => {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import { ComponentFixture, TestBed } from '@angular/core/testing';
import { FormsModule } from '@angular/forms';

import * as UtilsFunctions from '../../../utils/util';
import { configureTestSuite, expectPropertiesValues, expectSettersMethod } from './../../../util-test/util-expect.spec';
import { configureTestSuite, expectSettersMethod } from './../../../util-test/util-expect.spec';

import { removeDuplicatedOptions, removeUndefinedAndNullOptions } from '../../../utils/util';
import { PoFieldContainerComponent } from '../po-field-container/po-field-container.component';
Expand All @@ -16,9 +16,6 @@ describe('PoSelectComponent:', () => {
let component: PoSelectComponent;
let fixture: ComponentFixture<PoSelectComponent>;
let nativeElement;
const booleanValidFalseValues = [false, 'false'];
const booleanValidTrueValues = [true, 'true', ''];
const booleanInvalidValues = [undefined, null, 2, 'string'];

const event = new MouseEvent('click', { 'bubbles': false, 'cancelable': true });

Expand Down Expand Up @@ -152,7 +149,8 @@ describe('PoSelectComponent:', () => {
selectedValue: '',
displayValue: label => {},
updateModel: value => {},
emitChange: value => {}
emitChange: value => {},
getValueUpdate: value => {}
};

spyOn(fakeThis, 'emitChange');
Expand Down Expand Up @@ -498,4 +496,46 @@ describe('PoSelectComponent:', () => {
expect(component.fieldLabel).toEqual(defaultLabel);
});
});

describe('controlValueWithLabel', () => {
it('should return the object when controlValueWithLabel is true', () => {
const option = { value: 1, label: 'Xpto' };

component.controlValueWithLabel = true;

expect(component['getValueUpdate'](option)).toEqual(option);
});

it('should only return the value when controlValueWithLabel is false', () => {
const option = { value: 1, label: 'Xpto' };

component.controlValueWithLabel = false;

expect(component['getValueUpdate'](option)).toEqual(1);
});

it('should return a {value: any, label: any} object when controlValueWithLabel is true and both fieldValue and fieldLabel are set', () => {
const option = { id: 1, name: 'Xpto' };

component.controlValueWithLabel = true;
component.fieldValue = 'id';
component.fieldLabel = 'name';

expect(component['getValueUpdate'](option)).toEqual({ value: 1, label: 'Xpto' });
});

it('should only return the value when calling getValueWrite when controlValueWithLabel is true', () => {
component.controlValueWithLabel = true;
const option = { value: 1, label: 'Xpto' };

expect(component['getValueWrite'](option)).toEqual(1);
});

it('should return when calling getValueWrite when controlValueWithLabel is true and the object structure does not contain the value property', () => {
component.controlValueWithLabel = true;
const data = 1;

expect(component['getValueWrite'](data)).toEqual(data);
});
});
});
Original file line number Diff line number Diff line change
Expand Up @@ -274,6 +274,13 @@ export class PoSelectComponent extends PoFieldValidateModel<any> implements OnCh
}
}

/**
* @docsPrivate
*
* Determinar se o valor do compo deve retorna objeto do tipo {value: any, label: any}
*/
@Input({ alias: 'p-control-value-with-label', transform: convertToBoolean }) controlValueWithLabel?: boolean = false;

get fieldValue() {
return this._fieldValue;
}
Expand Down Expand Up @@ -364,14 +371,15 @@ export class PoSelectComponent extends PoFieldValidateModel<any> implements OnCh
if (this.selectedValue !== option[this.fieldValue]) {
this.selectedValue = option[this.fieldValue];
this.selectElement.nativeElement.value = option[this.fieldValue];
this.updateModel(option[this.fieldValue]);
this.updateModel(this.getValueUpdate(option));
this.displayValue = option[this.fieldLabel];
this.emitChange(option[this.fieldValue]);
}
}

// Recebe as alterações do model
onWriteValue(value: any) {
value = this.getValueWrite(value);
const optionFound: any = this.findOptionValue(value);

if (optionFound) {
Expand Down Expand Up @@ -454,6 +462,25 @@ export class PoSelectComponent extends PoFieldValidateModel<any> implements OnCh
}
}

private getValueUpdate(option: any) {
if (this.controlValueWithLabel) {
return {
value: option[this.fieldValue],
label: option[this.fieldLabel]
};
}

return option[this.fieldValue];
}

private getValueWrite(data: any) {
if (this.controlValueWithLabel && data?.value) {
return data?.value;
}

return data;
}

private transformInArray(objectWithArray: Array<any>): Array<PoSelectOptionGroup | any> {
return objectWithArray.reduce((options, items) => {
if (items.options) {
Expand Down
Loading