맞춤 웹 수신기에 핵심 기능 추가

이 페이지에는 맞춤 웹 수신기 앱

  1. 내장 플레이어 UI를 나타내는 cast-media-player 요소 입니다.
  2. 다양한 스타일을 지정할 수 있는 cast-media-player 요소를 위한 맞춤 CSS와 유사한 스타일 background-image, splash-image, font-family입니다.
  3. 웹 수신기 프레임워크를 로드하는 스크립트 요소
  4. 메시지를 가로채고 이벤트를 처리하는 JavaScript 코드
  5. 자동재생 대기 중입니다.
  6. 재생을 구성하는 옵션입니다.
  7. 웹 수신기 컨텍스트를 설정하는 옵션입니다.
  8. 웹 수신기 앱에서 지원하는 명령어를 설정하는 옵션입니다.
  9. 웹 수신기 애플리케이션을 시작하는 JavaScript 호출

애플리케이션 구성 및 옵션

애플리케이션 구성

CastReceiverContext 개발자에게 노출되는 가장 바깥쪽 클래스이며 기본 라이브러리를 제공하며 웹 수신기 SDK의 초기화를 처리합니다. SDK 애플리케이션 개발자가 SDK를 통해 SDK를 구성할 수 있는 CastReceiverOptions 이러한 구성은 애플리케이션 실행당 한 번 평가되며 호출 시 선택적 매개변수를 설정할 때 SDK가 start

아래 예는 발신자 연결이 아직 활발하게 연결되어 있는지 확인합니다. Web Receiver가 발신자와 통신할 수 있도록 maxInactivity 1초가 경과하면 SENDER_DISCONNECTED 이벤트가 전달됩니다. 아래 구성 이 제한 시간을 재정의합니다. 이는 문제를 디버깅할 때 유용할 수 있으며 웹 수신기 앱이 Chrome 원격 디버거 세션을 닫지 않도록 IDLE 상태인 연결된 발신자가 0개인 경우.

const context = cast.framework.CastReceiverContext.getInstance();
const options = new cast.framework.CastReceiverOptions();
options.maxInactivity = 3600; // Development only
context.start(options);

플레이어 구성

콘텐츠를 로드할 때 웹 수신기 SDK는 재생을 구성하는 방법을 제공합니다. 변수(예: 정보, 구성을 재시도하고 cast.framework.PlaybackConfig 이 정보는 Google에서 처리합니다. PlayerManager 플레이어가 생성되었을 때 평가됩니다. 플레이어가 생성됨 새 로드가 웹 수신기 SDK에 전달될 때마다 플레이어가 생성된 후의 PlaybackConfig는 다음 단계에서 평가됩니다. 콘텐츠 로드가 필요합니다. SDK는 PlaybackConfig

  • CastReceiverOptions.playbackConfig 를 설정하여 애플리케이션을 초기화할 때 기본 구성 옵션을 CastReceiverContext입니다.
  • PlayerManager.getPlaybackConfig() 현재 구성을 가져올 수 있습니다.
  • PlayerManager.setPlaybackConfig() 현재 구성을 재정의합니다. 이 설정은 다시 재정의될 때까지만 허용됩니다.
  • PlayerManager.setMediaPlaybackInfoHandler() 로드 중인 미디어 항목에 대해서만 추가 구성을 적용 현재 구성의 맨 위에 표시됩니다 핸들러는 플레이어 직전에 호출됩니다. 만들 수 있습니다. 여기에서 변경한 사항은 영구적이지 않으며 쿼리에 포함되지 않습니다. getPlaybackConfig()님에게 전송됩니다. 다음 미디어 항목이 로드되면 이 핸들러는 다시 호출됩니다.

아래 예는 다음을 초기화할 때 PlaybackConfig를 설정하는 방법을 보여줍니다. CastReceiverContext입니다. 이 구성은 외부 IP 주소가 있는 포트의 발신 요청을 매니페스트를 가져옵니다. 핸들러는 CORS Access-Control 요청이 쿠키 또는 인증 헤더와 같은 인증 정보를 사용하여 생성되어야 합니다.

const playbackConfig = new cast.framework.PlaybackConfig();
playbackConfig.manifestRequestHandler = requestInfo => {
  requestInfo.withCredentials = true;
};
context.start({playbackConfig: playbackConfig});

아래 예는 getter를 사용하여 PlaybackConfig를 재정의하는 방법을 보여줍니다. PlayerManager에 제공된 setter입니다. 이 설정은 플레이어가 광고를 재생하도록 세그먼트 1개가 로드된 후에 콘텐츠 재생을 재개합니다.

const playerManager =
    cast.framework.CastReceiverContext.getInstance().getPlayerManager();
const playbackConfig = (Object.assign(
            new cast.framework.PlaybackConfig(), playerManager.getPlaybackConfig()));
playbackConfig.autoResumeNumberOfSegments = 1;
playerManager.setPlaybackConfig(playbackConfig);

아래 예는 특정 부하에 대해 PlaybackConfig를 재정의하는 방법을 보여줍니다. 미디어 재생 정보 핸들러를 사용하여 미디어 요청을 보냅니다. 핸들러는 애플리케이션을 호출합니다. getLicenseUrlForMedia 메서드를 구현하여 licenseUrl 현재 항목의 contentId입니다.

playerManager.setMediaPlaybackInfoHandler((loadRequestData, playbackConfig) => {
  const mediaInformation = loadRequestData.media;
  playbackConfig.licenseUrl = getLicenseUrlForMedia(mediaInformation.contentId);

  return playbackConfig;
});

이벤트 리스너

웹 수신기 SDK를 사용하면 웹 수신기 앱이 플레이어 이벤트를 처리할 수 있습니다. 이 이벤트 리스너가 cast.framework.events.EventType 매개변수(또는 이러한 매개변수의 배열)를 통해 리스너를 트리거해야 합니다. 사전 구성된 배열 디버깅에 유용한 cast.framework.events.EventType는 다음에서 찾을 수 있습니다. cast.framework.events.category 이벤트 매개변수는 이벤트에 대한 추가 정보를 제공합니다.

예를 들어 mediaStatus 다음과 같은 로직을 사용하여 이벤트를 사용합니다.

const playerManager =
    cast.framework.CastReceiverContext.getInstance().getPlayerManager();
playerManager.addEventListener(
    cast.framework.events.EventType.MEDIA_STATUS, (event) => {
      // Write your own event handling code, for example
      // using the event.mediaStatus value
});

메시지 가로채기

웹 수신기 SDK를 사용하면 웹 수신기 앱이 메시지를 가로채고 해당 메시지에서 사용자 지정 코드를 실행합니다. 메시지 인터셉터는 cast.framework.messages.MessageType 가로채기해야 하는 메시지 유형을 지정하는 매개변수입니다.

인터셉터는 수정된 요청 값으로 대체합니다. null를 반환하면 기본 메시지 핸들러입니다. 자세한 내용은 미디어 로드를 참고하세요.

예를 들어 로드 요청 데이터를 변경하려면 다음과 같은 로직을 사용하여 이를 가로채서 수정합니다.

const context = cast.framework.CastReceiverContext.getInstance();
const playerManager = context.getPlayerManager();

playerManager.setMessageInterceptor(
    cast.framework.messages.MessageType.LOAD, loadRequestData => {
      const error = new cast.framework.messages.ErrorData(
                      cast.framework.messages.ErrorType.LOAD_FAILED);
      if (!loadRequestData.media) {
        error.reason = cast.framework.messages.ErrorReason.INVALID_PARAM;
        return error;
      }

      if (!loadRequestData.media.entity) {
        return loadRequestData;
      }

      return thirdparty.fetchAssetAndAuth(loadRequestData.media.entity,
                                          loadRequestData.credentials)
        .then(asset => {
          if (!asset) {
            throw cast.framework.messages.ErrorReason.INVALID_REQUEST;
          }

          loadRequestData.media.contentUrl = asset.url;
          loadRequestData.media.metadata = asset.metadata;
          loadRequestData.media.tracks = asset.tracks;
          return loadRequestData;
        }).catch(reason => {
          error.reason = reason; // cast.framework.messages.ErrorReason
          return error;
        });
    });

context.start();

오류 처리

메시지 인터셉터에서 오류가 발생하면 Web Receiver 앱은 적절한 cast.framework.messages.ErrorTypecast.framework.messages.ErrorReason

playerManager.setMessageInterceptor(
    cast.framework.messages.MessageType.LOAD, loadRequestData => {
      const error = new cast.framework.messages.ErrorData(
                      cast.framework.messages.ErrorType.LOAD_CANCELLED);
      if (!loadRequestData.media) {
        error.reason = cast.framework.messages.ErrorReason.INVALID_PARAM;
        return error;
      }

      ...

      return fetchAssetAndAuth(loadRequestData.media.entity,
                               loadRequestData.credentials)
        .then(asset => {
          ...
          return loadRequestData;
        }).catch(reason => {
          error.reason = reason; // cast.framework.messages.ErrorReason
          return error;
        });
    });

메시지 가로채기와 이벤트 리스너 비교

메시지 가로채기와 이벤트 리스너의 주요 차이점은 다음과 같습니다. 다음과 같습니다.

  • 이벤트 리스너에서는 요청 데이터를 수정할 수 없습니다.
  • 이벤트 리스너는 분석 또는 맞춤 함수를 트리거하는 데 가장 적합합니다.
playerManager.addEventListener(cast.framework.events.category.CORE,
    event => {
        console.log(event);
    });
  • 메시지 가로채기를 사용하면 메시지를 듣고 가로채서 요청 데이터 자체를 수정할 수 있습니다.
  • 메시지 가로채기는 데이터를 요청할 수 있습니다

미디어 로드

MediaInformationcast.framework.messages.MessageType.LOAD 다음을 포함한 메시지 entity, contentUrl, contentId입니다.

  • entity 는 발신자와 수신자 모두에 대해 구현에 사용할 추천 속성입니다. 수신하기만 하면 됩니다. 속성은 재생목록이거나 재생목록이 될 수 있는 딥 링크 URL입니다. 또는 미디어 콘텐츠일 수 있습니다. 애플리케이션은 이 URL을 파싱하고 적어도 하나는 다른 두 필드 중 하나 이상을 채웁니다.
  • contentUrl 플레이어가 콘텐츠를 로드하는 데 사용할 재생 가능 URL에 해당합니다. 예를 들어 이 URL은 DASH 매니페스트를 가리킬 수 있습니다.
  • contentId 은 재생 가능한 콘텐츠 URL일 수 있습니다 (contentUrl 속성) 또는 로드 중인 콘텐츠 또는 재생목록의 고유 식별자가 포함됩니다. 이 속성을 식별자로 사용하는 경우 애플리케이션에서 contentUrl에서 재생 가능한 URL을 지정합니다.

entity를 사용하여 실제 ID 또는 키 매개변수를 저장하는 것이 좋습니다. 미디어 URL에 contentUrl를 사용합니다. 이에 대한 예는 다음 스니펫입니다. 여기서 entityLOAD 요청에 있고 재생 가능한 contentUrl를 가져옴:

playerManager.setMessageInterceptor(
    cast.framework.messages.MessageType.LOAD, loadRequestData => {
      ...

      if (!loadRequestData.media.entity) {
        // Copy the value from contentId for legacy reasons if needed
        loadRequestData.media.entity = loadRequestData.media.contentId;
      }

      return thirdparty.fetchAssetAndAuth(loadRequestData.media.entity,
                                          loadRequestData.credentials)
        .then(asset => {
          loadRequestData.media.contentUrl = asset.url;
          ...
          return loadRequestData;
        });
    });

기기 기능

getDeviceCapabilities 메서드는 연결된 Cast 기기 및 동영상의 기기 정보를 제공합니다. 오디오 장치를 연결합니다. getDeviceCapabilities 메서드는 Google 어시스턴트, 블루투스, 연결된 디스플레이 및 오디오 관련 정보 기기에서 사용할 수 있습니다.

이 메서드는 지정된 enum을 사용하여 해당 enum에 대한 기기 기능을 가져올 수 있습니다. enum은 정의된 위치 cast.framework.system.DeviceCapabilities

이 예에서는 웹 수신기 기기에서 HDR을 재생할 수 있는지 확인하고 DolbyVision(DV)(IS_HDR_SUPPORTEDIS_DV_SUPPORTED 키 사용) 각각 1개의 값으로 사용합니다.

const context = cast.framework.CastReceiverContext.getInstance();
context.addEventListener(cast.framework.system.EventType.READY, () => {
  const deviceCapabilities = context.getDeviceCapabilities();
  if (deviceCapabilities &&
      deviceCapabilities[cast.framework.system.DeviceCapabilities.IS_HDR_SUPPORTED]) {
    // Write your own event handling code, for example
    // using the deviceCapabilities[cast.framework.system.DeviceCapabilities.IS_HDR_SUPPORTED] value
  }
  if (deviceCapabilities &&
      deviceCapabilities[cast.framework.system.DeviceCapabilities.IS_DV_SUPPORTED]) {
    // Write your own event handling code, for example
    // using the deviceCapabilities[cast.framework.system.DeviceCapabilities.IS_DV_SUPPORTED] value
  }
});
context.start();

사용자 상호작용 처리

사용자는 발신자를 통해 웹 수신기 애플리케이션과 상호작용할 수 있습니다. 애플리케이션 (웹, Android, iOS), 어시스턴트 지원의 음성 명령 기기, 스마트 디스플레이의 터치 컨트롤, Android TV의 리모컨 기기에서 사용할 수 있습니다. Cast SDK는 웹 수신기 앱이 다음 작업을 할 수 있도록 다양한 API를 제공합니다. 애플리케이션 UI를 업데이트하려면 사용자 작업 상태 필요한 경우 변경사항을 전송하여 백엔드 서비스를 업데이트합니다.

지원되는 미디어 명령어

UI 컨트롤 상태는 MediaStatus.supportedMediaCommands iOS 및 Android 발신기용 확장된 컨트롤러, 수신기 및 원격 제어 터치 기기에서 실행되는 앱과 Android TV 기기의 수신기 앱이 포함됩니다. 사용자가 특정 비트 단위 Command가 속성에서 사용 설정됩니다. 즉, 사용 설정되었음을 알 수 있습니다. 값을 설정하지 않으면 사용 중지됩니다. 이러한 값은 다음과 같이 웹 수신기에서 변경할 수 있습니다.

  1. 사용 PlayerManager.setSupportedMediaCommands 특정 Commands
  2. 다음을 사용하여 새 명령어 추가 addSupportedMediaCommands
  3. 다음을 사용하여 기존 명령어 삭제 removeSupportedMediaCommands
playerManager.setSupportedMediaCommands(cast.framework.messages.Command.SEEK |
  cast.framework.messages.Command.PAUSE);

수신자가 업데이트된 MediaStatus를 준비하면 다음이 포함됩니다. supportedMediaCommands 속성의 변경사항을 확인합니다. 상태가 브로드캐스트되면 연결된 발신기 앱이 UI의 버튼을 업데이트합니다. 변경할 수 있습니다

지원되는 미디어 명령어 및 터치 기기에 관한 자세한 내용은 다음을 참고하세요. Accessing UI controls 참조하세요.

사용자 작업 상태 관리

사용자는 UI와 상호작용하거나 음성 명령을 보낼 때 콘텐츠 및 재생 중인 항목과 관련된 속성 재생 요청 재생을 제어하는 모든 광고는 SDK에 의해 자동으로 처리됩니다. 사용자가 LIKE 명령어와 같이 재생 중인 현재 항목의 속성을 수정합니다. 수신기 애플리케이션이 이를 처리해야 합니다. SDK는 일련의 API를 사용하여 이러한 유형의 요청을 처리할 수 있습니다. 이러한 요청을 지원하기 위해 해야 합니다.

  • MediaInformation 설정 userActionStates 사용자의 환경설정과 일치해야 합니다.
  • USER_ACTION 메시지를 가로채고 요청된 작업을 결정합니다.
  • MediaInformation UserActionState를 업데이트하여 UI를 업데이트합니다.

다음 스니펫은 LOAD 요청을 가로채고 LoadRequestData님의 MediaInformation 이 경우 사용자는 콘텐츠를 표시할 수 있습니다.

playerManager.setMessageInterceptor(
    cast.framework.messages.MessageType.LOAD, (loadRequestData) => {
      const userActionLike = new cast.framework.messages.UserActionState(
          cast.framework.messages.UserAction.LIKE);
      loadRequestData.media.userActionStates = [userActionLike];

      return loadRequestData;
    });

다음 스니펫은 USER_ACTION 메시지를 가로채고 해당 백엔드를 반환합니다 그런 다음 수신자의 UserActionState

playerManager.setMessageInterceptor(cast.framework.messages.MessageType.USER_ACTION,
  (userActionRequestData) => {
    // Obtain the media information of the current content to associate the action to.
    let mediaInfo = playerManager.getMediaInformation();

    // If there is no media info return an error and ignore the request.
    if (!mediaInfo) {
        console.error('Not playing media, user action is not supported');
        return new cast.framework.messages.ErrorData(messages.ErrorType.BAD_REQUEST);
    }

    // Reach out to backend services to store user action modifications. See sample below.
    return sendUserAction(userActionRequestData, mediaInfo)

    // Upon response from the backend, update the client's UserActionState.
    .then(backendResponse => updateUserActionStates(backendResponse))

    // If any errors occurred in the backend return them to the cast receiver.
    .catch((error) => {
      console.error(error);
      return error;
    });
});

다음 스니펫은 백엔드 서비스 호출을 시뮬레이션합니다. 이 함수는 UserActionRequestData: 사용자가 요청한 변경 유형 확인 작업이 백엔드에서 지원되는 경우에만 네트워크 호출을 수행합니다.

function sendUserAction(userActionRequestData, mediaInfo) {
  return new Promise((resolve, reject) => {
    switch (userActionRequestData.userAction) {
      // Handle user action changes supported by the backend.
      case cast.framework.messages.UserAction.LIKE:
      case cast.framework.messages.UserAction.DISLIKE:
      case cast.framework.messages.UserAction.FOLLOW:
      case cast.framework.messages.UserAction.UNFOLLOW:
      case cast.framework.messages.UserAction.FLAG:
      case cast.framework.messages.UserAction.SKIP_AD:
        let backendResponse = {userActionRequestData: userActionRequestData, mediaInfo: mediaInfo};
        setTimeout(() => {resolve(backendResponse)}, 1000);
        break;
      // Reject all other user action changes.
      default:
        reject(
          new cast.framework.messages.ErrorData(cast.framework.messages.ErrorType.INVALID_REQUEST));
    }
  });
}

다음 스니펫은 UserActionRequestData를 가져와 MediaInformation에서 UserActionState를 삭제합니다. MediaInformationUserActionState는 요청된 작업과 연결됩니다. 이러한 변경사항은 디스플레이 제어 UI, 리모컨 앱, Android TV UI입니다. 또한 발신 MediaStatus 메시지를 통해 브로드캐스트되어 iOS 및 Android 발신기용 확장 컨트롤러입니다.

function updateUserActionStates(backendResponse) {
  // Unwrap the backend response.
  let mediaInfo = backendResponse.mediaInfo;
  let userActionRequestData = backendResponse.userActionRequestData;

  // If the current item playing has changed, don't update the UserActionState for the current item.
  if (playerManager.getMediaInformation().entity !== mediaInfo.entity) {
    return;
  }

  // Check for existing userActionStates in the MediaInformation.
  // If none, initialize a new array to populate states with.
  let userActionStates = mediaInfo.userActionStates || [];

  // Locate the index of the UserActionState that will be updated in the userActionStates array.
  let index = userActionStates.findIndex((currUserActionState) => {
    return currUserActionState.userAction == userActionRequestData.userAction;
  });

  if (userActionRequestData.clear) {
    // Remove the user action state from the array if cleared.
    if (index >= 0) {
      userActionStates.splice(index, 1);
    }
    else {
      console.warn("Could not find UserActionState to remove in MediaInformation");
    }
  } else {
    // Add the UserActionState to the array if enabled.
    userActionStates.push(
      new cast.framework.messages.UserActionState(userActionRequestData.userAction));
  }

  // Update the UserActionState array and set the new MediaInformation
  mediaInfo.userActionStates = userActionStates;
  playerManager.setMediaInformation(mediaInfo, true);
  return;
}

음성 명령

다음 미디어 명령어는 현재 어시스턴트 지원 기기 이러한 명령어의 기본 구현은 다음과 같습니다. 발견 위치 cast.framework.PlayerManager

명령어 설명
재생 재생 또는 일시중지 상태에서 재생을 다시 시작합니다.
일시중지 현재 재생 중인 콘텐츠를 일시중지합니다.
이전 미디어 대기열에서 이전 미디어 항목으로 건너뜁니다.
다음 미디어 대기열의 다음 미디어 항목으로 건너뜁니다.
중지 현재 재생 중인 미디어를 중지합니다.
반복 안함 현재 재생목록의 마지막 항목 재생이 완료되면 현재 재생목록의 미디어 항목 반복을 사용 중지합니다.
단일 반복 현재 재생 중인 미디어를 무제한 반복합니다.
모두 반복 대기열의 마지막 항목이 재생되면 대기열의 모든 항목을 반복합니다.
모두 반복 및 셔플 대기열의 마지막 항목 재생이 완료되면 대기열을 셔플하고 대기열의 모든 항목을 반복합니다.
셔플 미디어 대기열의 미디어 항목을 셔플합니다.
자막 사용 / 사용 중지 미디어 자막 사용 설정 / 중지 사용 / 사용 중지는 언어별로도 가능합니다.
절대 시간 탐색 지정된 절대 시간으로 건너뜁니다.
현재 시간을 기준으로 시간 상대탐색 현재 재생 시간을 기준으로 지정된 기간만큼 앞뒤로 이동합니다.
다시 플레이하기 현재 재생 중인 미디어를 다시 시작하거나 현재 재생 중인 미디어가 없는 경우 마지막으로 재생한 미디어 항목을 재생합니다.
재생 속도 설정 미디어 재생 속도를 다양하게 합니다. 이 작업은 기본적으로 처리해야 합니다. SET_PLAYBACK_RATE 메시지 인터셉터를 사용하여 수신 속도 요청을 재정의할 수 있습니다.

음성으로 지원되는 미디어 명령

음성 명령으로 어시스턴트에서 미디어 명령을 트리거하지 못하게 하려면 다음 단계를 따르세요. 사용하려면 먼저 지원되는 미디어 명령어 선택할 수 있습니다 그런 다음 다음을 사용 설정하여 명령어를 강제 적용해야 합니다. CastReceiverOptions.enforceSupportedCommands 속성 Cast SDK 발신자 및 터치 지원 기기의 UI가 이러한 구성을 반영합니다. 플래그가 사용 설정되지 않은 경우 수신 음성 실행할 것입니다

예를 들어 발신기 애플리케이션에서 PAUSE를 허용하고 터치 지원 기기의 경우, 이러한 터치 지원 기기를 반영하도록 수신기도 구성해야 합니다. 설정을 변경할 수 있습니다. 설정하면, 설정되지 않은 경우 수신되는 음성 명령이 삭제됩니다. 포함되어 있습니다.

아래 예에서는 시작할 때 CastReceiverOptions를 제공합니다. CastReceiverContext PAUSE 명령어 지원을 추가했으며 플레이어가 해당 명령어만 지원하도록 강제했습니다. 이제 음성 명령이 SEEK와 같은 다른 작업을 요청하면 거부됩니다. 사용자는 명령어가 아직 지원되지 않는다고 알립니다.

const context = cast.framework.CastReceiverContext.getInstance();

context.start({
  enforceSupportedCommands: true,
  supportedCommands: cast.framework.messages.Command.PAUSE
});

제한하려는 각 명령어에 별도의 로직을 적용할 수 있습니다. 삭제 enforceSupportedCommands 플래그 및 구성하려는 각 명령어에 대해 제한하면 수신 메시지를 가로챌 수 있습니다. 여기서 어시스턴트 지원 기기에 SEEK 명령어가 실행되도록 SDK에서 제공합니다. 웹 수신기 애플리케이션에서 탐색을 트리거하지 않습니다.

애플리케이션에서 지원하지 않는 미디어 명령어의 경우 적절한 오류 원인(예: NOT_SUPPORTED

playerManager.setMessageInterceptor(cast.framework.messages.MessageType.SEEK,
  seekData => {
    // Block seeking if the SEEK supported media command is disabled
    if (!(playerManager.getSupportedMediaCommands() & cast.framework.messages.Command.SEEK)) {
      let e = new cast.framework.messages.ErrorData(cast.framework.messages.ErrorType
      .INVALID_REQUEST);
      e.reason = cast.framework.messages.ErrorReason.NOT_SUPPORTED;
      return e;
    }

    return seekData;
  });

음성 활동의 백그라운드

어시스턴트로 인해 Cast 플랫폼에서 애플리케이션의 소리가 재생되는 경우 사용자 음성 듣기나 대답하기와 같은 활동을 FocusState NOT_IN_FOCUS 메시지가 웹 수신기 애플리케이션에 전송되면 시작됩니다. 활동이 종료되면 IN_FOCUS가 포함된 다른 메시지가 전송됩니다. 애플리케이션과 재생 중인 미디어에 따라 FocusStateNOT_IN_FOCUS일 때 메시지를 가로채 미디어를 일시중지합니다. FOCUS_STATE을 입력합니다.

예를 들어 오디오북 재생을 일시중지하는 것은 어시스턴트가 사용자 쿼리에 응답하는 중입니다.

playerManager.setMessageInterceptor(cast.framework.messages.MessageType.FOCUS_STATE,
  focusStateRequestData => {
    // Pause content when the app is out of focus. Resume when focus is restored.
    if (focusStateRequestData.state == cast.framework.messages.FocusState.NOT_IN_FOCUS) {
      playerManager.pause();
    } else {
      playerManager.play();
    }

    return focusStateRequestData;
  });

음성으로 지정된 자막 언어

사용자가 자막 언어를 명시적으로 지정하지 않은 경우 자막에 사용된 언어가 명령어를 말할 때 사용한 언어와 같습니다. 이 시나리오에서는 isSuggestedLanguage 매개변수는 관련 언어가 영향을 받았는지 여부를 명시적으로 요청할 수 있습니다.

예를 들어 "Hey Google,isSuggestedLanguagetrue 자막 켜 줘"라고 말합니다. 그 언어가 학습한 언어에 의해 추론되었고 말씀드렸습니다 'OK' 명령과 같이 언어가 명시적으로 요청된 경우 Google, 영어 자막 켜 줘" isSuggestedLanguagefalse로 설정되어 있습니다.

메타데이터 및 음성 전송

음성 명령은 기본적으로 웹 수신기에 의해 처리되지만 콘텐츠의 메타데이터가 완전하고 정확한지 확인합니다. 이렇게 하면 음성 명령이 어시스턴트에서 올바르게 처리되며 메타데이터가 Google Home 앱과 같은 새로운 유형의 인터페이스에 제대로 표시됩니다. Google Home Hub와 같은 스마트 디스플레이를 활용할 수 있습니다.

스트림 이전

스트림 전송의 기본은 세션 상태 보존입니다. 사용자는 음성 명령, Google Home을 사용하여 기존 오디오 및 동영상 스트림을 여러 기기로 옮길 수 있습니다. 앱 또는 스마트 디스플레이입니다. 미디어는 한 기기 (소스)에서 재생이 중지되고 다른 기기 (소스)에서 계속 재생됩니다. 대상)입니다. 최신 펌웨어가 설치된 모든 Cast 기기는 스트림 이전

스트림 이전의 이벤트 흐름은 다음과 같습니다.

  1. 소스 기기에서 다음을 실행합니다. <ph type="x-smartling-placeholder">
      </ph>
    1. 미디어 재생이 중지됩니다.
    2. 웹 수신기 애플리케이션이 현재 미디어를 저장하는 명령어를 수신합니다. state.
    3. 웹 수신기 애플리케이션이 종료됩니다.
  2. 대상 기기에서 다음을 실행합니다. <ph type="x-smartling-placeholder">
      </ph>
    1. 웹 수신기 애플리케이션이 로드됩니다.
    2. 저장된 미디어를 복원하라는 명령어를 웹 수신기 애플리케이션이 수신함 state.
    3. 미디어 재생이 다시 시작됩니다.

미디어 상태 요소는 다음과 같습니다.

  • 노래, 동영상 또는 미디어 항목의 특정 위치나 타임스탬프
  • 재생목록 또는 아티스트 뮤직 스테이션과 같이 더 넓은 재생목록에 포함됩니다.
  • 인증된 사용자입니다.
  • 재생 상태 (예: 재생 중 또는 일시중지됨)

스트림 전송 사용 설정

웹 수신기의 스트림 전송을 구현하려면 다음 단계를 따르세요.

  1. 업데이트 supportedMediaCommands 다음과 같이 STREAM_TRANSFER 명령어를 사용하세요.
    playerManager.addSupportedMediaCommands(
    cast.framework.messages.Command.STREAM_TRANSFER, true);
  2. 선택적으로 SESSION_STATERESUME_SESSION 메시지를 재정의합니다. 인터셉터에 대한 자세한 내용은 세션 보존'에 설명되어 있습니다. 상태가 될 수 있습니다. 맞춤 데이터가 필요한 경우에만 이를 재정의하세요. 세션 스냅샷의 일부로 저장됩니다 그 외의 경우에는 기본값이 세션 상태 보존을 위한 구현은 스트림 전송을 지원합니다.

세션 상태 보존

웹 수신기 SDK는 웹 수신기 앱의 기본 구현을 제공하여 현재 미디어 상태의 스냅샷을 생성하고, 상태를 로드 요청으로 변환하고 로드 요청으로 세션을 재개할 수 있습니다.

웹 수신기에 의해 생성된 로드 요청은 다음에서 재정의될 수 있습니다. SESSION_STATE 메시지 인터셉터(필요한 경우) 맞춤 데이터를 추가하려는 경우 로드 요청에 넣는 것이 좋습니다. loadRequestData.customData

playerManager.setMessageInterceptor(
    cast.framework.messages.MessageType.SESSION_STATE,
    function (sessionState) {
        // Override sessionState.loadRequestData if needed.
        const newCredentials = updateCredentials_(sessionState.loadRequestData.credentials);
        sessionState.loadRequestData.credentials = newCredentials;

        // Add custom data if needed.
        sessionState.loadRequestData.customData = {
            'membership': 'PREMIUM'
        };

        return sessionState;
    });

커스텀 데이터는 다음에서 가져올 수 있습니다. loadRequestData.customData (RESUME_SESSION 메시지 인터셉터)

let cred_ = null;
let membership_ = null;

playerManager.setMessageInterceptor(
    cast.framework.messages.MessageType.RESUME_SESSION,
    function (resumeSessionRequest) {
        let sessionState = resumeSessionRequest.sessionState;

        // Modify sessionState.loadRequestData if needed.
        cred_ = sessionState.loadRequestData.credentials;

        // Retrieve custom data.
        membership_ = sessionState.loadRequestData.customData.membership;

        return resumeSessionRequest;
    });

콘텐츠 미리 로드

웹 수신기는 현재 재생 후 미디어 항목의 미리 로드를 지원합니다. 있습니다.

미리 로드 작업은 예정된 상품 사양은 preloadTime 값을 QueueItem 객체 (제공되지 않는 경우 기본값은 20초) 시간은 초 단위로 표시되며 현재 재생 중인 항목의 끝을 기준으로 합니다 . 양수 값만 유효한지 확인합니다. 예를 들어 값이 10초이면 이 항목은 초 전의 항목이 끝납니다. 미리 로드 시간이 긴 경우 현재 항목에 남은 시간보다 더 짧은 경우 로드가 완료되자마자 있습니다. 따라서 매우 큰 preload 값이 queueItem에 지정되어 있으면 현재 아이템을 재생할 때마다 같은 효과를 얻을 수 있습니다. 이미 다음 항목을 미리 로드 중입니다. 그러나 기본 아키텍처의 설정과 선택은 개발자에게 전달하세요. 이 값은 대역폭과 스트리밍 성능에 영향을 미칠 수 있기 때문입니다. 반환합니다.

미리 로드는 기본적으로 HLS, DASH, 스무스 스트리밍 콘텐츠에서 작동합니다.

MP3와 같은 일반 MP4 동영상 및 오디오 파일은 Cast로 미리 로드되지 않습니다. 기기는 하나의 미디어 요소만 지원하며 기존 콘텐츠 항목이 계속 재생되고 있습니다.

맞춤 메시지

메시지 교환은 웹 수신기 애플리케이션의 주요 상호작용 방법입니다.

발신자는 플랫폼 (Android, iOS, 웹)을 전송합니다. 이벤트 객체( 메시지의 매니페스트) 이벤트 리스너에 전달되는 데이터 요소 (event.data) 지정할 수 있습니다.

Web Receiver 애플리케이션은 지정된 웹 서버에서 메시지를 수신 대기하도록 네임스페이스입니다. 이렇게 함으로써 웹 수신기 애플리케이션은 해당 네임스페이스 프로토콜을 지원합니다 그런 다음 메시지를 전달하고자 하는 연결된 모든 발신자가 해당 네임스페이스에서 통신하여 적절한 프로토콜을 사용할 수 있습니다.

모든 네임스페이스는 문자열로 정의되며 'urn:x-cast:'(으)로 시작해야 합니다. 임의의 문자열이 뒤에 옵니다. 예를 들어 'urn:x-cast:com.example.cast.mynamespace'.

다음은 웹 수신기가 연결된 발신자:

const context = cast.framework.CastReceiverContext.getInstance();

const CUSTOM_CHANNEL = 'urn:x-cast:com.example.cast.mynamespace';
context.addCustomMessageListener(CUSTOM_CHANNEL, function(customEvent) {
  // handle customEvent.
});

context.start();

마찬가지로 Web Receiver 애플리케이션은 전송자에게 상태를 웹 수신기의 네트워크 트래픽을 수신하게 됩니다. 웹 수신기 애플리케이션은 sendCustomMessage(namespace, senderId, message)CastReceiverContext 웹 수신기는 애플리케이션 상태 변경으로 인해 발생할 수 있습니다. 포인트 투 포인트 이상 (64kb 제한)을 사용하는 경우 Web Receiver는 또한 모든 연결된 발신자의 발신자입니다.

Cast 오디오 기기

오디오 지원은 오디오 기기용 Google Cast 가이드를 참조하세요. 있습니다.

Android TV

이 섹션에서는 Google Web Receiver가 입력을 재생으로 사용하는 방법을 설명합니다. Android TV 호환성입니다.

애플리케이션을 리모컨과 통합

Android TV 기기에서 실행되는 Google Web Receiver는 미디어 재생으로 사용하는 기기의 컨트롤 입력 (예: 휴대용 리모컨) 다음과 같이 urn:x-cast:com.google.cast.media 네임스페이스에 정의된 메시지 미디어 재생 메시지에 설명되어 있습니다. 내 애플리케이션은 애플리케이션 미디어를 제어하려면 이러한 메시지를 지원해야 함 Android TV의 컨트롤에서 기본 재생 컨트롤을 허용하도록 하기 위해 인코더-디코더입니다

Android TV 호환성 가이드라인

다음은 모바일 광고가 제대로 게재되도록 하기 위해 피해야 할 몇 가지 권장사항과 일반적인 함정입니다. 애플리케이션이 Android TV와 호환되는지 여부:

  • user-agent 문자열에는 'Android'와 'CrKey'가 포함됩니다. 일부 사이트는 모바일 전용 사이트로 리디렉션될 수 있습니다. 'Android' 라벨을 지정합니다. 'Android'라고 가정하지 마세요. 사용자 에이전트 문자열에서 항상 는 모바일 사용자를 나타냅니다.
  • Android의 미디어 스택은 데이터를 가져오기 위해 투명한 GZIP을 사용할 수 있습니다. 미디어 데이터는 Accept-Encoding: gzip에 응답할 수 있습니다.
  • Android TV HTML5 미디어 이벤트는 Chromecast에서 숨겨진 문제를 발견할 수도 있습니다.
  • 미디어를 업데이트할 때 <audio>/<video>에 의해 실행된 미디어 관련 이벤트를 사용합니다. 요소(예: timeupdate, pause, waiting) 네트워킹 사용 지양 progress, suspend, stalled 같은 관련 이벤트도 자주 발생합니다. 플랫폼에 따라 다릅니다 미디어 이벤트를 참고하세요. 를 참조하세요.
  • 수신자 사이트의 HTTPS 인증서를 설정할 때 중간 CA 인증서입니다. 자세한 내용은 Qualsys SSL 테스트 페이지를 확인: 사이트의 신뢰할 수 있는 인증 경로에 CA가 포함되어 있는지 확인합니다. 인증서가 '추가 다운로드'로 표시되면 Android 기반 지원합니다
  • Chromecast는 720p 그래픽 영역에 수신기 페이지를 표시하지만 Android TV를 비롯한 전송 플랫폼에서는 페이지를 최대 1080p까지 표시할 수 있습니다. 수신자 페이지는 다양한 해상도에서 매끄럽게 조정됩니다.