# Web APIの利用方法

このチュートリアルでは、サンプルアプリケーションを通して、デバイスカメラでの写真撮影ができる [MediaDevices API ](https://developer.mozilla.org/ja/docs/Web/API/MediaDevices)の使用方法を説明します。

## Electron TODOアプリの作成

まず、Monacaテンプレートを使用してアプリケーションを作成しましょう。\
Monacaダッシュボードから、 **`新しいプロジェクトを作る → サンプルアプリケーション`** に移動します。 次に、テンプレートリストから `Electron TODOアプリ` を選択し、プロジェクト名と説明を入力して、プロジェクトを作成します。

![](/files/-Mgxt79Br87IQl0KduPY)

### アプリケーション機能

このサンプルアプリケーションは、ToDoリストを作成および管理できます。\
ユーザーは、既存の写真をアップロードするか、写真を撮影して追加できます。リストはローカルストレージに保存されます。

{% hint style="info" %}
このチュートリアルでは、MediaCapture APIを使用して写真を撮る方法の説明に焦点を当てます。
{% endhint %}

アプリケーションを開くと、ローカルストレージに保存されているアイテムが表示されます。

![アプリケーションダッシュボード](/files/-MgxtDzpdA0lCsiv63ia)

新しいアイテムを作成するには、アプリケーションの右側にある `+ new` ボタンをクリックします。\
新しいモーダルダイアログが表示されます。 `camera` ボタンをクリックして、ToDoアイテムの入力、既存の写真のアップロードまたは新しい写真の撮影を行うことができます。

![Add New Item](/files/-MgxtMxuJgvWYBVJQXEF)

`camera` ボタンをクリックすると、カメラのビューを持つ別のモーダルダイアログが表示されます。\
`Capture` ボタンを押すと、ボックス内のレンダリングがキャプチャされ、画像として保存されます。

![](/files/-Mgxtb1EgpTayXedEq4j)

## &#x20;![](https://github.com/monaca/docs-monaca-ja/tree/b9d9de0c4acdfb2264db006ad844c26a677be9ec/images/cordova_electron/electron_todo_taking_picture.jpg)HTMLの説明

### カメラモーダル

次のコードは、カメラモーダルについてです。\
`camera` ボタンをクリックすると、このモーダルが表示されます。モーダルには、3つのボタン`rotate`、`capture`、 `cancel` があります。\
`rotate` ボタンは、デバイスが前面カメラと背面カメラの切り替えをサポートしている場合にのみ表示されます。\
video要素(id=video-container)は、内蔵のカメラからの映像をストリーミングするために使用されています。

```markup
<div class="modal fade" id="camera-modal" tabindex="-1" data-backdrop="static" role="dialog" aria-labelledby="camera-modal-label" aria-hidden="true">
    <div class="modal-dialog modal-dialog-centered" role="document">
        <div class="modal-content">
            <div class="camera-header-modal"></div>
            <div class="camera-modal-body modal-body text-center">
                <video id="video-container" class="camera-preview" autoplay></video>
            </div>
            <a id="cordova-camera-cancel" class="btn enabled camera-close-btn" data-dismiss="modal"><i class="fa fa-times"></i> cancel</a>
            <a id="rotate-camera" class="btn enabled camera-rotate-btn"><i class="fa fa-sync"></i> Rotate</a>
            <a id="camera-capture" class="btn enabled camera-capture-btn" data-dismiss="modal"><i class="fa fa-camera"></i> Capture</a>
        </div>
    </div>
</div>
```

## JavaScriptの説明

### グローバル変数宣言

カメラ機能に関する重要な変数を簡単に見てみましょう。

* `isFrontCamera`: フロントカメラとリアカメラを切り替えるために使用されます。
* `FRONT_CAMERA`: mediaDevices APIの [facingMode Enum ](https://w3c.github.io/mediacapture-main/#dom-videofacingmodeenum)のフロントカメラ値を保存するために使用されます。
* `REAR_CAMERA`: mediaDevices APIの [facingMode Enum ](https://w3c.github.io/mediacapture-main/#dom-videofacingmodeenum)の背面カメラ値を保存するために使用されます。

```javascript
let isFrontCamera;
const FRONT_CAMERA = 'user';
const REAR_CAMERA = 'environment';
const videoContainer = document.getElementById('video-container');
const btnOpenCameraModal = document.getElementById('open-camera-modal');
const btnRotateCamera = document.getElementById('rotate-camera');
...
```

### mediaDevices API サポートの確認

次のコードは、（1）mediaDevices APIがサポートされているかどうかを確認し、\
（2）デバイスがAndroidでrearカメラをデフォルトとして使用している場合は `rotate` ボタンをオンにします。

```javascript
function initialize() {
  // Check if getUserMedia is supported on the device
  if (!hasMediaDevicesApi()) {
    btnOpenCameraModal.hidden = true;
  }
  if (isAndroidOS()) {
    // use rear camera for android
    btnRotateCamera.hidden = false;
    isFrontCamera = false;
  } else {
    // use front camera for browser/electron
    btnRotateCamera.hidden = true;
    isFrontCamera = true;
  }
  ...
}

function hasMediaDevicesApi() {
  return !!(navigator.mediaDevices &&
    navigator.mediaDevices.getUserMedia);
}
```

### カメラのオン/オフ

`MediaStream` を生成するメディア入力の使用許可をユーザーに求めるために、`getUserMedia()`を使用します。\
ストリームには、ビデオトラック（カメラ、ビデオ録画デバイス、画面共有サービスなど）、オーディオトラック、他のトラックタイプを含めることができます。詳細については、こちらの[ 公式ドキュメント ](https://developer.mozilla.org/ja/docs/Web/API/MediaDevices)を参照してください。

```javascript
var promise = navigator.mediaDevices.getUserMedia(constraints);
```

この関数は Promise を返し、 [MediaStreamConstraints ](https://developer.mozilla.org/ja/docs/Web/API/MediaStreamConstraints)オブジェクトをパラメーターとして受け入れます。

次のコードでは、幅と高さを `250` ピクセルに指定し、指定された引数に基づいてカメラに面するモードを設定します。\
カメラデバイスが正常に接続されると、 [Media Stream ](https://developer.mozilla.org/ja/docs/Web/API/MediaStream)オブジェクトが返され、`video` 要素に割り当てられます。

```javascript
function turnOnCamera(frontCamera) {
  const facingModeOption = frontCamera ? FRONT_CAMERA : REAR_CAMERA;
  const constraints = {
    video: {
      width: {
        exact: 250
      },
      height: {
        exact: 250
      },
      facingMode: facingModeOption
    }
  };
  // Access to the camera and turn it own
  navigator.mediaDevices.getUserMedia(constraints)
    .then(handleSuccess)
    .catch(handleError);

  function handleSuccess(stream) {
    videoContainer.srcObject = stream;
  }

  function handleError(error) {
    alert('Could not get user media API' + JSON.stringify(error));
  }
}
```

カメラをオンにするには、トラックに関連付けられているすべてのソースを停止する必要があります。

```javascript
function turnOfCamera() {
  if (videoContainer && videoContainer.srcObject) {
    videoContainer.srcObject.getTracks().forEach(function(track) {
      track.stop();
    });
    videoContainer.srcObject = null;
  }
}
```

次の機能は、カメラを前面と背面に切り替えます。

```javascript
function rotateCamera(e) {
  isFrontCamera = !isFrontCamera;
  turnOfCamera();
  turnOnCamera(isFrontCamera);
}
```

### 写真を撮る

ビデオ ストリーム/トラックから写真を撮るには、まず `canvas` 幅と高さをvideoContainerと合わせます。\
次に、すべてのトラックを停止し、最後のトラックを画像形式に変換します。

```javascript
function takePicture(e) {
  const canvas = document.createElement('canvas');
  // Saving current image
  canvas.width = videoContainer.videoWidth;
  canvas.height = videoContainer.videoHeight;
  canvas.getContext('2d').drawImage(videoContainer, 0, 0);
  // If the video source Object is set, stop all tracks
  if (videoContainer.srcObject) {
    videoContainer.srcObject.getTracks().forEach(function(track) {
      track.stop();
      try {
        // Other browsers will fall back to image/png
        todoItemImage.src = canvas.toDataURL('image/webp');
      } catch (error) {
        alert('Could not get the picture.' + JSON.stringify(error));
      }
    });
  }
}
```

See Also:

* [Electronアプリのビルド](/products_guide/monaca_ide/build/electron.md)


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://ja.docs.monaca.io/tutorials/cordova_electron/use_web_api.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
