본문 바로가기

OpenCV없는 컬러영상처리 및 마우스 이벤트

화소 영역 처리

<화소 영역 처리>

 


시연 영상(유튜브): https://youtu.be/npL6e6XcHzE


 

<원본이미지 엠보싱 처리하기>

알고리즘
결과화면

 

function embossImage(){  //엠보싱 알고리즘
            outH = inH;
            outW = inW;

            // 배열 선언
            outImage = new Array(3); // 3면
            for(var m=0; m<3; m++) {
                outImage[m] = new Array(outH);
                for(let n=0; n<outH; n++)
                    outImage[m][n] = new Array(outW);
            }

            // 짱 중요한거 --> 마스크를 선택
            let mask = [[-1.0, 0.0, 0.0], [0.0, 0.0, 0.0], [0.0, 0.0, 1.0]];

            // 임시 입력 배열 (입력배열 + 2)
            let tmpInImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpInImage[m] = new Array(inH+2);
                for(let n=0;n<inH+2;n++){
                    tmpInImage[m][n] = new Array(inW+2);
                }
            }
            

            // 임시 출력 배열 (출력배열과 크기 동일)
            let tmpOutImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpOutImage[m] = new Array(outH+2);
                for(let n=0;n<inH+2;n++){
                    tmpOutImage[m][n] = new Array(outW+2);
                }
            }

            // 임시 입력 배열 초기화 ((127로)/평균값/인접값)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH+2; i++) {
                    for (let k=0; k<inW+2; k++) {
                        tmpInImage[rgb][i][k] = 127.0;
                    }
                }
            }

            // 입력 이미지 -> 임시 입력 이미지의 중간에 넣기
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        tmpInImage[rgb][i+1][k+1] = inImage[rgb][i][k];
                    }
                }
            }
            // 영상 처리 알고리즘 --> 회선 연산(=긁어가기)
            for(let rgb=0; rgb<3; rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        // 한점 처리
                        let S = 0.0; // 9점을 곱해서 합한 결과
                        for(let m=0;m<3;m++){
                            for(let n=0;n<3;n++){
                                S += tmpInImage[rgb][i+m][k+n] * mask[m][n];
                            }  
                        }
                        tmpOutImage[rgb][i][k] = S;
                    }
                }
            }

            // 후처리 작업 (마스크의 합계가 0이면 ... 127 정도를 더해주기를 고려)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        tmpOutImage[rgb][i][k] += 127.0;
                    }
                }
            }

            // 임시 출력 이미지 --> 원 출력 이미지
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        if((startX <= k && k< endX )&&(startY <=i && i<endY)){
                            if(tmpOutImage[rgb][i][k] > 255.0)
                                outImage[rgb][i][k] = 255;
                            else if(tmpOutImage[rgb][i][k] < 0.0)
                                outImage[rgb][i][k] = 0;
                            else
                                outImage[rgb][i][k] = parseInt(tmpOutImage[rgb][i][k]);
                            }
                        else{
                            outImage[rgb][i][k] = inImage[rgb][i][k];
                        }
                    }
                }
            }
            displayImage();
    }
    function embossImage_mouse(){
        var mouseCheck= document.getElementById("mouseEnable");
            //사각형 선택이 체크가 안되었을때!
            if(!mouseEnable.checked){
                startX = startY=0;
                endX = inW;
                endY= inH;
                embossImage();
                return;
            }
            //사각형 체크됨.
            //마우스 이벤트 리스너 켜기
            onEventListener();
    }

 

 

 


 

<원본이미지 블러링 처리하기>

알고리즘
결과화면

function blurrImage(){
        outH = inH;
            outW = inW;

            // 배열 선언
            outImage = new Array(3); // 3면
            for(var m=0; m<3; m++) {
                outImage[m] = new Array(outH);
                for(let n=0; n<outH; n++)
                    outImage[m][n] = new Array(outW);
            }

            // 짱 중요한거 --> 마스크를 선택
            let mask = [[1.0/9, 1.0/9, 1.0/9],
                            [1.0/9, 1.0/9, 1.0/9],
                            [1.0/9, 1.0/9, 1.0/9]];

            // 임시 입력 배열 (입력배열 + 2)
            let tmpInImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpInImage[m] = new Array(inH+2);
                for(let n=0;n<inH+2;n++){
                    tmpInImage[m][n] = new Array(inW+2);
                }
            }
            

            // 임시 출력 배열 (출력배열과 크기 동일)
            let tmpOutImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpOutImage[m] = new Array(outH+2);
                for(let n=0;n<inH+2;n++){
                    tmpOutImage[m][n] = new Array(outW+2);
                }
            }

            // 임시 입력 배열 초기화 ((127로)/평균값/인접값)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH+2; i++) {
                    for (let k=0; k<inW+2; k++) {
                        tmpInImage[rgb][i][k] = 127.0;
                    }
                }
            }

            // 입력 이미지 -> 임시 입력 이미지의 중간에 넣기
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        tmpInImage[rgb][i+1][k+1] = inImage[rgb][i][k];
                    }
                }
            }
            // 영상 처리 알고리즘 --> 회선 연산(=긁어가기)
            for(let rgb=0; rgb<3; rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        // 한점 처리
                        let S = 0.0; // 9점을 곱해서 합한 결과
                        for(let m=0;m<3;m++){
                            for(let n=0;n<3;n++){
                                S += tmpInImage[rgb][i+m][k+n] * mask[m][n];
                            }  
                        }
                        tmpOutImage[rgb][i][k] = S;
                    }
                }
            }

            // 후처리 작업 (마스크의 합계가 0이면 ... 127 정도를 더해주기를 고려)
            // for(let rgb=0;rgb<3;rgb++){
            //     for (let i=0; i<outH; i++) {
            //         for (let k=0; k<outW; k++) {
            //             tmpOutImage[rgb][i][k] += 127.0;
            //         }
            //     }
            // }

            // 임시 출력 이미지 --> 원 출력 이미지
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        if((startX <= k && k< endX )&&(startY <=i && i<endY)){
                            if(tmpOutImage[rgb][i][k] > 255.0)
                                outImage[rgb][i][k] = 255;
                            else if(tmpOutImage[rgb][i][k] < 0.0)
                                outImage[rgb][i][k] = 0;
                            else
                                outImage[rgb][i][k] = parseInt(tmpOutImage[rgb][i][k]);
                        }
                        else
                        outImage[rgb][i][k] = inImage[rgb][i][k];
                    }
                }
            }
            displayImage();
    }
    function blurrImage_mouse(){
        var mouseCheck= document.getElementById("mouseEnable");
            //사각형 선택이 체크가 안되었을때!
            if(!mouseEnable.checked){
                startX = startY=0;
                endX = inW;
                endY= inH;
                blurrImage();
                return;
            }
            //사각형 체크됨.
            //마우스 이벤트 리스너 켜기
            onEventListener();
    }

 


 

<원본이미지 샤프닝 처리하기>

알고리즘
결과화면

 

function sharpenImage(){
        outH = inH;
            outW = inW;

            // 배열 선언
            outImage = new Array(3); // 3면
            for(var m=0; m<3; m++) {
                outImage[m] = new Array(outH);
                for(let n=0; n<outH; n++)
                    outImage[m][n] = new Array(outW);
            }

            // 짱 중요한거 --> 마스크를 선택
            let mask = [[-1,-1,-1],
                    [-1,9,-1],
                    [-1,-1,-1]];

            // 임시 입력 배열 (입력배열 + 2)
            let tmpInImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpInImage[m] = new Array(inH+2);
                for(let n=0;n<inH+2;n++){
                    tmpInImage[m][n] = new Array(inW+2);
                }
            }
            

            // 임시 출력 배열 (출력배열과 크기 동일)
            let tmpOutImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpOutImage[m] = new Array(outH+2);
                for(let n=0;n<inH+2;n++){
                    tmpOutImage[m][n] = new Array(outW+2);
                }
            }

            // 임시 입력 배열 초기화 ((127로)/평균값/인접값)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH+2; i++) {
                    for (let k=0; k<inW+2; k++) {
                        tmpInImage[rgb][i][k] = 127.0;
                    }
                }
            }

            // 입력 이미지 -> 임시 입력 이미지의 중간에 넣기
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        tmpInImage[rgb][i+1][k+1] = inImage[rgb][i][k];
                    }
                }
            }
            // 영상 처리 알고리즘 --> 회선 연산(=긁어가기)
            for(let rgb=0; rgb<3; rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        // 한점 처리
                        let S = 0.0; // 9점을 곱해서 합한 결과
                        for(let m=0;m<3;m++){
                            for(let n=0;n<3;n++){
                                S += tmpInImage[rgb][i+m][k+n] * mask[m][n];
                            }  
                        }
                        tmpOutImage[rgb][i][k] = S;
                    }
                }
            }

            // 후처리 작업 (마스크의 합계가 0이면 ... 127 정도를 더해주기를 고려)
            // for(let rgb=0;rgb<3;rgb++){
            //     for (let i=0; i<outH; i++) {
            //         for (let k=0; k<outW; k++) {
            //             tmpOutImage[rgb][i][k] += 127.0;
            //         }
            //     }
            // }

            // 임시 출력 이미지 --> 원 출력 이미지
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        if((startX <= k && k< endX )&&(startY <=i && i<endY)){
                        if(tmpOutImage[rgb][i][k] > 255.0)
                            outImage[rgb][i][k] = 255;
                        else if(tmpOutImage[rgb][i][k] < 0.0)
                            outImage[rgb][i][k] = 0;
                        else
                            outImage[rgb][i][k] = parseInt(tmpOutImage[rgb][i][k]);
                        }
                        else
                        outImage[rgb][i][k] = inImage[rgb][i][k];
                    }
                }
            }
            displayImage();
    }
    function sharpenImage_mouse(){
        var mouseCheck= document.getElementById("mouseEnable");
            //사각형 선택이 체크가 안되었을때!
            if(!mouseEnable.checked){
                startX = startY=0;
                endX = inW;
                endY= inH;
                sharpenImage();
                return;
            }
            //사각형 체크됨.
            //마우스 이벤트 리스너 켜기
            onEventListener();
    }

 

 

 


시연영상(유튜브):https://youtu.be/ISk3CsyR7vM


<원본이미지 가우시안 처리하기>

알고리즘
결과화면

function gaussianImage(){
        outH = inH;
            outW = inW;

            // 배열 선언
            outImage = new Array(3); // 3면
            for(var m=0; m<3; m++) {
                outImage[m] = new Array(outH);
                for(let n=0; n<outH; n++)
                    outImage[m][n] = new Array(outW);
            }

            // 짱 중요한거 --> 마스크를 선택
            let mask = [
                [1.0/16, 1.0/8, 1.0/16],
                [1.0/8, 1.0/4, 1.0/8],
                [1.0/16, 1.0/8, 1.0/16]
                        ];

            // 임시 입력 배열 (입력배열 + 2)
            let tmpInImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpInImage[m] = new Array(inH+2);
                for(let n=0;n<inH+2;n++){
                    tmpInImage[m][n] = new Array(inW+2);
                }
            }
            

            // 임시 출력 배열 (출력배열과 크기 동일)
            let tmpOutImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpOutImage[m] = new Array(outH+2);
                for(let n=0;n<inH+2;n++){
                    tmpOutImage[m][n] = new Array(outW+2);
                }
            }

            // 임시 입력 배열 초기화 ((127로)/평균값/인접값)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH+2; i++) {
                    for (let k=0; k<inW+2; k++) {
                        tmpInImage[rgb][i][k] = 127.0;
                    }
                }
            }

            // 입력 이미지 -> 임시 입력 이미지의 중간에 넣기
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        tmpInImage[rgb][i+1][k+1] = inImage[rgb][i][k];
                    }
                }
            }
            // 영상 처리 알고리즘 --> 회선 연산(=긁어가기)
            for(let rgb=0; rgb<3; rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        // 한점 처리
                        let S = 0.0; // 9점을 곱해서 합한 결과
                        for(let m=0;m<3;m++){
                            for(let n=0;n<3;n++){
                                S += tmpInImage[rgb][i+m][k+n] * mask[m][n];
                            }  
                        }
                        tmpOutImage[rgb][i][k] = S;
                    }
                }
            }

            // 후처리 작업 (마스크의 합계가 0이면 ... 127 정도를 더해주기를 고려)
            // for(let rgb=0;rgb<3;rgb++){
            //     for (let i=0; i<outH; i++) {
            //         for (let k=0; k<outW; k++) {
            //             tmpOutImage[rgb][i][k] += 127.0;
            //         }
            //     }
            // }

            // 임시 출력 이미지 --> 원 출력 이미지
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        if((startX <= k && k< endX )&&(startY <=i && i<endY)){
                            if(tmpOutImage[rgb][i][k] > 255.0)
                                outImage[rgb][i][k] = 255;
                            else if(tmpOutImage[rgb][i][k] < 0.0)
                                outImage[rgb][i][k] = 0;
                            else
                                outImage[rgb][i][k] = parseInt(tmpOutImage[rgb][i][k]);
                        }
                        else
                        outImage[rgb][i][k] = inImage[rgb][i][k];
                    }
                }
            }
            displayImage();
    }
    function gaussianImage_mouse(){
        var mouseCheck= document.getElementById("mouseEnable");
            //사각형 선택이 체크가 안되었을때!
            if(!mouseEnable.checked){
                startX = startY=0;
                endX = inW;
                endY= inH;
                gaussianImage();
                return;
            }
            //사각형 체크됨.
            //마우스 이벤트 리스너 켜기
            onEventListener();
    }

 

 


<원본이미지 고주파 샤프닝>

알고리즘
결과화면

function hpfSharpImage(){
        outH = inH;
            outW = inW;

            // 배열 선언
            outImage = new Array(3); // 3면
            for(var m=0; m<3; m++) {
                outImage[m] = new Array(outH);
                for(let n=0; n<outH; n++)
                    outImage[m][n] = new Array(outW);
            }

            // 짱 중요한거 --> 마스크를 선택
            let mask = [
                            [-1.0/9, -1.0/9, -1.0/9],
                            [-1.0/9, 8.0/9, -1.0/9],
                            [-1.0/9, -1.0/9, -1.0/9]
                        ];

            // 임시 입력 배열 (입력배열 + 2)
            let tmpInImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpInImage[m] = new Array(inH+2);
                for(let n=0;n<inH+2;n++){
                    tmpInImage[m][n] = new Array(inW+2);
                }
            }
            

            // 임시 출력 배열 (출력배열과 크기 동일)
            let tmpOutImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpOutImage[m] = new Array(outH+2);
                for(let n=0;n<inH+2;n++){
                    tmpOutImage[m][n] = new Array(outW+2);
                }
            }

            // 임시 입력 배열 초기화 ((127로)/평균값/인접값)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH+2; i++) {
                    for (let k=0; k<inW+2; k++) {
                        tmpInImage[rgb][i][k] = 127.0;
                    }
                }
            }

            // 입력 이미지 -> 임시 입력 이미지의 중간에 넣기
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        tmpInImage[rgb][i+1][k+1] = inImage[rgb][i][k];
                    }
                }
            }
            // 영상 처리 알고리즘 --> 회선 연산(=긁어가기)
            for(let rgb=0; rgb<3; rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        // 한점 처리
                        let S = 0.0; // 9점을 곱해서 합한 결과
                        for(let m=0;m<3;m++){
                            for(let n=0;n<3;n++){
                                S += 100*tmpInImage[rgb][i+m][k+n] * mask[m][n];
                            }  
                        }
                        tmpOutImage[rgb][i][k] = S;
                    }
                }
            }

            // 후처리 작업 (마스크의 합계가 0이면 ... 127 정도를 더해주기를 고려)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        tmpOutImage[rgb][i][k] += 127.0;
                    }
                }
            }

            // 임시 출력 이미지 --> 원 출력 이미지
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        if((startX <= k && k< endX )&&(startY <=i && i<endY)){
                            if(tmpOutImage[rgb][i][k] > 255.0)
                                outImage[rgb][i][k] = 255;
                            else if(tmpOutImage[rgb][i][k] < 0.0)
                                outImage[rgb][i][k] = 0;
                            else
                                outImage[rgb][i][k] = parseInt(tmpOutImage[rgb][i][k]);
                        }
                        else
                            outImage[rgb][i][k] = inImage[rgb][i][k]; 
                    }
                }
            }
            displayImage();
    }
    function hpfSharpImage_mouse(){
        var mouseCheck= document.getElementById("mouseEnable");
            //사각형 선택이 체크가 안되었을때!
            if(!mouseEnable.checked){
                startX = startY=0;
                endX = inW;
                endY= inH;
                hpfSharpImage();
                return;
            }
            //사각형 체크됨.
            //마우스 이벤트 리스너 켜기
            onEventListener();
    }

 

 


<원본이미지 이동과 차분>

알고리즘
결과화면

function sadImage(){
        outH = inH;
            outW = inW;

            // 배열 선언
            outImage = new Array(3); // 3면
            for(var m=0; m<3; m++) {
                outImage[m] = new Array(outH);
                for(let n=0; n<outH; n++)
                    outImage[m][n] = new Array(outW);
            }

            // 짱 중요한거 --> 마스크를 선택
            let mask = [
                            [0.0, -1.0, 0.0],
                            [-1.0, 2.0, 0.0],
                            [0.0, 0.0, 0.0]
                        ];

            // 임시 입력 배열 (입력배열 + 2)
            let tmpInImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpInImage[m] = new Array(inH+2);
                for(let n=0;n<inH+2;n++){
                    tmpInImage[m][n] = new Array(inW+2);
                }
            }
            

            // 임시 출력 배열 (출력배열과 크기 동일)
            let tmpOutImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpOutImage[m] = new Array(outH+2);
                for(let n=0;n<inH+2;n++){
                    tmpOutImage[m][n] = new Array(outW+2);
                }
            }

            // 임시 입력 배열 초기화 ((127로)/평균값/인접값)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH+2; i++) {
                    for (let k=0; k<inW+2; k++) {
                        tmpInImage[rgb][i][k] = 127.0;
                    }
                }
            }

            // 입력 이미지 -> 임시 입력 이미지의 중간에 넣기
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        tmpInImage[rgb][i+1][k+1] = inImage[rgb][i][k];
                    }
                }
            }
            // 영상 처리 알고리즘 --> 회선 연산(=긁어가기)
            for(let rgb=0; rgb<3; rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        // 한점 처리
                        let S = 0.0; // 9점을 곱해서 합한 결과
                        for(let m=0;m<3;m++){
                            for(let n=0;n<3;n++){
                                S += tmpInImage[rgb][i+m][k+n] * mask[m][n];
                            }  
                        }
                        tmpOutImage[rgb][i][k] = S;
                    }
                }
            }

            // 후처리 작업 (마스크의 합계가 0이면 ... 127 정도를 더해주기를 고려)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        tmpOutImage[rgb][i][k] += 127.0;
                    }
                }
            }

            // 임시 출력 이미지 --> 원 출력 이미지
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        if((startX <= k && k< endX )&&(startY <=i && i<endY)){
                            if(tmpOutImage[rgb][i][k] > 255.0)
                                outImage[rgb][i][k] = 255;
                            else if(tmpOutImage[rgb][i][k] < 0.0)
                                outImage[rgb][i][k] = 0;
                            else
                                outImage[rgb][i][k] = parseInt(tmpOutImage[rgb][i][k]);
                        }
                        else
                            outImage[rgb][i][k] = inImage[rgb][i][k];
                    }
                }
            }
            displayImage();
    }
    function sadImage_mouse(){
        var mouseCheck= document.getElementById("mouseEnable");
            //사각형 선택이 체크가 안되었을때!
            if(!mouseEnable.checked){
                startX = startY=0;
                endX = inW;
                endY= inH;
                sadImage();
                return;
            }
            //사각형 체크됨.
            //마우스 이벤트 리스너 켜기
            onEventListener();
    }

 

 

 


시연영상(유튜브): https://youtu.be/aihnEexCmkU


 

<원본이미지 유사연산자처리하기>

알고리즘
결과화면

 

function opImage(){
        outH = inH;
            outW = inW;

            // 배열 선언
            outImage = new Array(3); // 3면
            for(var m=0; m<3; m++) {
                outImage[m] = new Array(outH);
                for(let n=0; n<outH; n++)
                    outImage[m][n] = new Array(outW);
            }

            // // 짱 중요한거 --> 마스크를 선택
            // let mask = [
            //                 [0.0, -1.0, 0.0],
            //                 [-1.0, 2.0, 0.0],
            //                 [0.0, 0.0, 0.0]
            //             ];

            // 임시 입력 배열 (입력배열 + 2)
            let tmpInImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpInImage[m] = new Array(inH+2);
                for(let n=0;n<inH+2;n++){
                    tmpInImage[m][n] = new Array(inW+2);
                }
            }
            

            // 임시 출력 배열 (출력배열과 크기 동일)
            let tmpOutImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpOutImage[m] = new Array(outH+2);
                for(let n=0;n<inH+2;n++){
                    tmpOutImage[m][n] = new Array(outW+2);
                }
            }

            // 임시 입력 배열 초기화 ((127로)/평균값/인접값)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH+2; i++) {
                    for (let k=0; k<inW+2; k++) {
                        tmpInImage[rgb][i][k] = 127.0;
                    }
                }
            }

            // 입력 이미지 -> 임시 입력 이미지의 중간에 넣기
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        tmpInImage[rgb][i+1][k+1] = inImage[rgb][i][k];
                    }
                }
            }
            // 영상 처리 알고리즘 --> 회선 연산(=긁어가기)
            for(let rgb=0; rgb<3; rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        // 한점 처리
                        let max=0.0;//주변것을 곱한것중 제일 큰수
                        for(let m=0;m<3;m++){
                            for(let n=0;n<3;n++){
                                if(Math.abs(tmpInImage[rgb][i+1][k+1]-tmpInImage[rgb][i+m][k+n])>=max)
                                    max = Math.abs(tmpInImage[rgb][i+1][k+1]-tmpInImage[rgb][i+m][k+n]);
                            }  
                        }
                        tmpOutImage[rgb][i][k] = max;
                    }
                }
            }

            // 후처리 작업 (마스크의 합계가 0이면 ... 127 정도를 더해주기를 고려)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        tmpOutImage[rgb][i][k] += 127.0;
                    }
                }
            }

            // 임시 출력 이미지 --> 원 출력 이미지
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        if((startX <= k && k< endX )&&(startY <=i && i<endY)){
                            if(tmpOutImage[rgb][i][k] > 255.0)
                                outImage[rgb][i][k] = 255;
                            else if(tmpOutImage[rgb][i][k] < 0.0)
                                outImage[rgb][i][k] = 0;
                            else
                                outImage[rgb][i][k] = parseInt(tmpOutImage[rgb][i][k]);
                        }
                        else
                            outImage[rgb][i][k] = inImage[rgb][i][k]; 
                    }
                }
            }
            displayImage();
    }
    function opImage_mouse(){
        var mouseCheck= document.getElementById("mouseEnable");
            //사각형 선택이 체크가 안되었을때!
            if(!mouseEnable.checked){
                startX = startY=0;
                endX = inW;
                endY= inH;
                opImage();
                return;
            }
            //사각형 체크됨.
            //마우스 이벤트 리스너 켜기
            onEventListener();
    }

 

 

 


<원본이미지 로버츠 마스크 수평/수직 처리하기>

알고리즘
결과화면

 

function robertsImage(){
        outH = inH;
            outW = inW;

            // 배열 선언
            outImage = new Array(3); // 3면
            for(var m=0; m<3; m++) {
                outImage[m] = new Array(outH);
                for(let n=0; n<outH; n++)
                    outImage[m][n] = new Array(outW);
            }

            // 짱 중요한거 --> 마스크를 선택
            let mask = [
                            [-1.0, 0.0, -1.0],
                            [0.0, 2.0, 0.0],
                            [0.0, 0.0, 0.0]
                        ];

            // 임시 입력 배열 (입력배열 + 2)
            let tmpInImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpInImage[m] = new Array(inH+2);
                for(let n=0;n<inH+2;n++){
                    tmpInImage[m][n] = new Array(inW+2);
                }
            }
            

            // 임시 출력 배열 (출력배열과 크기 동일)
            let tmpOutImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpOutImage[m] = new Array(outH+2);
                for(let n=0;n<inH+2;n++){
                    tmpOutImage[m][n] = new Array(outW+2);
                }
            }

            // 임시 입력 배열 초기화 ((127로)/평균값/인접값)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH+2; i++) {
                    for (let k=0; k<inW+2; k++) {
                        tmpInImage[rgb][i][k] = 127.0;
                    }
                }
            }

            // 입력 이미지 -> 임시 입력 이미지의 중간에 넣기
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        tmpInImage[rgb][i+1][k+1] = inImage[rgb][i][k];
                    }
                }
            }
            // 영상 처리 알고리즘 --> 회선 연산(=긁어가기)
            for(let rgb=0; rgb<3; rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        // 한점 처리
                        let S = 0.0; // 9점을 곱해서 합한 결과
                        for(let m=0;m<3;m++){
                            for(let n=0;n<3;n++){
                                S += tmpInImage[rgb][i+m][k+n] * mask[m][n];
                            }  
                        }
                        tmpOutImage[rgb][i][k] = S;
                    }
                }
            }

            // 후처리 작업 (마스크의 합계가 0이면 ... 127 정도를 더해주기를 고려)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        tmpOutImage[rgb][i][k] += 127.0;
                    }
                }
            }

            // 임시 출력 이미지 --> 원 출력 이미지
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        if((startX <= k && k< endX )&&(startY <=i && i<endY)){
                            if(tmpOutImage[rgb][i][k] > 255.0)
                                outImage[rgb][i][k] = 255;
                            else if(tmpOutImage[rgb][i][k] < 0.0)
                                outImage[rgb][i][k] = 0;
                            else
                                outImage[rgb][i][k] = parseInt(tmpOutImage[rgb][i][k]);
                        }
                        else
                        outImage[rgb][i][k] = inImage[rgb][i][k];
                    }
                }
            }
            displayImage();
    }
    function robertsImage_mouse(){
        var mouseCheck= document.getElementById("mouseEnable");
            //사각형 선택이 체크가 안되었을때!
            if(!mouseEnable.checked){
                startX = startY=0;
                endX = inW;
                endY= inH;
                robertsImage();
                return;
            }
            //사각형 체크됨.
            //마우스 이벤트 리스너 켜기
            onEventListener();
    }

 

 

 


<원본이미지 소벨마스크 수평/수직 처리하기>

알고리즘
결과화면

 

function sobelImage(){
        outH = inH;
            outW = inW;

            // 배열 선언
            outImage = new Array(3); // 3면
            for(var m=0; m<3; m++) {
                outImage[m] = new Array(outH);
                for(let n=0; n<outH; n++)
                    outImage[m][n] = new Array(outW);
            }

            // 짱 중요한거 --> 마스크를 선택
            let mask = [
                            [0.0, -2.0, -2.0],
                            [2.0, 0.0, -2.0],
                            [2.0, 2.0, 0.0]
                        ];

            // 임시 입력 배열 (입력배열 + 2)
            let tmpInImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpInImage[m] = new Array(inH+2);
                for(let n=0;n<inH+2;n++){
                    tmpInImage[m][n] = new Array(inW+2);
                }
            }
            

            // 임시 출력 배열 (출력배열과 크기 동일)
            let tmpOutImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpOutImage[m] = new Array(outH+2);
                for(let n=0;n<inH+2;n++){
                    tmpOutImage[m][n] = new Array(outW+2);
                }
            }

            // 임시 입력 배열 초기화 ((127로)/평균값/인접값)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH+2; i++) {
                    for (let k=0; k<inW+2; k++) {
                        tmpInImage[rgb][i][k] = 127.0;
                    }
                }
            }

            // 입력 이미지 -> 임시 입력 이미지의 중간에 넣기
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        tmpInImage[rgb][i+1][k+1] = inImage[rgb][i][k];
                    }
                }
            }
            // 영상 처리 알고리즘 --> 회선 연산(=긁어가기)
            for(let rgb=0; rgb<3; rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        // 한점 처리
                        let S = 0.0; // 9점을 곱해서 합한 결과
                        for(let m=0;m<3;m++){
                            for(let n=0;n<3;n++){
                                S += tmpInImage[rgb][i+m][k+n] * mask[m][n];
                            }  
                        }
                        tmpOutImage[rgb][i][k] = S;
                    }
                }
            }

            // 후처리 작업 (마스크의 합계가 0이면 ... 127 정도를 더해주기를 고려)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        tmpOutImage[rgb][i][k] += 127.0;
                    }
                }
            }

            // 임시 출력 이미지 --> 원 출력 이미지
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        if((startX <= k && k< endX )&&(startY <=i && i<endY)){
                            if(tmpOutImage[rgb][i][k] > 255.0)
                                outImage[rgb][i][k] = 255;
                            else if(tmpOutImage[rgb][i][k] < 0.0)
                                outImage[rgb][i][k] = 0;
                            else
                                outImage[rgb][i][k] = parseInt(tmpOutImage[rgb][i][k]);
                        }
                        else
                            outImage[rgb][i][k] = inImage[rgb][i][k];
                    }
                }
            }
            displayImage();
    }
    function sobelImage_mouse(){
        var mouseCheck= document.getElementById("mouseEnable");
            //사각형 선택이 체크가 안되었을때!
            if(!mouseEnable.checked){
                startX = startY=0;
                endX = inW;
                endY= inH;
                sobelImage();
                return;
            }
            //사각형 체크됨.
            //마우스 이벤트 리스너 켜기
            onEventListener();
    }

 

 

 


시연 영상(유튜브): https://youtu.be/o7OzQJP5oNw


 

<원본이미지 프리윗마스크 수평/수직 처리하기>

알고리즘
결과화면

 

function prewittImage(){
        outH = inH;
            outW = inW;

            // 배열 선언
            outImage = new Array(3); // 3면
            for(var m=0; m<3; m++) {
                outImage[m] = new Array(outH);
                for(let n=0; n<outH; n++)
                    outImage[m][n] = new Array(outW);
            }

            // 짱 중요한거 --> 마스크를 선택
            let mask = [
                            [0.0, -1.0, -2.0],
                            [1.0, 0.0, -1.0],
                            [2.0, 1.0, 0.0]
                        ];

            // 임시 입력 배열 (입력배열 + 2)
            let tmpInImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpInImage[m] = new Array(inH+2);
                for(let n=0;n<inH+2;n++){
                    tmpInImage[m][n] = new Array(inW+2);
                }
            }
            

            // 임시 출력 배열 (출력배열과 크기 동일)
            let tmpOutImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpOutImage[m] = new Array(outH+2);
                for(let n=0;n<inH+2;n++){
                    tmpOutImage[m][n] = new Array(outW+2);
                }
            }

            // 임시 입력 배열 초기화 ((127로)/평균값/인접값)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH+2; i++) {
                    for (let k=0; k<inW+2; k++) {
                        tmpInImage[rgb][i][k] = 127.0;
                    }
                }
            }

            // 입력 이미지 -> 임시 입력 이미지의 중간에 넣기
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        tmpInImage[rgb][i+1][k+1] = inImage[rgb][i][k];
                    }
                }
            }
            // 영상 처리 알고리즘 --> 회선 연산(=긁어가기)
            for(let rgb=0; rgb<3; rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        // 한점 처리
                        let S = 0.0; // 9점을 곱해서 합한 결과
                        for(let m=0;m<3;m++){
                            for(let n=0;n<3;n++){
                                S += tmpInImage[rgb][i+m][k+n] * mask[m][n];
                            }  
                        }
                        tmpOutImage[rgb][i][k] = S;
                    }
                }
            }

            // 후처리 작업 (마스크의 합계가 0이면 ... 127 정도를 더해주기를 고려)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        tmpOutImage[rgb][i][k] += 127.0;
                    }
                }
            }

            // 임시 출력 이미지 --> 원 출력 이미지
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        if((startX <= k && k< endX )&&(startY <=i && i<endY)){
                            if(tmpOutImage[rgb][i][k] > 255.0)
                                outImage[rgb][i][k] = 255;
                            else if(tmpOutImage[rgb][i][k] < 0.0)
                                outImage[rgb][i][k] = 0;
                            else
                                outImage[rgb][i][k] = parseInt(tmpOutImage[rgb][i][k]);
                        }
                        else
                            outImage[rgb][i][k] = inImage[rgb][i][k];
                    }
                }
            }
            displayImage();
    }
    function prewittImage_mouse(){
        var mouseCheck= document.getElementById("mouseEnable");
            //사각형 선택이 체크가 안되었을때!
            if(!mouseEnable.checked){
                startX = startY=0;
                endX = inW;
                endY= inH;
                prewittImage();
                return;
            }
            //사각형 체크됨.
            //마우스 이벤트 리스너 켜기
            onEventListener();
    }

 

 


<원본이미지 라플라시안 처리하기>

알고리즘
결과화면

 

function laplacianImage(){
        outH = inH;
            outW = inW;

            // 배열 선언
            outImage = new Array(3); // 3면
            for(var m=0; m<3; m++) {
                outImage[m] = new Array(outH);
                for(let n=0; n<outH; n++)
                    outImage[m][n] = new Array(outW);
            }

            // 짱 중요한거 --> 마스크를 선택
            let mask = [
                            [0.0, 1.0, 0.0],
                            [1.0, -4.0, 1.0],
                            [0.0, 1.0, 0.0]
                        ];

            // 임시 입력 배열 (입력배열 + 2)
            let tmpInImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpInImage[m] = new Array(inH+2);
                for(let n=0;n<inH+2;n++){
                    tmpInImage[m][n] = new Array(inW+2);
                }
            }
            

            // 임시 출력 배열 (출력배열과 크기 동일)
            let tmpOutImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpOutImage[m] = new Array(outH+2);
                for(let n=0;n<inH+2;n++){
                    tmpOutImage[m][n] = new Array(outW+2);
                }
            }

            // 임시 입력 배열 초기화 ((127로)/평균값/인접값)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH+2; i++) {
                    for (let k=0; k<inW+2; k++) {
                        tmpInImage[rgb][i][k] = 127.0;
                    }
                }
            }

            // 입력 이미지 -> 임시 입력 이미지의 중간에 넣기
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        tmpInImage[rgb][i+1][k+1] = inImage[rgb][i][k];
                    }
                }
            }
            // 영상 처리 알고리즘 --> 회선 연산(=긁어가기)
            for(let rgb=0; rgb<3; rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        // 한점 처리
                        let S = 0.0; // 9점을 곱해서 합한 결과
                        for(let m=0;m<3;m++){
                            for(let n=0;n<3;n++){
                                S += tmpInImage[rgb][i+m][k+n] * mask[m][n];
                            }  
                        }
                        tmpOutImage[rgb][i][k] = S;
                    }
                }
            }

            // 후처리 작업 (마스크의 합계가 0이면 ... 127 정도를 더해주기를 고려)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        tmpOutImage[rgb][i][k] += 127.0;
                    }
                }
            }

            // 임시 출력 이미지 --> 원 출력 이미지
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        if((startX <= k && k< endX )&&(startY <=i && i<endY)){
                            if(tmpOutImage[rgb][i][k] > 255.0)
                                outImage[rgb][i][k] = 255;
                            else if(tmpOutImage[rgb][i][k] < 0.0)
                                outImage[rgb][i][k] = 0;
                            else
                                outImage[rgb][i][k] = parseInt(tmpOutImage[rgb][i][k]);
                        }
                        else
                        outImage[rgb][i][k] = inImage[rgb][i][k];
                    }
                }
            }
            displayImage();
    }
    function laplacianImage_mouse(){
        var mouseCheck= document.getElementById("mouseEnable");
            //사각형 선택이 체크가 안되었을때!
            if(!mouseEnable.checked){
                startX = startY=0;
                endX = inW;
                endY= inH;
                laplacianImage();
                return;
            }
            //사각형 체크됨.
            //마우스 이벤트 리스너 켜기
            onEventListener();
    }

 

 


<원본이미지 로그처리하기>

알고리즘
결과화면

 

function logImage(){
        outH = inH;
            outW = inW;

            // 배열 선언
            outImage = new Array(3); // 3면
            for(var m=0; m<3; m++) {
                outImage[m] = new Array(outH);
                for(let n=0; n<outH; n++)
                    outImage[m][n] = new Array(outW);
            }

            // 짱 중요한거 --> 마스크를 선택
            let mask = [
                            [0.0,0.0,-1.0,0.0,0.0],
                            [0.0,-1.0,-2.0,-1.0,0.0],
                            [-1.0,-2.0,16.0,-2.0,-1.0],
                            [0.0,-1.0,-2.0,-1.0,0.0],
                            [0.0,0.0,-1.0,0.0,0.0]
                        ];

            // 임시 입력 배열 (입력배열 + 2)
            let tmpInImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpInImage[m] = new Array(inH+4);
                for(let n=0;n<inH+4;n++){
                    tmpInImage[m][n] = new Array(inW+4);
                }
            }
            

            // 임시 출력 배열 (출력배열과 크기 동일)
            let tmpOutImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpOutImage[m] = new Array(outH+4);
                for(let n=0;n<inH+4;n++){
                    tmpOutImage[m][n] = new Array(outW+4);
                }
            }

            // 임시 입력 배열 초기화 ((127로)/평균값/인접값)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH+4; i++) {
                    for (let k=0; k<inW+4; k++) {
                        tmpInImage[rgb][i][k] = 127.0;
                    }
                }
            }

            // 입력 이미지 -> 임시 입력 이미지의 중간에 넣기
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        tmpInImage[rgb][i+2][k+2] = inImage[rgb][i][k];
                    }
                }
            }
            // 영상 처리 알고리즘 --> 회선 연산(=긁어가기)
            for(let rgb=0; rgb<3; rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        // 한점 처리
                        let S = 0.0; // 9점을 곱해서 합한 결과
                        for(let m=0;m<5;m++){
                            for(let n=0;n<5;n++){
                                S += tmpInImage[rgb][i+m][k+n] * mask[m][n];
                            }  
                        }
                        tmpOutImage[rgb][i][k] = S;
                    }
                }
            }

            // 후처리 작업 (마스크의 합계가 0이면 ... 127 정도를 더해주기를 고려)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        tmpOutImage[rgb][i][k] += 127.0;
                    }
                }
            }

            // 임시 출력 이미지 --> 원 출력 이미지
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        if((startX <= k && k< endX )&&(startY <=i && i<endY)){
                            if(tmpOutImage[rgb][i][k] > 255.0)
                                outImage[rgb][i][k] = 255;
                            else if(tmpOutImage[rgb][i][k] < 0.0)
                                outImage[rgb][i][k] = 0;
                            else
                                outImage[rgb][i][k] = parseInt(tmpOutImage[rgb][i][k]);}
                        else
                        outImage[rgb][i][k] = inImage[rgb][i][k];
                    }
                }
            }
            displayImage();
    }
    function logImage_mouse(){
        var mouseCheck= document.getElementById("mouseEnable");
            //사각형 선택이 체크가 안되었을때!
            if(!mouseEnable.checked){
                startX = startY=0;
                endX = inW;
                endY= inH;
                logImage();
                return;
            }
            //사각형 체크됨.
            //마우스 이벤트 리스너 켜기
            onEventListener();
    }

 

 


시연 영상(유튜브): https://youtu.be/vfYO73j8P-8


 

<원본이미지 도그처리하기>

알고리즘
결과화면

 

function dogImage(){
        outH = inH;
            outW = inW;

            // 배열 선언
            outImage = new Array(3); // 3면
            for(var m=0; m<3; m++) {
                outImage[m] = new Array(outH);
                for(let n=0; n<outH; n++)
                    outImage[m][n] = new Array(outW);
            }

            // 짱 중요한거 --> 마스크를 선택
            let mask = [
                            [0.0,0.0,0.0,-1.0,-1.0,-1.0,0.0,0.0,0.0],
                            [0.0,-2.0,-3.0,-3.0,-3.0,-3.0,-3.0,-2.0,0.0],
                            [0.0,-3.0,-2.0,-1.0,-1.0,-1.0,-2.0,-3.0,0.0],
                            [-1.0,-3.0,-1.0,9.0,9.0,9.0,-1.0,-3.0,-1.0],
                            [-1.0,-3.0,-1.0,9.0,19.0,9.0,-1.0,-3.0,-1.0],
                            [-1.0,-3.0,-1.0,9.0,9.0,9.0,-1.0,-3.0,-1.0],
                            [0.0,-3.0,-2.0,-1.0,-1.0,-1.0,-2.0,-3.0,0.0],
                            [0.0,-2.0,-3.0,-3.0,-3.0,-3.0,-3.0,-2.0,0.0],
                            [0.0,0.0,0.0,-1.0,-1.0,-1.0,0.0,0.0,0.0]
                        ];

            // 임시 입력 배열 (입력배열 + 2)
            let tmpInImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpInImage[m] = new Array(inH+8);
                for(let n=0;n<inH+8;n++){
                    tmpInImage[m][n] = new Array(inW+8);
                }
            }
            

            // 임시 출력 배열 (출력배열과 크기 동일)
            let tmpOutImage = new Array(3);
            for(let m=0;m<3;m++){
                tmpOutImage[m] = new Array(outH+8);
                for(let n=0;n<inH+8;n++){
                    tmpOutImage[m][n] = new Array(outW+8);
                }
            }

            // 임시 입력 배열 초기화 ((127로)/평균값/인접값)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH+8; i++) {
                    for (let k=0; k<inW+8; k++) {
                        tmpInImage[rgb][i][k] = 127.0;
                    }
                }
            }

            // 입력 이미지 -> 임시 입력 이미지의 중간에 넣기
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        tmpInImage[rgb][i+4][k+4] = inImage[rgb][i][k];
                    }
                }
            }
            // 영상 처리 알고리즘 --> 회선 연산(=긁어가기)
            for(let rgb=0; rgb<3; rgb++){
                for (let i=0; i<inH; i++) {
                    for (let k=0; k<inW; k++) {
                        // 한점 처리
                        let S = 0.0; // 9점을 곱해서 합한 결과
                        for(let m=0;m<9;m++){
                            for(let n=0;n<9;n++){
                                S += tmpInImage[rgb][i+m][k+n] * mask[m][n];
                            }  
                        }
                        tmpOutImage[rgb][i][k] = S;
                    }
                }
            }

            // 후처리 작업 (마스크의 합계가 0이면 ... 127 정도를 더해주기를 고려)
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        tmpOutImage[rgb][i][k] += 127.0;
                    }
                }
            }

            // 임시 출력 이미지 --> 원 출력 이미지
            for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        if((startX <= k && k< endX )&&(startY <=i && i<endY)){
                            if(tmpOutImage[rgb][i][k] > 255.0)
                                outImage[rgb][i][k] = 255;
                            else if(tmpOutImage[rgb][i][k] < 0.0)
                                outImage[rgb][i][k] = 0;
                            else
                                outImage[rgb][i][k] = parseInt(tmpOutImage[rgb][i][k]);
                        }
                        else 
                            outImage[rgb][i][k] = inImage[rgb][i][k];
                    }
                }
            }
            displayImage();
    }
    function dogImage_mouse(){
        var mouseCheck= document.getElementById("mouseEnable");
            //사각형 선택이 체크가 안되었을때!
            if(!mouseEnable.checked){
                startX = startY=0;
                endX = inW;
                endY= inH;
                dogImage();
                return;
            }
            //사각형 체크됨.
            //마우스 이벤트 리스너 켜기
            onEventListener();
    }

 

 

 


<원본이미지 모자이크 처리하기>

알고리즘
결과화면

function mosaic(){
        var scale = Math.pow(2,parseInt(prompt("모자이크 크기", "")));
        if (scale>inH) scale = inH;
          // (중요!) 출력 이미지의 크기가 결정 ---> 알고리즘에 의존...
        outH=inH;
        outW=inW;
            // 출력 영상의 2차원 메모리 할당
        outImage = new Array(3);
        for(var m=0; m<3; m++){
            outImage[m] = new Array(outH);
            for(let n=0; n<outH; n++)
                outImage[m][n] = new Array(outW);
        }
        // 임시 입력 배열 (입력배열 + 2)
        let tmpInImage = new Array(3);
        for(let m=0;m<3;m++){
            tmpInImage[m] = new Array(outH);
            for(let n=0;n<outH+2;n++){
                tmpInImage[m][n] = new Array(outH);
            }
        }
            
        // **** 진짜 영상처리 알고리즘 *****
        //모자이크처리
        for (var rgb=0; rgb<3; rgb++) {
            for(var i=0; i<inH-scale+1; i+=scale){
                for(var k=0; k<inW-scale+1; k+=scale){
                    var mean = 0.0;
                    for(var m=0; m<scale; m++){
                        for(var n=0; n<scale; n++){
                            mean += inImage[rgb][i+m][k+n]/Math.pow(scale,2);
                        }
                    }
                    for(var m=0; m<scale; m++){
                        for(var n=0; n<scale; n++)
                        tmpInImage[rgb][i+m][k+n] = mean;
                    }
                }
            }
        }
        // 임시 출력 이미지 --> 원 출력 이미지
        for(let rgb=0;rgb<3;rgb++){
                for (let i=0; i<outH; i++) {
                    for (let k=0; k<outW; k++) {
                        if((startX <= k && k< endX )&&(startY <=i && i<endY)){
                            outImage[rgb][i][k]=tmpInImage[rgb][i][k];
                            }
                        else{
                            outImage[rgb][i][k] = inImage[rgb][i][k];
                        }
                    }
                }
            }
        
        displayImage();
    }
    function mosaic_mouse(){
        var mouseCheck= document.getElementById("mouseEnable");
            //사각형 선택이 체크가 안되었을때!
            if(!mouseEnable.checked){
                startX = startY=0;
                endX = inW;
                endY= inH;
                mosaic();
                return;
            }
            //사각형 체크됨.
            //마우스 이벤트 리스너 켜기
            onEventListener();
    }