# Drawing Module API 문서

## 📋 개요

Drawing Module은 웹 브라우저에서 사용할 수 있는 독립적인 Canvas 기반 그리기 도구입니다. 모달 형태의 UI를 제공하며, 다양한 그리기 기능과 이미지 편집 기능을 포함합니다.

## 🚀 빠른 시작

### 1. 파일 포함

```html
<!DOCTYPE html>
<html>
<head>
    <!-- Bootstrap CSS (선택사항) -->
    <link href="https://cdn.jsdelivr.net/npm/bootstrap@5.1.3/dist/css/bootstrap.min.css" rel="stylesheet">
    <!-- Bootstrap Icons (선택사항) -->
    <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap-icons@1.8.1/font/bootstrap-icons.css">
    <!-- Drawing Module CSS (필수) -->
    <link href="css/drawingModule.css" rel="stylesheet">
</head>
<body>
    <!-- jQuery (필수) -->
    <script src="https://code.jquery.com/jquery-3.6.0.min.js"></script>
    <!-- Drawing Module JS (필수) -->
    <script src="js/drawingModule.js"></script>
</body>
</html>
```

### 2. 기본 사용법

```javascript
// 기본 인스턴스 생성
const drawer = new DrawingModule({
    container: 'body',
    onSave: (data) => {
        console.log('저장된 이미지:', data.imageData);
        console.log('저장 시간:', data.timestamp);
    }
});

// 그리기 도구 표시
drawer.show();
```

## 📊 API 참조

### 생성자 (Constructor)

```javascript
new DrawingModule(options)
```

#### 옵션 매개변수

| 옵션 | 타입 | 기본값 | 설명 |
|------|------|--------|------|
| `container` | string | 'body' | 모달을 생성할 컨테이너 선택자 |
| `width` | number | 800 | 모달의 전체 너비 (px) |
| `height` | number | 600 | 모달의 전체 높이 (px) |
| `canvasWidth` | number | 320 | 캔버스의 실제 너비 (px) |
| `canvasHeight` | number | 240 | 캔버스의 실제 높이 (px) |
| `title` | string | '그리기 도구' | 모달 헤더 제목 |
| `initialImage` | string | null | 초기에 로드할 이미지 URL 또는 데이터 URL |
| `onSave` | function | null | 저장 시 호출되는 콜백 함수 |
| `onCancel` | function | null | 취소 시 호출되는 콜백 함수 |

#### 콜백 함수 시그니처

**onSave 콜백:**
```javascript
onSave: (data) => {
    // data.imageData - base64 인코딩된 이미지 데이터
    // data.timestamp - 저장 시각 (Date 객체)
    // data.width - 캔버스 너비
    // data.height - 캔버스 높이
}
```

**onCancel 콜백:**
```javascript
onCancel: () => {
    // 사용자가 취소 버튼을 클릭했을 때 호출
}
```

### 메서드 (Methods)

#### show()
그리기 도구 모달을 표시합니다.

```javascript
drawer.show();
```

#### hide()
그리기 도구 모달을 숨깁니다.

```javascript
drawer.hide();
```

#### loadImage(imageUrl)
캔버스에 이미지를 로드합니다.

```javascript
drawer.loadImage('path/to/image.png');
// 또는 데이터 URL
drawer.loadImage('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAYAAAAfFcSJAAAADUlEQVR42mNkYPhfDwAChwGA60e6kgAAAABJRU5ErkJggg==');
```

#### clear()
캔버스의 모든 내용을 지웁니다.

```javascript
drawer.clear();
```

#### getImageData()
현재 캔버스의 이미지 데이터를 반환합니다.

```javascript
const imageData = drawer.getImageData();
console.log(imageData); // base64 문자열
```

## 🎨 주요 기능

### 그리기 모드
- **점연결 (Polyline)**: 클릭한 점들을 연결하여 선을 그립니다
- **직선 (Line)**: 시작점과 끝점을 클릭하여 직선을 그립니다
- **자유선 (Free)**: 마우스를 드래그하여 자유롭게 선을 그립니다

### 추가 기능
- **직각 모드**: 수평/수직선만 그리기 (체크박스로 활성화)
- **색상 선택**: 16진수 컬러 피커로 선 색상 변경
- **선 굵기 조절**: 1-10px 범위의 슬라이더로 선 굵기 조정
- **지우개**: 원형 지우개로 특정 영역 삭제 (크기 조절 가능)
- **텍스트 추가**: 클릭한 위치에 텍스트 입력
- **실행취소 (Undo)**: 마지막 작업 되돌리기
- **초기화**: 캔버스의 모든 내용 삭제
- **터치 지원**: 모바일/태블릿 디바이스 터치 이벤트 지원

## 📱 사용 예제

### 1. 기본 그리기 도구

```javascript
const basicDrawer = new DrawingModule({
    container: 'body',
    onSave: (data) => {
        // 이미지를 로컬 저장소에 저장
        localStorage.setItem('drawing', data.imageData);
        alert('그리기가 저장되었습니다!');
    }
});
basicDrawer.show();
```

### 2. 커스텀 크기 캔버스

```javascript
const largeDrawer = new DrawingModule({
    container: '#myContainer',
    canvasWidth: 640,
    canvasHeight: 480,
    title: '큰 캔버스 그리기',
    onSave: (data) => {
        console.log(`캔버스 크기: ${data.width}x${data.height}`);
        downloadImage(data.imageData, 'large-drawing.png');
    }
});
largeDrawer.show();
```

### 3. 이미지 편집

```javascript
const imageEditor = new DrawingModule({
    container: 'body',
    initialImage: '/path/to/existing-image.jpg',
    title: '이미지 편집',
    onSave: (data) => {
        // 편집된 이미지를 서버에 업로드
        uploadImageToServer(data.imageData);
    },
    onCancel: () => {
        console.log('이미지 편집이 취소되었습니다.');
    }
});
imageEditor.show();
```

### 4. 서버로 이미지 저장

```javascript
const drawer = new DrawingModule({
    container: 'body',
    onSave: (data) => {
        // AJAX로 서버에 이미지 전송
        $.ajax({
            url: '/api/save-drawing',
            method: 'POST',
            data: {
                image: data.imageData,
                timestamp: data.timestamp.toISOString(),
                width: data.width,
                height: data.height
            },
            success: function(response) {
                alert('서버에 저장되었습니다!');
                console.log('저장된 이미지 ID:', response.imageId);
            },
            error: function(error) {
                alert('저장에 실패했습니다: ' + error.responseText);
            }
        });
    }
});
drawer.show();
```

### 5. 다중 인스턴스

```javascript
// 동시에 여러 개의 그리기 도구 사용
const drawer1 = new DrawingModule({
    container: 'body',
    title: '그리기 1',
    canvasWidth: 200,
    canvasHeight: 200,
    onSave: (data) => console.log('Drawing 1 saved')
});

const drawer2 = new DrawingModule({
    container: 'body',
    title: '그리기 2',
    canvasWidth: 300,
    canvasHeight: 200,
    onSave: (data) => console.log('Drawing 2 saved')
});

drawer1.show();
setTimeout(() => drawer2.show(), 100); // 약간의 지연
```

## 🛠️ 유틸리티 함수

### 이미지 다운로드 함수

```javascript
function downloadImage(dataUrl, filename) {
    const link = document.createElement('a');
    link.download = filename;
    link.href = dataUrl;
    link.click();
}

// 사용법
const drawer = new DrawingModule({
    onSave: (data) => {
        downloadImage(data.imageData, 'my-drawing.png');
    }
});
```

### Base64를 Blob으로 변환

```javascript
function dataURLtoBlob(dataURL) {
    const arr = dataURL.split(',');
    const mime = arr[0].match(/:(.*?);/)[1];
    const bstr = atob(arr[1]);
    let n = bstr.length;
    const u8arr = new Uint8Array(n);

    while (n--) {
        u8arr[n] = bstr.charCodeAt(n);
    }

    return new Blob([u8arr], {type: mime});
}

// 사용법
const drawer = new DrawingModule({
    onSave: (data) => {
        const blob = dataURLtoBlob(data.imageData);
        const formData = new FormData();
        formData.append('image', blob, 'drawing.png');

        // FormData를 서버에 전송
        fetch('/upload', {
            method: 'POST',
            body: formData
        });
    }
});
```

## 🎯 파일 구조

```
project/
├── test_drawing.php          # 테스트 페이지 (PHP)
├── css/
│   └── drawingModule.css     # 스타일시트
├── js/
│   └── drawingModule.js      # 메인 JavaScript 모듈
└── drawModule.md            # 이 문서
```

## 🔧 커스터마이징

### CSS 커스터마이징

주요 CSS 클래스들을 오버라이드하여 스타일을 변경할 수 있습니다:

```css
/* 모달 배경색 변경 */
.dm-modal {
    background-color: rgba(0, 0, 0, 0.8);
}

/* 버튼 색상 변경 */
.dm-btn-primary {
    background-color: #custom-color;
}

/* 캔버스 테두리 스타일 변경 */
#dmCanvas {
    border: 3px solid #custom-border-color;
}
```

### JavaScript 이벤트 훅

모듈의 동작을 커스터마이징하려면 콜백을 사용하세요:

```javascript
const drawer = new DrawingModule({
    onSave: (data) => {
        // 저장 전 검증
        if (data.width < 100 || data.height < 100) {
            alert('그림이 너무 작습니다!');
            return;
        }

        // 커스텀 저장 로직
        customSaveFunction(data);
    },
    onCancel: () => {
        // 취소 시 정리 작업
        cleanupResources();
    }
});
```

## 🚨 주의사항

1. **jQuery 의존성**: 이 모듈은 jQuery에 의존하므로 jQuery를 먼저 로드해야 합니다.

2. **CSS 파일 필수**: `drawingModule.css` 파일이 없으면 UI가 제대로 표시되지 않습니다.

3. **브라우저 호환성**: HTML5 Canvas를 지원하는 브라우저에서만 작동합니다.

4. **이미지 크기 제한**: 매우 큰 캔버스는 브라우저 성능에 영향을 줄 수 있습니다.

5. **메모리 관리**: 여러 인스턴스를 사용할 때는 사용하지 않는 인스턴스를 적절히 정리하세요.

## 🐛 문제 해결

### 일반적인 문제들

**Q: 모달이 표시되지 않아요.**
A: CSS 파일이 제대로 로드되었는지, 그리고 `show()` 메서드를 호출했는지 확인하세요.

**Q: 그리기가 작동하지 않아요.**
A: jQuery가 로드되었는지, 그리고 JavaScript 콘솔에 오류가 없는지 확인하세요.

**Q: 이미지 저장이 안 돼요.**
A: `onSave` 콜백이 제대로 설정되었는지 확인하세요.

**Q: 모바일에서 터치가 작동하지 않아요.**
A: 최신 버전의 모듈을 사용하고 있는지 확인하세요. 터치 이벤트는 자동으로 처리됩니다.

## 📄 라이선스

이 모듈은 MIT 라이선스 하에 배포됩니다.

## 🔄 업데이트 내역

- **v1.0.0**: 초기 릴리스
  - 기본 그리기 기능
  - 모달 UI
  - 이미지 로드/저장
  - 터치 지원