Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(2)

Side by Side Diff: media/muxers/webm_muxer.cc

Issue 1863893002: MediaStreamRecorder: Separate video/audio origin of timestamps for WebM muxer (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 4 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « media/muxers/webm_muxer.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2015 The Chromium Authors. All rights reserved. 1 // Copyright 2015 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "media/muxers/webm_muxer.h" 5 #include "media/muxers/webm_muxer.h"
6 6
7 #include "base/bind.h" 7 #include "base/bind.h"
8 #include "media/audio/audio_parameters.h" 8 #include "media/audio/audio_parameters.h"
9 #include "media/base/limits.h" 9 #include "media/base/limits.h"
10 #include "media/base/video_frame.h" 10 #include "media/base/video_frame.h"
(...skipping 99 matching lines...) Expand 10 before | Expand all | Expand 10 after
110 base::TimeTicks timestamp, 110 base::TimeTicks timestamp,
111 bool is_key_frame) { 111 bool is_key_frame) {
112 DVLOG(1) << __FUNCTION__ << " - " << encoded_data->size() << "B"; 112 DVLOG(1) << __FUNCTION__ << " - " << encoded_data->size() << "B";
113 DCHECK(thread_checker_.CalledOnValidThread()); 113 DCHECK(thread_checker_.CalledOnValidThread());
114 114
115 if (!video_track_index_) { 115 if (!video_track_index_) {
116 // |track_index_|, cannot be zero (!), initialize WebmMuxer in that case. 116 // |track_index_|, cannot be zero (!), initialize WebmMuxer in that case.
117 // http://www.matroska.org/technical/specs/index.html#Tracks 117 // http://www.matroska.org/technical/specs/index.html#Tracks
118 AddVideoTrack(video_frame->visible_rect().size(), 118 AddVideoTrack(video_frame->visible_rect().size(),
119 GetFrameRate(video_frame)); 119 GetFrameRate(video_frame));
120 if (first_frame_timestamp_.is_null()) 120 if (first_frame_timestamp_video_.is_null())
121 first_frame_timestamp_ = timestamp; 121 first_frame_timestamp_video_ = timestamp;
122 } 122 }
123 123
124 // TODO(ajose): Support multiple tracks: http://crbug.com/528523 124 // TODO(ajose): Support multiple tracks: http://crbug.com/528523
125 if (has_audio_ && !audio_track_index_) { 125 if (has_audio_ && !audio_track_index_) {
126 DVLOG(1) << __FUNCTION__ << ": delaying until audio track ready."; 126 DVLOG(1) << __FUNCTION__ << ": delaying until audio track ready.";
127 if (is_key_frame) // Upon Key frame reception, empty the encoded queue. 127 if (is_key_frame) // Upon Key frame reception, empty the encoded queue.
128 encoded_frames_queue_.clear(); 128 encoded_frames_queue_.clear();
129 129
130 encoded_frames_queue_.push_back(make_scoped_ptr(new EncodedVideoFrame( 130 encoded_frames_queue_.push_back(make_scoped_ptr(new EncodedVideoFrame(
131 std::move(encoded_data), timestamp, is_key_frame))); 131 std::move(encoded_data), timestamp, is_key_frame)));
132 return; 132 return;
133 } 133 }
134 134
135 // Dump all saved encoded video frames if any. 135 // Dump all saved encoded video frames if any.
136 while (!encoded_frames_queue_.empty()) { 136 while (!encoded_frames_queue_.empty()) {
137 AddFrame(std::move(encoded_frames_queue_.front()->data), video_track_index_, 137 AddFrame(
138 encoded_frames_queue_.front()->timestamp, 138 std::move(encoded_frames_queue_.front()->data), video_track_index_,
139 encoded_frames_queue_.front()->is_keyframe); 139 encoded_frames_queue_.front()->timestamp - first_frame_timestamp_video_,
140 encoded_frames_queue_.front()->is_keyframe);
140 encoded_frames_queue_.pop_front(); 141 encoded_frames_queue_.pop_front();
141 } 142 }
142 143
143 AddFrame(std::move(encoded_data), video_track_index_, timestamp, 144 AddFrame(std::move(encoded_data), video_track_index_,
144 is_key_frame); 145 timestamp - first_frame_timestamp_video_, is_key_frame);
145 } 146 }
146 147
147 void WebmMuxer::OnEncodedAudio(const media::AudioParameters& params, 148 void WebmMuxer::OnEncodedAudio(const media::AudioParameters& params,
148 scoped_ptr<std::string> encoded_data, 149 scoped_ptr<std::string> encoded_data,
149 base::TimeTicks timestamp) { 150 base::TimeTicks timestamp) {
150 DVLOG(2) << __FUNCTION__ << " - " << encoded_data->size() << "B"; 151 DVLOG(2) << __FUNCTION__ << " - " << encoded_data->size() << "B";
151 DCHECK(thread_checker_.CalledOnValidThread()); 152 DCHECK(thread_checker_.CalledOnValidThread());
152 153
153 if (!audio_track_index_) { 154 if (!audio_track_index_) {
154 AddAudioTrack(params); 155 AddAudioTrack(params);
155 if (first_frame_timestamp_.is_null()) 156 if (first_frame_timestamp_audio_.is_null())
156 first_frame_timestamp_ = timestamp; 157 first_frame_timestamp_audio_ = timestamp;
157 } 158 }
158 159
159 // TODO(ajose): Don't drop audio data: http://crbug.com/547948 160 // TODO(ajose): Don't drop audio data: http://crbug.com/547948
160 // TODO(ajose): Support multiple tracks: http://crbug.com/528523 161 // TODO(ajose): Support multiple tracks: http://crbug.com/528523
161 if (has_video_ && !video_track_index_) { 162 if (has_video_ && !video_track_index_) {
162 DVLOG(1) << __FUNCTION__ << ": delaying until video track ready."; 163 DVLOG(1) << __FUNCTION__ << ": delaying until video track ready.";
163 return; 164 return;
164 } 165 }
165 166
166 // Dump all saved encoded video frames if any. 167 // Dump all saved encoded video frames if any.
167 while (!encoded_frames_queue_.empty()) { 168 while (!encoded_frames_queue_.empty()) {
168 AddFrame(std::move(encoded_frames_queue_.front()->data), video_track_index_, 169 AddFrame(
169 encoded_frames_queue_.front()->timestamp, 170 std::move(encoded_frames_queue_.front()->data), video_track_index_,
170 encoded_frames_queue_.front()->is_keyframe); 171 encoded_frames_queue_.front()->timestamp - first_frame_timestamp_video_,
172 encoded_frames_queue_.front()->is_keyframe);
171 encoded_frames_queue_.pop_front(); 173 encoded_frames_queue_.pop_front();
172 } 174 }
173 175
174 AddFrame(std::move(encoded_data), audio_track_index_, timestamp, 176 AddFrame(std::move(encoded_data), audio_track_index_,
177 timestamp - first_frame_timestamp_audio_,
175 true /* is_key_frame -- always true for audio */); 178 true /* is_key_frame -- always true for audio */);
176 } 179 }
177 180
178 void WebmMuxer::Pause() { 181 void WebmMuxer::Pause() {
179 DVLOG(1) << __FUNCTION__; 182 DVLOG(1) << __FUNCTION__;
180 DCHECK(thread_checker_.CalledOnValidThread()); 183 DCHECK(thread_checker_.CalledOnValidThread());
181 if (!elapsed_time_in_pause_) 184 if (!elapsed_time_in_pause_)
182 elapsed_time_in_pause_.reset(new base::ElapsedTimer()); 185 elapsed_time_in_pause_.reset(new base::ElapsedTimer());
183 } 186 }
184 187
(...skipping 88 matching lines...) Expand 10 before | Expand all | Expand 10 after
273 276
274 void WebmMuxer::ElementStartNotify(mkvmuxer::uint64 element_id, 277 void WebmMuxer::ElementStartNotify(mkvmuxer::uint64 element_id,
275 mkvmuxer::int64 position) { 278 mkvmuxer::int64 position) {
276 // This method gets pinged before items are sent to |write_data_callback_|. 279 // This method gets pinged before items are sent to |write_data_callback_|.
277 DCHECK_GE(position, position_.ValueOrDefault(0)) 280 DCHECK_GE(position, position_.ValueOrDefault(0))
278 << "Can't go back in a live WebM stream."; 281 << "Can't go back in a live WebM stream.";
279 } 282 }
280 283
281 void WebmMuxer::AddFrame(scoped_ptr<std::string> encoded_data, 284 void WebmMuxer::AddFrame(scoped_ptr<std::string> encoded_data,
282 uint8_t track_index, 285 uint8_t track_index,
283 base::TimeTicks timestamp, 286 base::TimeDelta timestamp,
284 bool is_key_frame) { 287 bool is_key_frame) {
285 DCHECK(thread_checker_.CalledOnValidThread()); 288 DCHECK(thread_checker_.CalledOnValidThread());
286 DCHECK(!has_video_ || video_track_index_); 289 DCHECK(!has_video_ || video_track_index_);
287 DCHECK(!has_audio_ || audio_track_index_); 290 DCHECK(!has_audio_ || audio_track_index_);
288 291
289 most_recent_timestamp_ = 292 most_recent_timestamp_ =
290 std::max(most_recent_timestamp_, 293 std::max(most_recent_timestamp_, timestamp - total_time_in_pause_);
291 timestamp - total_time_in_pause_ - first_frame_timestamp_);
292 294
293 segment_.AddFrame(reinterpret_cast<const uint8_t*>(encoded_data->data()), 295 segment_.AddFrame(reinterpret_cast<const uint8_t*>(encoded_data->data()),
294 encoded_data->size(), track_index, 296 encoded_data->size(), track_index,
295 most_recent_timestamp_.InMicroseconds() * 297 most_recent_timestamp_.InMicroseconds() *
296 base::Time::kNanosecondsPerMicrosecond, 298 base::Time::kNanosecondsPerMicrosecond,
297 is_key_frame); 299 is_key_frame);
298 } 300 }
299 301
300 WebmMuxer::EncodedVideoFrame::EncodedVideoFrame(scoped_ptr<std::string> data, 302 WebmMuxer::EncodedVideoFrame::EncodedVideoFrame(scoped_ptr<std::string> data,
301 base::TimeTicks timestamp, 303 base::TimeTicks timestamp,
302 bool is_keyframe) 304 bool is_keyframe)
303 : data(std::move(data)), timestamp(timestamp), is_keyframe(is_keyframe) {} 305 : data(std::move(data)), timestamp(timestamp), is_keyframe(is_keyframe) {}
304 306
305 WebmMuxer::EncodedVideoFrame::~EncodedVideoFrame() {} 307 WebmMuxer::EncodedVideoFrame::~EncodedVideoFrame() {}
306 308
307 } // namespace media 309 } // namespace media
OLDNEW
« no previous file with comments | « media/muxers/webm_muxer.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698