다음을 통해 공유


프레젠테이션 시계

프레젠테이션 클록 프레젠테이션의 시계 시간을 생성하는 개체입니다. 프레젠테이션 시계에서 보고한 시간을 프레젠테이션 시간이라고 합니다. 프레젠테이션의 모든 스트림은 프레젠테이션 시간과 동기화됩니다. 프레젠테이션 시계는 다음 인터페이스를 노출합니다.

인터페이스 묘사
IMFPresentationClock 프레젠테이션 클록을 사용하기 위한 기본 인터페이스입니다.
IMFRateControl 클록 속도를 제어합니다.
IMFTimer 타이머 콜백을 제공합니다.
IMFShutdown 프레젠테이션 시계를 종료합니다.

 

미디어 싱크는 프레젠테이션 시간을 사용하여 샘플을 렌더링할 시기를 예약합니다. 미디어 싱크가 새 샘플을 받을 때마다 샘플에서 타임스탬프를 가져오고 지정된 시간에 또는 가능한 한 해당 시간에 가까운 시간에 샘플을 렌더링합니다. 토폴로지의 모든 미디어 싱크는 동일한 프레젠테이션 시계를 공유하므로 여러 스트림(예: 오디오 및 비디오)이 동기화됩니다. 미디어 원본 및 변환은 샘플을 배달할 시기를 예약하지 않으므로 프레젠테이션 시계를 사용하지 않습니다. 대신 파이프라인이 새 샘플을 요청할 때마다 샘플을 생성합니다.

재생에 미디어 세션을 사용하는 경우 미디어 세션은 프레젠테이션 시계를 만들고, 시간 원본을 선택하고, 미디어 싱크에 알리는 모든 세부 정보를 처리합니다. 애플리케이션은 재생 중에 프레젠테이션 시계를 사용하여 현재 프레젠테이션 시간을 가져올 수 있지만, 그렇지 않으면 프레젠테이션 시계에서 메서드를 호출하지 않습니다.

클록 시간 및 클록 상태

프레젠테이션 시계에서 최신 시계 시간을 얻으려면 IMFPresentationClock::GetTime호출합니다. 시계 시간은 항상 100나노초 단위이므로 1초는 10,000,000(10^7) 틱입니다. 이는 10MHz의 주파수에 해당합니다.

프레젠테이션 시계에는 실행, 일시 중지 및 중지의 세 가지 상태가 있습니다.

  • 클록을 실행하려면 IMFPresentationClock::Start호출합니다. Start 메서드는 클록의 시작 시간을 지정합니다. 클록이 실행되는 동안 클록 시간은 시작 시간에서 현재 클록 속도로 증가합니다.
  • 시계를 일시 중지하려면 IMFPresentationClock::P ause호출합니다. 클록이 일시 중지된 동안에는 클록 시간이 진행되지 않으며 GetTime 클록이 일시 중지된 시간을 반환합니다.
  • 시계를 중지하려면 IMFPresentationClock::stop호출합니다. 클록이 중지되면 클록 시간이 진행되지 않으며 GetTime 0을 반환합니다.

기본적으로 클록은 1.0의 속도로 진행되며, 이는 100나노초당 1틱을 의미합니다. 클록이 진행되는 속도를 변경하려면 IMFRateControl 인터페이스에 대한 프레젠테이션 시계를 쿼리하고 IMFRateControl::SetRate호출합니다.

개체는 프레젠테이션 시계에서 상태 변경 내용(속도 변경 포함)에 대한 알림을 받을 수 있습니다. 알림을 받으려면 IMFClockStateSink 인터페이스를 구현하고 프레젠테이션 시계에서 IMFPresentationClock::AddClockStateSink 호출합니다. 종료하기 전에 IMFPresentationClock::RemoveClockStateSink 호출하여 개체의 등록을 취소합니다. 미디어 싱크는 이 메커니즘을 사용하여 시계에서 알림을 받습니다.

프레젠테이션 시간

미디어 싱크는 샘플이 올바른 시간에 렌더링되거나 가능한 한 올바른 시간에 가깝게 렌더링되도록 각 샘플을 예약하려고 합니다. 다음 정의가 적용됩니다.

  • 프레젠테이션 시간. 샘플을 렌더링해야 하는 시간입니다. 시간은 100나노초 단위로 제공됩니다.
  • 미디어 시간. 콘텐츠의 시작 시간을 기준으로 합니다. 예를 들어 비디오 파일 길이가 10초인 경우 파일의 중간 지점은 미디어 시간이 5초입니다.
  • 타임스탬프를 사용합니다. 미디어 샘플에 표시된 시간입니다. 타임스탬프를 얻으려면 IMFSample::GetSampleTime호출합니다. 미디어 원본이 샘플을 생성할 때 타임스탬프를 미디어 시간과 동일하게 설정합니다. 미디어 세션은 타임스탬프를 프레젠테이션 시간으로 변환합니다.

기본적으로 미디어 시간과 프레젠테이션 시간은 동일합니다. 예를 들어 비디오 프레임이 원본 파일에 5초씩 나타나는 경우 미디어 시간과 프레젠테이션 시간은 모두 5초입니다. Sequencer Source사용하는 경우 타이밍 모델이 좀 더 복잡하여 세그먼트 간 원활한 전환을 가능하게 합니다. 시퀀서 원본의 타이밍 모델에 대한 자세한 내용은 시퀀스 프레젠테이션 시간참조하세요.

미디어 원본은 항상 타임스탬프를 미디어 시간과 동일하게 설정합니다. 프레젠테이션 시간이 미디어 시간과 일치하지 않으면 미디어 세션에서 미디어 샘플의 타임스탬프를 변환합니다. 싱크가 샘플을 받을 때까지 샘플의 타임스탬프는 프레젠테이션 시간으로 변환됩니다. 싱크는 프레젠테이션 시계의 현재 시간에 대해 샘플을 예약합니다. (빈도 없는 싱크는 프레젠테이션 시계를 무시하므로 예외입니다.)

애플리케이션이 새 위치를 찾으면 미디어 세션에서 지정된 검색 시간에 프레젠테이션 시계를 다시 시작합니다. 예를 들어 애플리케이션이 파일에서 5초 위치를 찾는 경우 미디어 세션은 5초에 시계를 시작합니다. 검색 시간이 키 프레임 경계에 속하지 않는 경우 미디어 원본은 약간 이전 타임스탬프를 사용하여 샘플을 제공할 수 있습니다. 디코더가 모든 프레임을 디코딩할 수 있도록 이 작업이 필요합니다. 미디어 세션은 요청된 검색 시간과 일치하기 위해 미디어 싱크에 도달하기 전에 샘플을 삭제하거나 트리밍합니다. 예를 들어 검색 시간이 5초이면 첫 번째 오디오 샘플이 4.5초에서 시작될 수 있습니다. 미디어 세션은 첫 번째 디코딩된 오디오 샘플에서 처음 0.5초 동안 트리밍됩니다.

프레젠테이션 시계 만들기

프레젠테이션 시계를 만들려면 MFCreatePresentationClock호출합니다. 시계를 종료하려면 IMFShutdown 인터페이스를 쿼리하고 IMFShutdown::Shutdown호출합니다. MFCreatePresentationClock 호출자는 Shutdown; 호출을 담당합니다. 대부분의 경우 애플리케이션이 아닌 미디어 세션입니다.

프레젠테이션 시간 원본

이름에도 불구하고 프레젠테이션 시계는 실제로 클록을 구현하지 않습니다. 대신 프레젠테이션 시간 원본이라고 하는 다른 개체에서 시계 시간을. 시간 원본은 정확한 클록 틱을 생성하고 IMFPresentationTimeSource 인터페이스를 노출하는 모든 개체일 수 있습니다. 다음 그림에서는 이 프로세스를 보여 줍니다.

프레젠테이션 시계와 프레젠테이션 시간 원본 간의 관계를 보여 주는 다이어그램

프레젠테이션 클록이 처음 만들어지면 시간 원본이 없습니다. 시간 원본을 설정하려면 시간 원본의 IMFPresentationTimeSource 인터페이스에 대한 포인터를 사용하여 IMFPresentationClock::SetTimeSource 호출합니다. 시간 원본은 프레젠테이션 시계(실행, 일시 중지 및 중지)와 동일한 상태를 지원하며 IMFClockStateSink 인터페이스를 구현해야 합니다. 프레젠테이션 시계는 이 인터페이스를 사용하여 상태 변경 시기를 시간 원본에 알립니다. 이러한 방식으로 시간 원본은 클록 틱을 제공하지만 프레젠테이션 시계는 클록의 상태 변경을 시작합니다.

일부 미디어 싱크는 정확한 시계에 액세스할 수 있으므로 IMFPresentationTimeSource 인터페이스를 노출합니다. 특히 오디오 렌더러는 사운드 카드의 주파수를 시계로 사용할 수 있습니다. 오디오 재생에서는 오디오 렌더러가 시간 원본으로 작동하여 비디오가 오디오 재생 속도와 동기화되도록 하는 것이 유용합니다. 이는 일반적으로 오디오를 외부 클록과 일치시키려고 시도하는 것보다 더 나은 결과를 생성합니다.

또한 Media Foundation은 시스템 시계에 따라 프레젠테이션 시간 원본을 제공합니다. 이 개체를 만들려면 MFCreateSystemTimeSource호출합니다. 시간 원본을 제공하는 미디어 싱크가 없는 경우 시스템 시간 원본을 사용할 수 있습니다.

일반적으로 미디어 싱크는 프레젠테이션 시계가 사용하는 시간 원본에 관계없이 제공된 프레젠테이션 시계를 사용해야 합니다. 이 규칙은 미디어 싱크가 IMFPresentationTimeSource구현하는 경우에도 적용됩니다. 프레젠테이션 시계에서 다른 시간 원본을 사용하는 경우 미디어 싱크는 자체 내부 시계가 아닌 해당 시간 원본을 따라야 합니다.

미디어 싱크가 프레젠테이션 시계를 따르지 않는 경우 두 가지 상황이 있습니다.

  • 일부 미디어 싱크는 속도 없는 . 미디어 싱크가 속도 없는 경우 프레젠테이션 시계에 따라 예약하지 않고 가능한 한 빨리 샘플을 사용합니다. 일반적으로 속도 없는 싱크는 파일에 데이터를 기록하므로 가능한 한 빨리 작업을 완료하는 것이 좋습니다. 속도 없는 싱크는 IMFMediaSink::GetCharacteristics 메서드에서 MEDIASINK_RATELESS 플래그를 반환합니다. 토폴로지의 모든 싱크가 속도 없는 경우 미디어 세션은 가능한 한 빨리 파이프라인을 통해 데이터를 푸시합니다.

  • 일부 미디어 싱크는 속도와 자체 이외의 시간 원본을 일치시킬 수 없습니다. 이 경우 싱크는 GetCharacteristics 메서드에서 MEDIASINK_CANNOT_MATCH_CLOCK 플래그를 반환합니다. 파이프라인은 여전히 다른 시간 원본을 사용할 수 있지만 결과는 최적보다 작습니다. 싱크가 뒤처지고 재생 중에 결함이 발생할 수 있습니다.

Media Foundation 플랫폼 API