jsp, js, jquery 환경에서 파일 이미지 미리보기 기능 구현하기
첨부파일 기능을 개발할 때 확장자 제한, 파일명 길이 제한, 파일 사이즈 제한과 같은 기능들을 주로 구현하는데
만약 이미지 파일 업로드가 목적이라면 미리보기(Preview) 기능이 필요할 때도 있다
📌 기능
0. 파일 첨부
1. 확장자 제한
2. 파일 사이즈 제한
3. 파일명 길이 제한
4. 이미지 미리보기
5. 미리보기 이미지 클릭시 원본크기 팝업
📌 예시
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>imgPreview</title>
<style>
@font-face {
font-family: 'GangwonEdu_OTFBoldA';
src: url('https://cdn.jsdelivr.net/gh/projectnoonnu/noonfonts_2201-2@1.0/GangwonEdu_OTFBoldA.woff') format('woff');
font-weight: normal;
font-style: normal;
}
html {font-family: 'GangwonEdu_OTFBoldA'}
.uploadImg {margin:10px;margin-top:150px;}
img#previewImg{cursor:pointer;max-height:200px; max-width:100%;display:block;}
.filebox {display:inline-block;margin:10px;}
.filebox label {display: inline-block; padding: 4px 8px; margin-left:5px; color: #999; font-size: inherit; line-height: normal; vertical-align: middle; border-radius: .25em; cursor: pointer; color: #fff; background-color: #895fc0; border: 1px solid #683d8b;}
.filebox input[type="file"] {position: absolute;width: 1px;height: 1px;padding: 0;margin: -1px;overflow: hidden;clip:rect(0,0,0,0);border: 0;}
.filebox .upload-name{display: inline-block; padding: 0.3em 0.4em; font-size: inherit; font-family: inherit; line-height: normal; vertical-align: middle; background-color: #f5f5f5;
border: 1px solid #ebebeb; border-bottom-color: #e2e2e2; border-radius: .25em; -webkit-appearance: none; -moz-appearance: none; appearance: none; }
</style>
<script src="https://code.jquery.com/jquery-3.6.0.min.js" integrity="sha256-/xUj+3OJU5yExlq6GSYGSHk7tPXikynS7ogEvDej/m4=" crossorigin="anonymous"></script>
</head>
<body>
<div class="uploadImg">
<div class="filebox">
<input class="upload-name" value="선택된 파일 없음" disabled="disabled">
<input type="file" id="file1" class="upload-hidden" name="file1">
<label for="file1">이미지 첨부</label>
</div>
<img id="previewImg" onclick="popImage(this.src)">
</div>
</body>
</html>
위의 코드는 기능 구현 테스트를 위한 샘플 html 코드이다
가독성을 위해 css가 복잡하게 적혀있지만 기능 구현과는 관련 없고 body 영역이 중요하다
filebox 안의 label은 파일 첨부를 위한 버튼의 개념이고 실제 파일이 첨부되는 곳은 input type file인 곳이다
그리고 <img id="previewImg">는 미리보기로 보여질 이미지 부분이다
아래가 스크립트에 대한 부분이다
<script>
$(document).ready(function(){
//파일첨부 이벤트
$('.filebox .upload-hidden').on('change', function(){
if(window.FileReader){
var filename = $(this)[0].files[0].name;
if(!validFileType(filename)){
alert("허용하지 않는 확장자 파일입니다.");
return false;
}else{
if(!validFileSize($(this)[0].files[0])){
alert("파일 사이즈가 10MB를 초과합니다.");
return false;
}else{
if(!validFileNameSize(filename)){
alert("파일명이 30자를 초과합니다.");
return false;
}
}
}
} else {
var filename = $(this).val().split('/').pop().split('\\').pop();
}
$(this).prev().val(filename); //input upload-name 에 파일명 설정해주기
readImage($(this)[0]); //미리보기
});
});
function validFileType(filename) {
const fileTypes = ["png", "jpg", "jpeg"];
return fileTypes.indexOf(filename.substring(filename.lastIndexOf(".")+1, filename.length).toLowerCase()) >= 0;
}
function validFileSize(file){
if(file.size > 10000000){ //10MB
return false;
}else{
return true;
}
}
function validFileNameSize(filename){
if(filename.length > 30){ //30자
return false;
}else{
return true;
}
}
//이미지 띄우기
function readImage(input) {
if(input.files && input.files[0]) {
const reader = new FileReader();
reader.onload = function(e){
const previewImage = document.getElementById("previewImg");
previewImage.src = e.target.result;
}
// reader가 이미지 읽도록 하기
reader.readAsDataURL(input.files[0]);
}
}
//이미지 원본 팝업 띄우기
function popImage(url) {
var img = new Image();
img.src = url;
var img_width = img.width;
var win_width = img.width + 25;
var img_height = img.height;
var win = img.height + 30;
var popup = window.open('', '_blank', 'width=' + img_width + ', height=' + img_height + ', menubars=no, scrollbars=auto');
popup.document.write("<style>body{margin:0px;}</style><img src='"+url+"' width='"+win_width+"'>");
}
</script>
파일첨부 이벤트 발생시 일어나는 Validation에 대한 코드는 생략하고
이미지 파일 미리보기 기능 관련 코드만 떼어서 보면 아래와 같다
readImage($(this)[0]); //미리보기
//이미지 띄우기
function readImage(input) {
if(input.files && input.files[0]) {
const reader = new FileReader();
reader.onload = function(e){
const previewImage = document.getElementById("previewImg");
previewImage.src = e.target.result;
}
// reader가 이미지 읽도록 하기
reader.readAsDataURL(input.files[0]);
}
}
readImage 함수를 호출하여 미리보기를 호출하는데 이 때 input file을 파라미터로 넣어준다
그래서 해당 input에 파일이 있을경우 FileReader를 선언하고
미리 만들어놓은 img태그의 src가 onload될때의 파일을 가리키도록 onload function을 작성해준 다음
reader가 파일을 읽어오도록 readAsDataURL()을 실행하는 것이다
📌 실행화면
위의 html + script를 복사하여 vscode에서 실행해본 결과이다
728x90
반응형