pIvan / ngx-color-picker

Pure Angular color picker library.
MIT License
96 stars 16 forks source link

Error on writing to signals on first open #83

Closed elementalTIMING closed 5 months ago

elementalTIMING commented 5 months ago

HI,

since the update to Angular 17 I get the following error message when initiating the color picker.

Error: NG0600: Writing to signals is not allowed in a `computed` or an `effect` by default. Use `allowSignalWrites` in the `CreateEffectOptions` to enable this inside effects.
    at core.mjs:31253:15
    at throwInvalidWriteToSignalError (signals.mjs:407:5)
    at signalSetFn (signals.mjs:444:9)
    at getter.set (core.mjs:17192:26)
    at Object.next (iplab-ngx-color-picker.mjs:1642:24)
    at ConsumerObserver.next (Subscriber.js:91:33)
    at SafeSubscriber._next (Subscriber.js:60:26)
    at SafeSubscriber.next (Subscriber.js:31:18)
    at distinctUntilChanged.js:14:28
    at OperatorSubscriber._next (OperatorSubscriber.js:13:21)

The error is shown when the component is initialized the first time. It also is shown in "template" mode only, like:

<sketch-picker [(color)]="color[key]"></sketch-picker>

The usage with <chrome-picker [control]="ColorPickerControl"> is fine, but the use of ColorPickerControl is no option.

Please can you fix it?

pIvan commented 5 months ago

Hi @elementalTIMING, it will be fixed today

elementalTIMING commented 5 months ago

Hi @elementalTIMING, it will be fixed today

Great! Thx!

pIvan commented 5 months ago

I can't reproduce it, can you try this code in the demo page? Or is it possible to send me a wider context, that is, the code in which this component is located?

pIvan commented 5 months ago

can you send me a picture of this line of code in lib 1642? "line at Object.next (iplab-ngx-color-picker.mjs:1642:24)"

elementalTIMING commented 5 months ago

I can't reproduce it, can you try this code in the demo page? Or is it possible to send me a wider context, that is, the code in which this component is located?

not really. I just have Angular 17 (meanwhile 18) installed and call it as shown it here

<sketch-picker [(color)]="color[key]"></sketch-picker>

Well, this needs to be done

computed(() => {
    ....
}, { allowSignalWrites: true })
image
pIvan commented 5 months ago

I don't have computed() anywhere in the code, also none of the effects I have used, does not use a signal to set the color

elementalTIMING commented 5 months ago

I don't have computed() anywhere in the code, also none of the effects I have used, does not use a signal to set the color

Wow, that' weird, But the error code shows:

Error: NG0600: Writing to signals is not allowed in a `computed` or an `effect` by default. Use `allowSignalWrites` in the `CreateEffectOptions` to enable this inside effects.
    at core.mjs:32182:15
    at throwInvalidWriteToSignalError (signals.mjs:414:5)
    at signalSetFn (signals.mjs:451:9)
    at getter.set (core.mjs:18076:26)
    at Object.next (iplab-ngx-color-picker.mjs:1642:24)
    at ConsumerObserver.next (Subscriber.js:91:33)
    at SafeSubscriber._next (Subscriber.js:60:26)
    at SafeSubscriber.next (Subscriber.js:31:18)
    at distinctUntilChanged.js:14:28
    at OperatorSubscriber._next (OperatorSubscriber.js:13:21)

If I follow this code, then the issue comes from here

image
pIvan commented 5 months ago

Thanks, It would be great if you could give me more context for ng-template so I can write test scenarios very fast! :)

elementalTIMING commented 5 months ago

Thanks, It would be great if you could give me more context for ng-template so I can write test scenarios very fast! :)

Well, that's easy to do :-) This is the code fragment from where I call it. Pls, don't be confused about the form. It doesn't have a real function yet. The popover comes from Valor Bootstrap (https://valor-software.com/ngx-bootstrap/#/components/popover?tab=overview#popover-context)

<form #form="ngForm">
    <div class="form-row">
        <div class="col-12">
            <h6>Background Color</h6>
            <div class="row align-middle">
                <label class="col-3 col-form-label col-form-label-sm">Grid Color</label>
                <div class="col-1">
                    <div class="single-color border" [ngStyle]="{ 'background-color': lapCounterData.gridColor }" title="Grid Color" [popover]="popColorTemplate" [popoverContext]="{ color: lapCounterData, key: 'gridColor' }" [outsideClick]="true">&nbsp;</div>
                </div>
            </div>
        </div>
    </div>
</form>

The lapCounterData data structure looks like this:

/** the data model with the scoreboard user profile settings */
public lapCounterData: ILapCounterSettings;

export interface ILapCounterSettings {
    laneColors: ILapCounterSkater[];

    isShowSkaterNames: boolean;
    isShowIcons: boolean;
    logo: string;

    bgColor: string;
    gridColor: string;
    gridSize: number;
}

So what I'm doing is to use the lapCounterData.gridColor property for the color picker. Hopefully, this information gives you some ideas.

pIvan commented 5 months ago

Thank you very much, it will be helpful for me to write a test scenario, I can see where the problem is, the effect reacts to the input binding, and also then via the subject I emit a change on the control which again sets the value on the signal in the circuit. Although it can't go round because of the distinct check, I'll change the logic a bit

elementalTIMING commented 5 months ago

Thank you very much, it will be helpful for me to write a test scenario, I can see where the problem is, the effect reacts to the input binding, and also then via the subject I emit a change on the control which again sets the value on the signal in the circuit

Good to hear that my input was a bit helpful. I'm crossing my fingers that you'll be able to provide a fix. :-)

elementalTIMING commented 5 months ago

It works like a charm now again! Thx a lot!

pIvan commented 5 months ago

Also version 18 is available ;)

elementalTIMING commented 5 months ago

Installed and quick tested. Works! :-)