SolidJSS
SolidJS2y ago
13 replies
daalfox

Reactive field inside objects of an array

import {
  Accessor,
  ParentComponent,
  Setter,
  createContext,
  createEffect,
  createSignal
} from 'solid-js'

class Cart {
  get: Accessor<Array<CartItem>>
  private set: Setter<Array<CartItem>>
  constructor(items = []) {
    ;[this.get, this.set] = createSignal<Array<CartItem>>(items)
  }

  add(id: number) {
    let item = this.get().find((item) => item.id === id)

    if (item === undefined) {
      this.set((prev) => [...prev, new CartItem(id)])
    } else {
      throw Error('item already exists')
    }
  }
  remove(id: number) {
    this.set((prev) =>
      prev.toSpliced(
        prev.findIndex((item) => item.id === id),
        1
      )
    )
  }
}

class CartItem {
  id: number
  count: number

  constructor(id: number) {
    this.id = id
    this.count = 1
  }

  increment() {
    this.count++
  }
  decrement() {
    if (this.count > 1) {
      this.count--
    } else {
      throw Error(`count is ${this.count}, can't decrement more`)
    }
  }
}

export const cartContext = createContext(new Cart())

export const Provider: ParentComponent = (props) => {
  const cart = new Cart()
  createEffect(() => {
    console.log(cart.get()) // I want this to update when I update `CartItem`'s count
  })
  return <cartContext.Provider value={cart}>{props.children}</cartContext.Provider>
}

How do I achieve this (line 62)?
Basically I want a reactive field inside objects of an array which update the array itself when they change
Was this page helpful?