오픈 소스 모험: 에피소드 44: SolidJS의 무시무시한 눈
23539 단어 javascriptsolidjs
이 앱은 간단합니다. 마우스를 따라다니는 눈이 무작위로 배치되어 있습니다.
이전 에피소드에서 프로젝트의 기본 구조를 다루었습니다. 여기서는 흥미로운 부분에 집중하겠습니다.
index.css
SolidJS는 구성 요소 범위 CSS를 지원하지만 단순화를 위해 모든 것을 정적 구성 요소에 넣었습니다.
body {
margin: 0;
min-height: 100vh;
display: flex;
text-align: center;
justify-content: center;
align-items: center;
}
svg {
width: 100vw;
height: 100vh;
display: block;
background-color: #aaa;
}
.eye1 {
fill: white;
stroke: black;
stroke-width: 3px;
}
.eye2 {
stroke: black;
stroke-width: 1px;
}
.eye3 {
fill: black;
}
앱솔리드
App
구성 요소는 생성될 때 무작위로 배치된 Eye
목록을 초기화합니다. 또한 마우스의 위치를 추적하여 하위 인스턴스Eye
에 전달합니다.import Eye from "./Eye"
import { createSignal } from "solid-js"
function randomColor() {
let h = Math.random() * 360
let s = Math.round(50 + Math.random() * 50)
let l = Math.round(30 + Math.random() * 40)
return `hsl(${h}, ${s}%, ${l}%)`
}
function eyeDistance(eye1, eye2) {
let dx = eye1.x - eye2.x;
let dy = eye1.y - eye2.y;
return Math.sqrt((dx * dx) + (dy * dy))
}
function canPlaceEye(eyes, newEye) {
return eyes.every(eye =>
eyeDistance(eye, newEye) >= eye.sz + newEye.sz + 5
)
}
function generateEyes() {
let eyes = []
let wh = window.innerHeight
let ww = window.innerWidth
let mx = Math.random() * ww
let my = Math.random() * wh
for(let i=0; i<1000; i++) {
let sz = 20 + Math.random() * 60
let x = sz + Math.random() * (ww - 2 * sz)
let y = sz + Math.random() * (wh - 2 * sz)
let color = randomColor()
let newEye = {x, y, sz, color}
if (canPlaceEye(eyes, newEye)) {
eyes.push(newEye)
}
}
return eyes
}
function App() {
let eyes = generateEyes()
let wh = window.innerHeight
let ww = window.innerWidth
// init it to something random if mouse starts outside window
let [mx, setMx] = createSignal(Math.random() * ww)
let [my, setMy] = createSignal(Math.random() * wh)
function onMouseMove() {
let svg = document.getElementById("eyes")
let rect = svg.getBoundingClientRect()
setMx(event.pageX - rect.x)
setMy(event.pageY - rect.y)
}
return (
<svg id="eyes" onMouseMove={onMouseMove}>
<For each={eyes}>
{({x, y, sz, color}) => <Eye x={x} y={y} sz={sz} color={color} mx={mx} my={my} />}
</For>
</svg>
)
}
export default App
몇 가지 주목할만한 사항:
.map
로 루프를 돌지 않으므로 <For>...</For>
를 사용해야 합니다. React를 제외한 대부분의 프레임워크는 루프, if/else 등을 위한 특수 구문을 갖게 됩니다. mx
및 my
마우스 위치가 있습니다. eyes
는 정적이므로 createSignal
수정그 외에는 React에서 수행하는 것과 매우 유사하므로 React 개발자의 학습 곡선은 매우 낮을 것입니다.
아이.솔리드
다음은
Eye
구성 요소입니다.import { createSignal, createEffect } from "solid-js"
function Eye({x,y,sz,color,mx,my}) {
let [rx, setRx] = createSignal(x)
let [ry, setRy] = createSignal(y)
createEffect(() => {
let max_eye_movement = 0.3 * sz
let dx = mx() !== null ? (mx() - x) : 0
let dy = my() !== null ? (my() - y) : 0
let dl = Math.max(0.000001, Math.sqrt(dx*dx + dy*dy))
let displacement = Math.min(max_eye_movement, dl)
setRx(x + dx/dl * displacement)
setRy(y + dy/dl * displacement)
})
return (
<g>
<circle class="eye1" cx={x} cy={y} r={sz} />
<circle class="eye2" cx={rx()} cy={ry()} r={sz * 0.5} style={`fill: ${color}`}/>
<circle class="eye3" cx={rx()} cy={ry()} r={sz * 0.2}/>
</g>
)
}
export default Eye
이것은 매우 어색합니다. React에서는 상태나 효과가 필요하지 않습니다.
mx
와 my
를 소품으로 취하고 모든 것을 계산한 다음 결과를 반환합니다.Solid는 훨씬 더 명시적이어야 합니다. 틀림없이 많은 추가 작업 비용으로 약간의 성능을 얻을 수 있습니다.
거의 틀림없이 React 코드처럼 보입니다. Recat 개발자는 무슨 일이 일어나고 있는지 이해할 것입니다. 이러한 선택이 이루어진 이유는 다소 불분명할 것입니다.
지금까지의 이야기
저는 이것을 GitHub Pagesyou can see it here에 배포했습니다. 매우 원활하게 작동하며 제가 테스트한 꽤 많은 프레임워크가 이미 이 앱에서 어려움을 겪고 있습니다.
지금까지 SolidJS에 대한 나의 인상은 놀랍지 않습니다. 그것의 반응성은 React나 Svelte보다 훨씬 더 많은 개발자의 작업을 필요로 하며, 나는 그것이 나에게 가치가 있다고 생각하지 않습니다.
SolidJS가 제공하는 트레이드 오프가 합리적인 시나리오를 확실히 볼 수 있습니다. React와 유사하므로 많은 React 개발자의 경우 Svelte보다 훨씬 쉽게 전환할 수 있습니다. 가상 DOM 오버헤드가 없으면 Svelte와 거의 비슷하고 React보다 훨씬 더 나은 성능을 발휘해야 합니다(원칙적으로 아무것도 벤치마크하지 않았습니다). 그리고 Svelte와 달리 모두 런타임이므로 모든 곳에서 지원되는 JSX 이외의 도구가 필요하지 않습니다.
그러나 전반적으로 나는 내 프로젝트에 Svelte를 고수할 것이라고 생각합니다.
다음에 온다
다음 몇 개의 에피소드에서는 비디오 게임 데이터 분석을 수행할 것입니다.
Reference
이 문제에 관하여(오픈 소스 모험: 에피소드 44: SolidJS의 무시무시한 눈), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://dev.to/taw/open-source-adventures-episode-44-spooky-eyes-in-solidjs-52ie텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)