728x90
이미지 파일을 업로드 하고 프로그래바( ProgressBar )를 이용하여 업로드 진행률을 나타내는 시각적 효과를 만들고 싶었다.
event#01.
<input type="file">을 숨김 처리하고 다른 버튼을 클릭하였을 경우 <input type="file">버튼을 클릭한 것과 같은 효과를 만든다. 실제로 브라우저를 통해 등록하는 파일의 정보는 <input type="file>태그가 보관하기 때문이다.
ecent#02.
사용자가 업로드를 위해 선택한 파일의 개수만큼 각 파일의 정보를 표기할 프로그래바( ProgressBar )와 정보를 표시할 레이어를 생성하여준다.
이때 업로드하는 파일이 이미지 파일( JPG, PNG, GIF 등 )인지 검사하는 로직을 수행여 이미지 파일이 아닌 파일이 존재하는경우 업로드 할 수 없게 처리한다.
event#03.
이미 event#02에서 <input type="file">에 사용자가 선택한 이미지는 전부 올라와져 있다.
그렇지만 이렇게 나눈이유는 사용자가 올린 파일의 용량( Byte )체크 및 실제 서버에 전송을 하는 경우 업로드 시각적 효과를 주기위하여 별도로 분리하였다.
event#04.
업로드된 이미지 파일을의 값( base64 )을 읽어들여 화면에 출력하여 업로드한 이미지 파일을 확인 할 수 있게 한다. 정적 메서드 사용환경 및 게시판 등에서의 사용을 위해 분류하였다.
# 소스코드
<!DOCTYPE html>
<html lang="ko">
<head>
<meta http-equiv="Content-Type" content="text/html;charset=utf-8">
<title>:: 파일 업로드 및 이미지 썸네일 생성 ::</title>
<style type="text/css">
#fileSelect {
display:none;
}
.progressBar {
width:100%;
}
#imgThumbnails {
display: flex;
flex-wrap: wrap;
}
.thumbnail {
margin: 10px;
}
</style>
</head>
<body>
<input type="file" id="fileSelect" multiple/>
<div>
<div id="progressContainer"></div>
</div>
<div id="imgThumbnails"></div>
<br/><hr/><br/>
<button type="button" id="btnFileSelect">파일 선택</button>
<button type="button" id="btnFileUpload">업로드</button>
<button type="button" id="btnThumbnailCreate">썸네일 생성</button>
</body>
<script type="text/javascript">
document.addEventListener("DOMContentLoaded", function() {
// @event#01. 파일 선택 버튼에 대한 클릭 이벤트 처리
document.querySelector("#btnFileSelect").addEventListener("click", function() {
// 파일 선택 input을 클릭함
document.querySelector("#fileSelect").click();
});
// @event#02. 업로드할 File 개수별 프로그래스바 UI 생성
document.querySelector("#fileSelect").addEventListener("change", function(event) {
// 이미지 파일인지 검사
if(isImageFile(event.target.files) === false) {
alert("업로드할 파일중 이미지 파일이 아닌항목이 존재합니다.\nJPG, PNG, GIF 등의 파일만 업로드 해주세요.");
return;
}
for(let file of event.target.files) {
// p 요소 생성
const divElement = document.createElement("div");
divElement.classList.add("uploadProgress");
// progress 요소 생성
const progressElement = document.createElement("progress");
progressElement.setAttribute("value", "0");
progressElement.setAttribute("max", "100");
progressElement.classList.add("progressBar");
// span 요소들 생성
const loadedSpan = document.createElement("span");
loadedSpan.textContent = "0";
loadedSpan.classList.add("loaded");
const totalSpan = document.createElement("span");
totalSpan.textContent = "0 Byte";
totalSpan.classList.add("totalBytes");
const rateSpan = document.createElement("span");
rateSpan.textContent = "0%";
rateSpan.classList.add("rate");
const nameSpan = document.createElement("span");
nameSpan.textContent = "unknown";
nameSpan.classList.add("fileName");
// span 요소들을 p 요소에 추가
divElement.appendChild(progressElement);
divElement.appendChild(document.createTextNode(" ")); // 공백 추가
divElement.appendChild(loadedSpan);
divElement.appendChild(document.createTextNode(" / ")); // 공백 추가
divElement.appendChild(totalSpan);
divElement.appendChild(document.createTextNode("("));
divElement.appendChild(rateSpan);
divElement.appendChild(document.createTextNode(")"));
divElement.appendChild(document.createTextNode(" ")); // 공백 추가
divElement.appendChild(nameSpan);
document.querySelector("#progressContainer").appendChild(divElement);
}
});
// @event#03. 업로드할 File 프로그래스바 UI 효과
document.querySelector("#btnFileUpload").addEventListener("click", function() {
const files = document.querySelector("#fileSelect").files;
if(files.length > 0) {
for(let num = 0; num < files.length; num++) {
const reader = new FileReader();
// FileReader 로드 이벤트 핸들러 지정
reader.onloadend = function(event) {
const rate = (event.loaded * 100 / event.total).toFixed(1);
document.querySelectorAll(".progressBar")[num].value = rate;
document.querySelectorAll(".loaded")[num].textContent = event.loaded;
document.querySelectorAll(".totalBytes")[num].textContent = event.total + " Byte";
document.querySelectorAll(".rate")[num].textContent = rate + "%";
document.querySelectorAll(".fileName")[num].textContent = files[num].name;
};
// 바이너리 형식으로 파일 데이터 얻기
reader.readAsBinaryString(files[num]);
}
} else {
alert("업로드할 이미지 파일이 존재하지 않습니다.");
}
});
// @event#04. 이미지 썸네일 생성
document.querySelector("#btnThumbnailCreate").addEventListener("click", function () {
const files = document.querySelector("#fileSelect").files;
if(files.length > 0) {
for(let num = 0; num < files.length; num++) {
const reader = new FileReader();
// FileReader 로드 이벤트 핸들러 지정
reader.onloadend = function(event) {
const imgElement = document.createElement("img");
imgElement.src = event.target.result;
document.querySelector("#imgThumbnails").appendChild(imgElement);
};
// 바이너리 형식으로 파일 데이터 얻기
reader.readAsDataURL(files[num]);
}
} else {
alert("썸네일을 생성할 이미지 파일이 존재하지 않습니다.");
}
});
});
// 이미지 파일 여부 확인 함수
function isImageFile(files) {
// 이미지 파일이 아닌경우 false 리턴
for(let file of files) {
if(file.type.startsWith("image/") === false) {
return false;
}
}
// 이미지 파일인 경우
return true;
}
</script>
</html>
# 출력결과
■ 이미지 파일 업로드시 진행률 표시 및 썸네일 생성
728x90
'JavaScript' 카테고리의 다른 글
[JavaScript] 다중 파일 업로드시 진행률(ProgressBar) 표시 (0) | 2024.01.18 |
---|---|
[JavaScript] AJAX를 이용하는 Page Navigation 제작 (0) | 2023.12.08 |
[JavaScript] 체크박스를 이용한 백분율 선택 (0) | 2023.05.24 |
[JavaScript] 입력한 텍스트의 Byte 체크 (0) | 2023.02.14 |
[JavaScript] 입력한 텍스트의 문자길이 체크 (0) | 2023.02.14 |