Skip to content

Commit

Permalink
Fix is.equ obj:shallow, allow it to test arrays 1 level deep, fix can…
Browse files Browse the repository at this point in the history
…vas.camera prop being stale
  • Loading branch information
drcmda committed Mar 4, 2023
1 parent 2850fdf commit 99fef6c
Show file tree
Hide file tree
Showing 4 changed files with 28 additions and 5 deletions.
6 changes: 5 additions & 1 deletion example/src/demos/Test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,13 +16,17 @@ function Test() {
}, [])

useFrame((state) => {
console.log(state.pointer.x)
//console.log(state.pointer.x)
})

return <primitive object={which ? o1 : o2} />
}

export default function App() {
const [foo, bar] = useState(0)
useEffect(() => {
setTimeout(() => bar(1), 1000)
}, [])
return (
<Canvas>
<Test />
Expand Down
8 changes: 5 additions & 3 deletions packages/fiber/src/core/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -168,6 +168,7 @@ function createRoot<TCanvas extends Canvas>(canvas: TCanvas): ReconcilerRoot<TCa
// Locals
let onCreated: ((state: RootState) => void) | undefined
let configured = false
let lastCamera: RenderProps<TCanvas>['camera']

return {
configure(props: RenderProps<TCanvas> = {}) {
Expand Down Expand Up @@ -205,8 +206,9 @@ function createRoot<TCanvas extends Canvas>(canvas: TCanvas): ReconcilerRoot<TCa
if (!is.equ(params, raycaster.params, shallowLoose))
applyProps(raycaster as any, { params: { ...raycaster.params, ...params } })

// Create default camera (one time only!)
if (!state.camera) {
// Create default camera
if (!is.equ(lastCamera, shallowLoose)) {
lastCamera = cameraOptions
const isCamera = cameraOptions instanceof THREE.Camera
const camera = isCamera
? (cameraOptions as Camera)
Expand All @@ -217,7 +219,7 @@ function createRoot<TCanvas extends Canvas>(canvas: TCanvas): ReconcilerRoot<TCa
camera.position.z = 5
if (cameraOptions) applyProps(camera as any, cameraOptions as any)
// Always look at center by default
if (!cameraOptions?.rotation) camera.lookAt(0, 0, 0)
if (!state.camera && !cameraOptions?.rotation) camera.lookAt(0, 0, 0)
}
state.set({ camera })
}
Expand Down
12 changes: 11 additions & 1 deletion packages/fiber/src/core/utils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -126,11 +126,21 @@ export const is = {
if ((isArr || isObj) && a === b) return true
// Last resort, go through keys
let i
// Check if a has all the keys of b
for (i in a) if (!(i in b)) return false
for (i in strict ? b : a) if (a[i] !== b[i]) return false
// Check if values between keys match
if (isObj && arrays === 'shallow' && objects === 'shallow') {
for (i in strict ? b : a) if (!is.equ(a[i], b[i], { strict, objects: 'reference' })) return false
} else {
for (i in strict ? b : a) if (a[i] !== b[i]) return false
}
// If i is undefined
if (is.und(i)) {
// If both arrays are empty we consider them equal
if (isArr && a.length === 0 && b.length === 0) return true
// If both objects are empty we consider them equal
if (isObj && Object.keys(a).length === 0 && Object.keys(b).length === 0) return true
// Otherwise match them by value
if (a !== b) return false
}
return true
Expand Down
7 changes: 7 additions & 0 deletions packages/fiber/tests/core/utils.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -83,6 +83,13 @@ describe('is', () => {
expect(is.equ({ a: 1, b: 1 }, { a: 1 }, { objects: 'shallow' })).toBe(false)
expect(is.equ({ a: 1 }, { a: 1, b: 1 }, { objects: 'shallow' })).toBe(false)
expect(is.equ({ a: 1 }, { a: 1, b: 1 }, { objects: 'shallow', strict: false })).toBe(true)
expect(is.equ({ a: [1, 2, 3] }, { a: [1, 2, 3] }, { arrays: 'reference', objects: 'reference' })).toBe(false)
expect(is.equ({ a: [1, 2, 3] }, { a: [1, 2, 3] }, { objects: 'reference' })).toBe(false)
expect(is.equ({ a: [1, 2, 3] }, { a: [1, 2, 3] }, { objects: 'shallow' })).toBe(true)
expect(is.equ({ a: [1, 2, 3] }, { a: [1, 2, 3, 4] }, { objects: 'shallow' })).toBe(false)
expect(is.equ({ a: [1, 2, 3] }, { a: [1, 2, 3, 4] }, { objects: 'shallow', strict: false })).toBe(true)
expect(is.equ({ a: [1, 2, 3] }, { a: [1, 2, 3], b: 1 }, { objects: 'shallow' })).toBe(false)
expect(is.equ({ a: [1, 2, 3] }, { a: [1, 2, 3], b: 1 }, { objects: 'shallow', strict: false })).toBe(true)

const arr = [1, 2, 3]
expect(is.equ(arr, arr)).toBe(true)
Expand Down

0 comments on commit 99fef6c

Please sign in to comment.