primereact icon indicating copy to clipboard operation
primereact copied to clipboard

Dropdown: Init-Value not working if options have label,value properties

Open sja-cslab opened this issue 1 year ago • 8 comments

Describe the bug

If Dropdown is filled with {label: string, value: any}[] the inital value isn't selected.

Reproducer

https://stackblitz.com/edit/vitejs-vite-2prkbq?file=src%2FApp.tsx

PrimeReact version

10.6.5

React version

18.x

Language

ALL

Build / Runtime

Vite

Browser(s)

No response

Steps to reproduce the behavior

No response

Expected behavior

No response

sja-cslab avatar May 08 '24 09:05 sja-cslab

I noticed that this is not an error. My problem here is noted in the docs:

If optionValue is omitted and the object has no value property, the object itself becomes the value of an option

So this is more a question than a Bug => How can I get and set the Object, even if it has a value property?

sja-cslab avatar May 08 '24 09:05 sja-cslab

https://stackblitz.com/edit/vitejs-vite-tmd4yk?file=src%2FApp.tsx

I changed your code a bit. This should work.

Rekl0w avatar May 08 '24 10:05 Rekl0w

That works, and I'm using it in other parts of my code. However, now if I need to work with that object, for example, in the onChange event, I need to find it within the options. So, that is an acceptable workaround but not a real solution for that problem.

I guess you want to say, 'you cannot get an object directly from the component if it has a value property,' correct?

sja-cslab avatar May 08 '24 10:05 sja-cslab

value prop is need to work with a state that can be changed but if you give a static value to it, it won't change.

I guess you want to say, 'you cannot get an object directly from the component if it has a value property,' correct?

You can get an object with onChange method but this component is not sets the object directly. It sets the value prop and works with it.

Rekl0w avatar May 08 '24 11:05 Rekl0w

@Rekl0w, I see your point; however, it feels wrong that the component works differently based on how something looks inside.

If I pass, for example, [{foo: "label", bar: "value"}, {foo: "label2", bar: "value2"}] and use optionLabel="foo", I'll get the whole object in onChange. If I rename those bar properties to value, it won't work anymore. I hope you get my point.

@melloware Could we make that to a feature/enhancement request? What about an extra option "workWithObject" or something? :)

sja-cslab avatar May 08 '24 13:05 sja-cslab

Yes this has always been a weird contention with using Object vs Primitive and letting it know which JSON fields you mean to use for value and label.

melloware avatar May 08 '24 13:05 melloware

I would expect that if I do not set optionValue, that I get back whatever I throw in.

sja-cslab avatar May 08 '24 13:05 sja-cslab

@melloware just looked at the code

const getOptionValue = (option) => {
    return props.optionValue ? ObjectUtils.resolveFieldData(option, props.optionValue) : ObjectUtils.resolveFieldData(option, 'value') || option;
};

The question I have here is why it has been decided that it is a good idea to try to resolve option.value if no optionValue is set. Why not just return option then? Without digging deeper, I would expect option to be a primitive if only primitives are available.

sja-cslab avatar May 14 '24 11:05 sja-cslab