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

Unified Diff: webrtc/modules/audio_conference_mixer/test/audio_conference_mixer_unittest.cc

Issue 1257583011: Adding unittests to AudioConferenceMixer. (Closed) Base URL: https://chromium.googlesource.com/external/webrtc.git@master
Patch Set: Created 5 years, 4 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 side-by-side diff with in-line comments
Download patch
« no previous file with comments | « no previous file | webrtc/modules/modules.gyp » ('j') | webrtc/modules/modules.gyp » ('J')
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: webrtc/modules/audio_conference_mixer/test/audio_conference_mixer_unittest.cc
diff --git a/webrtc/modules/audio_conference_mixer/test/audio_conference_mixer_unittest.cc b/webrtc/modules/audio_conference_mixer/test/audio_conference_mixer_unittest.cc
new file mode 100644
index 0000000000000000000000000000000000000000..13010937b38b6f3d9cd06a53798e77cbd29163de
--- /dev/null
+++ b/webrtc/modules/audio_conference_mixer/test/audio_conference_mixer_unittest.cc
@@ -0,0 +1,166 @@
+/*
+ * Copyright (c) 2015 The WebRTC project authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style license
+ * that can be found in the LICENSE file in the root of the source
+ * tree. An additional intellectual property rights grant can be found
+ * in the file PATENTS. All contributing project authors may
+ * be found in the AUTHORS file in the root of the source tree.
+ */
+
+#include "webrtc/base/scoped_ptr.h"
+#include "webrtc/modules/audio_conference_mixer/interface/audio_conference_mixer.h"
+#include "webrtc/modules/audio_conference_mixer/interface/audio_conference_mixer_defines.h"
+
+#include "testing/gmock/include/gmock/gmock.h"
Andrew MacDonald 2015/08/18 04:03:48 This can go with the other includes.
+
+namespace webrtc {
+
+using testing::_;
+using testing::AtLeast;
+using testing::Invoke;
+using testing::Return;
+
+class MockAudioMixerOutputReceiver : public AudioMixerOutputReceiver {
+ public:
+ MOCK_METHOD4(NewMixedAudio, void(const int32_t id,
+ const AudioFrame& general_audio_frame,
+ const AudioFrame** unique_audio_frames,
+ const uint32_t size));
+};
+
+class MockMixerParticipant : public MixerParticipant {
+ public:
+ MockMixerParticipant() {
+ ON_CALL(*this, GetAudioFrame(_, _))
+ .WillByDefault(Invoke(this, &MockMixerParticipant::FakeAudioFrame));
Andrew MacDonald 2015/08/18 04:03:48 If you always want this behavior, don't mock it, b
minyue-webrtc 2015/08/25 15:36:12 The reason that I mock GetAudioFrame is that I wan
ajm 2015/08/25 16:46:03 Ah OK. You can often define the methods actions di
+ }
+ MOCK_METHOD2(GetAudioFrame,
+ int32_t(const int32_t id, AudioFrame& audio_frame));
+ MOCK_METHOD1(NeededFrequency, int32_t(const int32_t id));
+ AudioFrame fake_frame_;
Andrew MacDonald 2015/08/18 04:03:48 This should be private with a setter.
minyue-webrtc 2015/08/25 15:36:12 Yes, it can be nicer but the it is more complicate
ajm 2015/08/25 16:46:03 The typical way to do this is: AudioFrame* fake_fr
minyue-webrtc 2015/08/31 14:28:39 I like the proposal, changes made accordingly.
+ private:
+ int32_t FakeAudioFrame(const int32_t id, AudioFrame& audio_frame) {
+ audio_frame.CopyFrom(fake_frame_);
+ return 0;
+ }
+};
+
+TEST(AudioConferenceMixer, AnonymousAndUnanonymous) {
Andrew MacDonald 2015/08/18 04:03:48 Nonanonymous is a bit more natural (but also weird
minyue-webrtc 2015/08/25 15:36:12 How about "Named"?
ajm 2015/08/25 16:46:03 Nice.
+ const int kId = 1;
+ // Should not matter even if partipants are more than
+ // kMaximumAmountOfMixedParticipants.
+ const int kUnanonymous =
+ AudioConferenceMixer::kMaximumAmountOfMixedParticipants + 1;
+ const int kAnonymous =
+ AudioConferenceMixer::kMaximumAmountOfMixedParticipants + 1;
+
+ rtc::scoped_ptr<AudioConferenceMixer> mixer;
+ mixer.reset(AudioConferenceMixer::Create(kId));
Andrew MacDonald 2015/08/18 04:03:48 Don't reset, assign directly: rtc::scoped_ptr<Audi
minyue-webrtc 2015/08/25 15:36:12 Done.
+
+ MockMixerParticipant unanonymous[kUnanonymous];
+ MockMixerParticipant anonymous[kAnonymous];
Andrew MacDonald 2015/08/18 04:03:48 Use vectors.
minyue-webrtc 2015/08/25 15:36:12 Done.
+
+ bool ret;
+ for (int i = 0; i < kUnanonymous; i++) {
Andrew MacDonald 2015/08/18 04:03:48 nit: ++i and below
minyue-webrtc 2015/08/25 15:36:12 Done.
+ EXPECT_EQ(0, mixer->SetMixabilityStatus(unanonymous[i], true));
+ EXPECT_EQ(0, mixer->MixabilityStatus(unanonymous[i], ret));
Andrew MacDonald 2015/08/18 04:03:48 Is there any value in testing this with more than
minyue-webrtc 2015/08/25 15:36:12 May be not very needed. But I made the number of "
+ EXPECT_TRUE(ret);
+ }
+
+ for (int i = 0; i < kAnonymous; i++) {
Andrew MacDonald 2015/08/18 04:03:48 Same here, is this loop adding any value? And the
minyue-webrtc 2015/08/25 15:36:12 I made the number of "named" to be larger than kMa
+ // Participant must be registered before turning it into anonymous.
+ EXPECT_EQ(-1, mixer->SetAnonymousMixabilityStatus(anonymous[i], true));
+ EXPECT_EQ(0, mixer->SetMixabilityStatus(anonymous[i], true));
+ EXPECT_EQ(0, mixer->MixabilityStatus(anonymous[i], ret));
+ EXPECT_TRUE(ret);
+ EXPECT_EQ(0, mixer->AnonymousMixabilityStatus(anonymous[i], ret));
+ EXPECT_FALSE(ret);
+
+ EXPECT_EQ(0, mixer->SetAnonymousMixabilityStatus(anonymous[i], true));
+ EXPECT_EQ(0, mixer->AnonymousMixabilityStatus(anonymous[i], ret));
+ EXPECT_TRUE(ret);
+
+ // Anonymous participants do not show status by MixabilityStatus.
+ EXPECT_EQ(0, mixer->MixabilityStatus(anonymous[i], ret));
+ EXPECT_FALSE(ret);
+ }
+
+ for (int i = 0; i < kUnanonymous; i++) {
+ EXPECT_EQ(0, mixer->SetMixabilityStatus(unanonymous[i], false));
+ EXPECT_EQ(0, mixer->MixabilityStatus(unanonymous[i], ret));
+ EXPECT_FALSE(ret);
+ }
+
+ for (int i = 0; i < kAnonymous - 1; i++) {
+ EXPECT_EQ(0, mixer->SetAnonymousMixabilityStatus(anonymous[i], false));
+ EXPECT_EQ(0, mixer->AnonymousMixabilityStatus(anonymous[i], ret));
+ EXPECT_FALSE(ret);
+ // SetAnonymousMixabilityStatus(anonymous, false) moves anonymous to the
+ // unanonymous group.
+ EXPECT_EQ(0, mixer->MixabilityStatus(anonymous[i], ret));
+ EXPECT_TRUE(ret);
+ }
+
+ // SetMixabilityStatus(anonymous, false) will remove anonymous from both
+ // anonymous and unanonymous groups.
+ EXPECT_EQ(0, mixer->SetMixabilityStatus(anonymous[kAnonymous - 1], false));
+ EXPECT_EQ(0, mixer->AnonymousMixabilityStatus(anonymous[kAnonymous - 1],
+ ret));
+ EXPECT_FALSE(ret);
+ EXPECT_EQ(0, mixer->MixabilityStatus(anonymous[kAnonymous - 1], ret));
+ EXPECT_FALSE(ret);
+}
+
+TEST(AudioConferenceMixer, LargestEnergyVadActiveMixed) {
+ const int kId = 1;
+ const int kParticipants =
+ AudioConferenceMixer::kMaximumAmountOfMixedParticipants + 3;
+
+ rtc::scoped_ptr<AudioConferenceMixer> mixer;
+ mixer.reset(AudioConferenceMixer::Create(kId));
Andrew MacDonald 2015/08/18 04:03:48 As above, reset is not needed.
minyue-webrtc 2015/08/25 15:36:12 Done.
+
+ MockAudioMixerOutputReceiver output_receiver;
+ EXPECT_EQ(0, mixer->RegisterMixedStreamCallback(output_receiver));
+
+ MockMixerParticipant participants[kParticipants];
Andrew MacDonald 2015/08/18 04:03:48 vector
minyue-webrtc 2015/08/25 15:36:12 Done.
+
+ for (int i = 0; i < kParticipants; i++) {
+ participants[i].fake_frame_.UpdateFrame(i, 0, nullptr, 320, 32000,
Andrew MacDonald 2015/08/18 04:03:48 This is a rarely used method. Could you just set t
minyue-webrtc 2015/08/25 15:36:12 I searched for its usage, and found that it is not
ajm 2015/08/25 16:46:03 I'd argue that this is _less_ readable since you h
minyue-webrtc 2015/08/31 14:28:39 I'd take your initial suggestion.
+ AudioFrame::kNormalSpeech,
+ AudioFrame::kVadActive, 1, 0);
+ // Use 80 to escape from ramped-in window.
Andrew MacDonald 2015/08/18 04:03:48 Do you mean that you need to choose a late enough
minyue-webrtc 2015/08/25 15:36:12 Done.
+ participants[i].fake_frame_.data_[80] = i;
+
+ EXPECT_EQ(0, mixer->SetMixabilityStatus(participants[i], true));
+ EXPECT_CALL(participants[i], GetAudioFrame(_, _))
+ .Times(AtLeast(1));
+ EXPECT_CALL(participants[i], NeededFrequency(_))
+ .WillRepeatedly(Return(32000));
+ }
+
+ // Last participant gives audio frame with passive VAD, although it has the
+ // largest energy.
+ participants[kParticipants - 1].fake_frame_.vad_activity_ =
+ AudioFrame::kVadPassive;
+
+ EXPECT_CALL(output_receiver, NewMixedAudio(_, _, _, _))
+ .Times(AtLeast(1));
+
+ EXPECT_EQ(0, mixer->Process());
+
+ bool ret;
Andrew MacDonald 2015/08/18 04:03:48 Instead of ret, name this what it is: is_mixed.
minyue-webrtc 2015/08/25 15:36:12 Done.
+ for (int i = 0; i < kParticipants; i++) {
+ EXPECT_EQ(0, participants[i].IsMixed(ret));
+ if (i == kParticipants - 1 || i < kParticipants - 1 -
+ AudioConferenceMixer::kMaximumAmountOfMixedParticipants) {
+ EXPECT_FALSE(ret) << "Mixing status of Participant #" << i << " wrong.";
+ } else {
+ EXPECT_TRUE(ret) << "Mixing status of Participant #" << i << " wrong.";
+ }
+ }
+
+ EXPECT_EQ(0, mixer->UnRegisterMixedStreamCallback());
+}
+
+} // namespace webrtc
« no previous file with comments | « no previous file | webrtc/modules/modules.gyp » ('j') | webrtc/modules/modules.gyp » ('J')

Powered by Google App Engine
This is Rietveld 408576698