안녕, 오늘 나는 매우 멋진 것을 공유할 수 있어.
사용자의 서명이나 도면을 수집해야 할 경우에 대비하여 프로그램에 추가할 수 있는 서명 패드를 만드는 방법을 알려드리겠습니다.
또한 서명 패드에서 서버를 보낼 수 있는 이미지를 만드는 방법도 알려드리겠습니다.
준비됐나요? 를 시작하겠습니다.
먼저 hour page의 HTML 구조를 만들고 app.js와 app.css를 index.html 페이지에 연결해보자.
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Singature Pad</title>
<link rel="stylesheet" href="app.css">
</head>
<body>
<form class="signature-pad-form" action="#" method="POST">
<h1>Important Contract</h1>
<p>Important contract description</p>
<p><b>Signature</b></p>
<canvas height="100" width="300" class="signature-pad"></canvas>
<p><a href="#" class="clear-button">Clear</a></p>
<button class="submit-button" type="submit">SUBMIT</button>
</form>
<script src="app.js"></script>
</body>
</html>
이제 app.css 파일에 css를 추가하여 시그니처 패드처럼 보이도록 하겠습니다.
:root {
--primary-color: #000;
}
body {
font-family: Arial, Helvetica, sans-serif;
line-height: 1.4;
padding: 1rem;
}
.signature-pad-form {
max-width: 300px;
margin: 0 auto;
}
.signature-pad {
cursor: url(pen.png) 1 26, pointer;
border: 2px solid var(--primary-color);
border-radius: 4px;
}
.clear-button {
color: var(--primary-color);
}
.submit-button {
width: 100%;
background-color: var(--primary-color);
border: none;
padding: 0.5rem 1rem;
color: #fff;
cursor: pointer;
margin-top: 2rem;
}
@media (pointer: coarse) {
body {
overflow: hidden; /* Needed to prevent the vertical scroll on touch devices */
}
}
좋아, 이제 구조와 스타일이 정해졌으니 재미있는 일을 해보자:)
우리는 이제 app.js에서 코드 작성을 시작할 수 있다.
먼저 서명 패드를 지울 수 있는 양식, 캔버스 및 단추에 대한 몇 가지 상수를 저장하려고 합니다.
const canvas = document.querySelector('canvas');
const form = document.querySelector('.signature-pad-form');
const clearButton = document.querySelector('.clear-button');
그러면 곧 필요할 캔버스 컨텍스트를 다른 상수에서 저장해 봅시다. 이 경우 서명이 2d이므로 2d 컨텍스트만 있으면 됩니다.
const ctx = canvas.getContext('2d');
마지막으로 쓰기 모드를 설정 및 해제할 수 있는 변수를 몇 개 만들어 보겠습니다.
let writingMode = false;
완벽해!
다음 단계로 이벤트 수신기가 패드와 상호 작용하도록 설정할 수 있습니다. 우리는 포인터다운, 포인터업, 포인터모브의 소리를 들어야 할 것이다.
포인터다운은 쓰기 모드를 true로 설정하는 데 사용되고 포인터업은 쓰기 모드를 false로 설정하는 데 사용됩니다.
canvas.addEventListener('pointerdown', handlePointerDown, {passive: true});
canvas.addEventListener('pointerup', handlePointerUp, {passive: true});
canvas.addEventListener('pointermove', handlePointerMove, {passive: true});
이제 핸들러를 구현해 보겠습니다.
handlePointerDown
const handlePointerDown = (event) => {
writingMode = true;
ctx.beginPath();
const [positionX, positionY] = getCursorPosition(event);
ctx.moveTo(positionX, positionY);
}
handlePointerUp
const handlePointerUp = () => {
writingMode = false;
}
handlePointerMove
const handlePointerMove = (event) => {
if (!writingMode) return
const [positionX, positionY] = getCursorPosition(event);
ctx.lineTo(positionX, positionY);
ctx.stroke();
}
여기서 getCursorPosition은 다음과 같습니다.
const getCursorPosition = (event) => {
positionX = event.clientX - event.target.getBoundingClientRect().x;
positionY = event.clientY - event.target.getBoundingClientRect().y;
return [positionX, positionY];
}
그런 다음 캔버스 컨텍스트에 몇 가지 속성을 설정하여 도면 선의 스타일을 지정합니다.
ctx.lineWidth = 3;
ctx.lineJoin = ctx.lineCap = 'round';
거의 다 왔습니다, 마지막으로 추가할 것은 캔버스를 지우는 기능과 양식을 제출하는 기능입니다.
form.addEventListener('submit', (event) => {
event.preventDefault();
const imageURL = canvas.toDataURL();
const image = document.createElement('img');
image.src = imageURL;
image.height = canvas.height;
image.width = canvas.width;
image.style.display = 'block';
form.appendChild(image);
clearPad();
})
const clearPad = () => {
ctx.clearRect(0, 0, canvas.width, canvas.height);
}
clearButton.addEventListener('click', (event) => {
event.preventDefault();
clearPad();
})
바로 그거야! 최종 결과는 이렇게 나와야 돼.
읽어주셔서 감사하고 다음 기사에서 뵙겠습니다:) 좋은 하루 보내시고 행복한 코딩!
'javascript' 카테고리의 다른 글
웹 개발에 Typescript 가 필요한 이유 (0) | 2021.12.28 |
---|---|
네이티브 웹뷰를 사용하기 전에 알아야 할 내용 (0) | 2021.12.28 |
Javascript 산술 연산자, 코드 편집기, 함수, 객체 및 배열 (0) | 2021.12.28 |
JavaScript에서 문자열에 있는 모든 단어의 모든 첫 글자를 대문자로 변경하는 방법 (0) | 2021.12.28 |
Javascript를 이용한 빠른 Array Reverse 구현 방법 (0) | 2021.12.28 |
댓글