CSS n-선택기 변수
29393 단어 webdevcsswebcomponentsjavascript
사진 작성자Mario Gogh가 Unsplash
적어도 2021년 6월에 내가 이 줄을 쓸 때, CSS 변수를 사용하면 미디어 조회나 선택기에서 지원되지 않는다. 예를 들어
:nth-child(var(--my-variable))
는 작용하지 않는다.이것은 약간 불행하지만, 결코 해결할 수 없는 것은 아니다.최근의 일부 개발에서, 나는 이 제한을 빙빙 돌려서 DOM의
style
요소를 웹 구성 요소에 주입하여 DeckDeckGo의 코드 블록에 애니메이션을 설정하도록 했다.소개하다.
엄밀히 말하면, 아래의 기교는 웹 구성 요소에 적용되지 않고, 어떤 요소에도 적용될 수 있다.지금까지 나는 단지 이런 기술을 사용하고 있을 뿐이다😜.
나는 우선 일반 구성 요소의 도움으로 이 생각을 보여주고, 문장의 끝에는 같은 방법을 사용하지만, StencilJS 기능 구성 요소로 실현할 것이다.
이 자습서의 목표
우리는 웹 구성 요소를 개발하여
<ul/>
목록을 보여주고 항목의 디스플레이에 애니메이션을 설정할 수 있습니다.어셈블리를 로드한 후에는 DOM에서 의미 요소가 추가되거나 삭제되지 않습니다.애니메이션은 수정
style
을 통해 이루어질 것이다. 더욱 정확히 말하면 선택된 li:nth-child(n)
에 서로 다른 스타일을 적용한다.바닐라 JS
인터넷 없이 창의력을 보여주기 위해
index.html
페이지를 만들었습니다.그것은 우리가 곧 개발할 바닐라 성분을 소모할 것이다.우리는 애니메이션을 터치하기 위해 button
도 추가했다.<html>
<head>
<script type="module" src="./my-component.js"></script>
</head>
<body>
<my-component></my-component>
<button>Next</button>
<script>
document
.querySelector('button')
.addEventListener(
'click',
() => document.querySelector('my-component').next()
);
</script>
</body>
</html>
다른 이름my-component.js
의 파일에서 웹 구성 요소를 만들었습니다.애니메이션이 없습니다.우리는 이것open이 그림자 DOMshadowRoot
에 접근할 수 있다고 성명했다li
. 우리는 모든 것을 숨기고 정의하는 스타일을 만들었다transition
.마지막으로, 우리는 ul
목록과 그 하위 항목 li
을 추가했다.class MyComponent extends HTMLElement {
constructor() {
super();
this.attachShadow({mode: 'open'});
const style = this.initStyle();
const ul = this.initElement();
this.shadowRoot.appendChild(style);
this.shadowRoot.appendChild(ul);
}
connectedCallback() {
this.className = 'hydrated';
}
next() {
// TODO in next chapter
}
initStyle() {
const style = document.createElement('style');
style.innerHTML = `
:host {
display: block;
}
li {
opacity: 0;
transition: opacity 0.5s ease-out;
}
`;
return style;
}
initElement() {
const ul = document.createElement('ul');
const li1 = document.createElement('li');
li1.innerHTML = 'Spine';
const li2 = document.createElement('li');
li2.innerHTML = 'Cowboy';
const li3 = document.createElement('li');
li3.innerHTML = 'Shelving';
ul.append(li1, li2, li3);
return ul;
}
}
customElements.define('my-component', MyComponent);
이 때 브라우저 npx serve .
에서 예시를 열면 숨겨진 내용을 포함하는 구성 요소와 아직 효력이 발생하지 않은 단추를 찾을 수 있습니다.볼 것도 없지만 시작일 뿐이야😁.애니메이션을 개발하기 위해서 우리는 디스플레이
li
를 추적해야 한다. 이것이 바로 우리가 구성 요소에 상태(index
를 추가해야 하는 이유이다.class MyComponent extends HTMLElement {
index = 0;
constructor() {
...
덕분에 우리는 next()
방법을 실현할 수 있다. 이 방법은 우리가 이전에 HTML 페이지에 추가한 단추에서 호출된 것이다.Not my most beautiful code ever. Let’s agree it has only a demo purpose 😅.
next() {
this.index = this.index === 3 ? 1 : this.index + 1;
const selector = `
li:nth-child(${this.index}) {
opacity: 1;
}
`;
let style = this.shadowRoot.querySelector('style#animation');
if (style) {
style.innerHTML = selector;
return;
}
style = document.createElement('style');
style.setAttribute('id', 'animation');
style.innerHTML = selector;
this.shadowRoot.appendChild(style);
}
그곳에서 무슨 일이 일어났습니까?이것은 우선 표시할 다음
index
li
을 설정한 다음, selector
스타일을 적용하기 위해 CSS opacity
를 만듭니다.요컨대, 이것은 우리가 사용할 수 없는 CSS 변수를 대체할 것이다.그런 다음 웹 구성 요소의 섀도우 컨텐트에 적용된 애니메이션 전용 스타일이 포함되어 있는지 확인합니다.있으면, 새 값 선택기로 스타일을 업데이트하고, 없으면, 새 스타일 표시자를 만듭니다.
이 방법을 호출할 때마다 새
style
이 적용되기 때문에 다른 li:nth-child(n)
이 표시됩니다.만약에 우리가 브라우저를 다시 켜서 시도를 한다면 우리의 단추
next
를 눌렀을 때 항목은 애니메이션이어야 한다. 만약에 inspector의 구성 요소를 더 살펴보면 음영style
요소가 매번 방법이 호출될 때마다 변화하는 것을 주의해야 한다.거푸집
우리는 같은 예로 즐거움을 배가하지만 StencilJS 기능 구성 요소를 사용한다🤙.
You can start a new project with the command line
npm init stencil
우리는 완전히 같은 구성 요소를 개발하고 있기 때문에 이전의 HTML 내용 (이 구성 요소를 설명하고 프로젝트
button
에 하나 ./src/index.html
를 복사할 수 있습니다. 아주 작은 차이만 있을 뿐입니다. 방법 next()
은 반드시 설명하고 async-await 호출을 사용해야 합니다.이것은 템플릿의 가장 좋은 실천이며 구성 요소의 공공 방법은 반드시 async
이어야 한다.<!DOCTYPE html>
<html dir="ltr" lang="en">
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0, minimum-scale=1.0, maximum-scale=5.0" />
<title>Stencil Component Starter</title>
<script type="module" src="/build/demo-stencil.esm.js"></script>
<script nomodule src="/build/demo-stencil.js"></script>
</head>
<body>
<!-- Same code as in previous chapter -->
<my-component></my-component>
<button>Next</button>
<script>
document.querySelector('button')
.addEventListener(
'click',
async () => await document
.querySelector('my-component').next()
);
</script>
<!-- Same code as in previous chapter -->
</body>
</html>
우리도 앞의 절차를 반복해서 먼저 구성 요소를 만들 수 있습니다. 이 구성 요소는 보여주기 ul
목록과 숨겨진 항목 li
을 제외하고는 아무것도 하지 않습니다.import { Component, h } from '@stencil/core';
@Component({
tag: 'my-component',
styles: `:host {
display: block;
}
li {
opacity: 0;
transition: opacity 0.5s ease-out;
}
`,
shadow: true,
})
export class MyComponent {
render() {
return <ul>
<li>Spine</li>
<li>Cowboy</li>
<li>Shelving</li>
</ul>
}
}
테스트 구성 요소 (npm run start
를 통해 우리도 같은 결과를 얻어야 한다😉.강조 표시된
li
를 추적하기 위해서는 상태와 함수 state
가 필요합니다.우리는 둘 다 구성 요소에 추가할 것이다.@State()
private index: number = 0;
@Method()
async next() {
this.index = this.index === 3 ? 1 : this.index + 1;
}
Vanilla 구성 요소에 비해, 우리는 bundler를 사용하기 때문에 개발 과정을 간소화하기 때문에, 우리는 스스로 다시 과장할 필요가 없다.state
에 대한 수정 사항이 있을 때마다 다시 렌더링이 트리거되고 업데이트해야 하는 노드만 업데이트됩니다.그럼에도 불구하고 CSS 선택기 변수를 구현해야 합니다.앞에서 말한 바와 같이, 이 목적에서 우리는 기능 구성 요소를 사용할 것이다.그것은 클래스 구성 요소와 함께 일할 수 있지만, 나는 기능 구성 요소가 이 작업에 매우 적합하다고 생각한다.
const Animate: FunctionalComponent<{index: number;}> = ({index}) => {
return (
<style>{`
li:nth-child(${index}) {
opacity: 1;
}
`}</style>
);
};
이 구성 요소는 style
요소를 보여 줍니다. 이 요소의 값은 we path입니다. 즉, 우리의 state
입니다.마지막으로, 우리는 기능 구성 요소를 사용하여 우리의 상태 값에 연결해야 한다.이렇게 하면 값이 변경될 때마다 다시 렌더링됩니다.
render() {
return <Host>
<Animate index={this.index}></Animate>
<ul>
<li>Spine</li>
<li>Cowboy</li>
<li>Shelving</li>
</ul>
</Host>
}
이렇게 하면 우리는 같은 구성 요소를 복제할 수 있다🥳.이러한 구성 요소는 단일 코드 블록으로 구성됩니다.
import { Component, FunctionalComponent, h, Host, Method, State } from '@stencil/core';
const Animate: FunctionalComponent<{index: number;}> = ({index}) => {
return (
<style>{`
li:nth-child(${index}) {
opacity: 1;
}
`}</style>
);
};
@Component({
tag: 'my-component',
styles: `:host {
display: block;
}
li {
opacity: 0;
transition: opacity 0.5s ease-out;
}
`,
shadow: true,
})
export class MyComponent {
@State()
private index: number = 0;
@Method()
async next() {
this.index = this.index === 3 ? 1 : this.index + 1;
}
render() {
return <Host>
<Animate index={this.index}></Animate>
<ul>
<li>Spine</li>
<li>Cowboy</li>
<li>Shelving</li>
</ul>
</Host>
}
}
요약
솔직히 말해서, 나는 이 문장이 독자를 찾을 수 있을지 없을지 확실하지 않다. 나도 언젠가 그것이 누군가에게 유용할 것이라고 생각하지 않는다. 그러나, 그래, 나는 이 기교를 사용하는 것을 좋아한다😜. 또한 프레젠테이션의 목적을 위해 Vanilla JS나 Stencil로 같은 코드를 개발하는 것도 흥미롭다.
무한원까지!
다윗
전화나 제website로 연락 주세요.
다음 프레젠테이션을 수행하십시오DeckDeckGo.
Reference
이 문제에 관하여(CSS n-선택기 변수), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://dev.to/daviddalbusco/css-nth-selectors-variable-86f텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)