00001
00002 #include <QString>
00003 #include <QVariant>
00004
00005
00006 #include <mythcontext.h>
00007 #include <mythdbcon.h>
00008 #include <mythdirs.h>
00009 #include <mythprogressdialog.h>
00010
00011 #include <audiooutpututil.h>
00012
00013 #include "audiogeneralsettings.h"
00014 #include "setupwizard_general.h"
00015 #include "setupwizard_audio.h"
00016 #include "setupwizard_video.h"
00017
00018 AudioSetupWizard::AudioSetupWizard(MythScreenStack *parent,
00019 MythScreenType *previous,
00020 const char *name)
00021 : MythScreenType(parent, name),
00022 m_outputlist(NULL), m_testThread(NULL),
00023 m_generalScreen(previous), m_audioDeviceButtonList(NULL),
00024 m_speakerNumberButtonList(NULL), m_dtsCheck(NULL),
00025 m_ac3Check(NULL), m_eac3Check(NULL),
00026 m_truehdCheck(NULL), m_dtshdCheck(NULL),
00027 m_testSpeakerButton(NULL), m_nextButton(NULL),
00028 m_prevButton(NULL), m_maxspeakers(2),
00029 m_lastAudioDevice("")
00030 {
00031 }
00032
00033 bool AudioSetupWizard::Create()
00034 {
00035 bool foundtheme = false;
00036
00037
00038 foundtheme = LoadWindowFromXML("config-ui.xml", "audiowizard", this);
00039
00040 if (!foundtheme)
00041 return false;
00042
00043 m_audioDeviceButtonList =
00044 dynamic_cast<MythUIButtonList *> (GetChild("audiodevices"));
00045 m_speakerNumberButtonList =
00046 dynamic_cast<MythUIButtonList *> (GetChild("speakers"));
00047
00048 m_dtsCheck = dynamic_cast<MythUICheckBox *> (GetChild("dtscheck"));
00049 m_ac3Check = dynamic_cast<MythUICheckBox *> (GetChild("ac3check"));
00050 m_eac3Check = dynamic_cast<MythUICheckBox *> (GetChild("eac3check"));
00051 m_truehdCheck = dynamic_cast<MythUICheckBox *> (GetChild("truehdcheck"));
00052 m_dtshdCheck = dynamic_cast<MythUICheckBox *> (GetChild("dtshdcheck"));
00053
00054 m_testSpeakerButton =
00055 dynamic_cast<MythUIButton *> (GetChild("testspeakers"));
00056
00057 m_nextButton = dynamic_cast<MythUIButton *> (GetChild("next"));
00058 m_prevButton = dynamic_cast<MythUIButton *> (GetChild("previous"));
00059
00060 if (!m_audioDeviceButtonList || !m_speakerNumberButtonList ||
00061 !m_dtsCheck || !m_ac3Check || !m_eac3Check || !m_truehdCheck ||
00062 !m_dtshdCheck || !m_testSpeakerButton || !m_nextButton || !m_prevButton)
00063 {
00064 LOG(VB_GENERAL, LOG_ERR, "Theme is missing critical theme elements.");
00065 return false;
00066 }
00067
00068
00069
00070
00071 int dtsSetting = gCoreContext->GetNumSetting("DTSPassThru", 0);
00072 if (dtsSetting == 1)
00073 m_dtsCheck->SetCheckState(MythUIStateType::Full);
00074
00075 int ac3Setting = gCoreContext->GetNumSetting("AC3PassThru", 0);
00076 if (ac3Setting == 1)
00077 m_ac3Check->SetCheckState(MythUIStateType::Full);
00078
00079 int eac3Setting = gCoreContext->GetNumSetting("EAC3PassThru", 0);
00080 if (eac3Setting == 1)
00081 m_eac3Check->SetCheckState(MythUIStateType::Full);
00082
00083 int truehdSetting = gCoreContext->GetNumSetting("TrueHDPassThru", 0);
00084 if (truehdSetting == 1)
00085 m_truehdCheck->SetCheckState(MythUIStateType::Full);
00086
00087 int dtshdSetting = gCoreContext->GetNumSetting("DTSHDPassThru", 0);
00088 if (dtshdSetting == 1)
00089 m_dtshdCheck->SetCheckState(MythUIStateType::Full);
00090
00091
00092
00093
00094 m_audioDeviceButtonList->SetHelpText( tr("Select from one of the "
00095 "audio devices detected on your system. When "
00096 "satisfied, you can test audio before moving "
00097 "on. If you fail to configure audio, video "
00098 "playback may fail as well.") );
00099 m_speakerNumberButtonList->SetHelpText( tr("Select the number of speakers you "
00100 "have.") );
00101
00102
00103 m_dtsCheck->SetHelpText( tr("Select this checkbox if your receiver "
00104 "is capable of playing DTS.") );
00105 m_ac3Check->SetHelpText( tr("Select this checkbox if your receiver "
00106 "is capable of playing AC-3 (Dolby Digital).") );
00107 m_eac3Check->SetHelpText( tr("Select this checkbox if your receiver "
00108 "is capable of playing E-AC-3 (Dolby Digital Plus).") );
00109 m_truehdCheck->SetHelpText( tr("Select this checkbox if your receiver "
00110 "is capable of playing TrueHD.") );
00111 m_dtshdCheck->SetHelpText( tr("Select this checkbox if your receiver "
00112 "is capable of playing DTS-HD.") );
00113
00114
00115 m_testSpeakerButton->SetHelpText( tr("Test your audio settings by playing "
00116 "noise through each speaker.") );
00117 m_nextButton->SetHelpText( tr("Save these changes and move on to the next "
00118 "configuration step.") );
00119 m_prevButton->SetHelpText( tr("Return to the previous configuration step.") );
00120
00121
00122 m_testSpeakerButton->SetText(tr("Test Speakers"));
00123
00124 connect(m_testSpeakerButton, SIGNAL(Clicked()), this, SLOT(toggleSpeakers()));
00125 connect(m_nextButton, SIGNAL(Clicked()), this, SLOT(slotNext()));
00126 connect(m_prevButton, SIGNAL(Clicked()), this, SLOT(slotPrevious()));
00127
00128 QString message = tr("Discovering audio devices...");
00129 LoadInBackground(message);
00130
00131 BuildFocusList();
00132
00133 return true;
00134 }
00135
00136 AudioSetupWizard::~AudioSetupWizard()
00137 {
00138 if (m_testThread)
00139 {
00140 m_testThread->cancel();
00141 m_testThread->wait();
00142 delete m_testThread;
00143 }
00144 if (m_outputlist)
00145 {
00146 delete m_outputlist;
00147 }
00148 }
00149
00150 void AudioSetupWizard::Load(void)
00151 {
00152 m_outputlist = AudioOutput::GetOutputList();
00153 }
00154
00155 void AudioSetupWizard::Init(void)
00156 {
00157 QString current = gCoreContext->GetSetting(QString("AudioOutputDevice"));
00158 bool found = false;
00159
00160 if (!current.isEmpty())
00161 {
00162 for (AudioOutput::ADCVect::const_iterator it = m_outputlist->begin();
00163 it != m_outputlist->end(); ++it)
00164 {
00165 if (it->name == current)
00166 {
00167 found = true;
00168 break;
00169 }
00170 }
00171 if (!found)
00172 {
00173 AudioOutput::AudioDeviceConfig *adc =
00174 AudioOutput::GetAudioDeviceConfig(current, current, true);
00175 if (adc->settings.IsInvalid())
00176 {
00177 LOG(VB_GENERAL, LOG_ERR, QString("Audio device %1 isn't usable")
00178 .arg(current));
00179 }
00180 else
00181 {
00182
00183 m_outputlist->insert(0, *adc);
00184 }
00185 delete adc;
00186 }
00187 }
00188 for (AudioOutput::ADCVect::const_iterator it = m_outputlist->begin();
00189 it != m_outputlist->end(); ++it)
00190 {
00191 QString name = it->name;
00192 MythUIButtonListItem *output =
00193 new MythUIButtonListItem(m_audioDeviceButtonList, name);
00194 output->SetData(name);
00195 }
00196 if (found)
00197 {
00198 m_audioDeviceButtonList->SetValueByData(qVariantFromValue(current));
00199 }
00200
00201 m_maxspeakers = gCoreContext->GetNumSetting("MaxChannels", 2);
00202 m_lastAudioDevice = m_audioDeviceButtonList->GetItemCurrent()->GetText();
00203
00204
00205 UpdateCapabilities();
00206
00207 connect(m_ac3Check,
00208 SIGNAL(valueChanged()), SLOT(UpdateCapabilitiesAC3()));
00209 connect(m_audioDeviceButtonList,
00210 SIGNAL(itemSelected(MythUIButtonListItem*)),
00211 SLOT(UpdateCapabilities(MythUIButtonListItem*)));
00212 }
00213
00214 AudioOutputSettings AudioSetupWizard::UpdateCapabilities(bool restore, bool AC3)
00215 {
00216 QString out = m_audioDeviceButtonList->GetItemCurrent()->GetText();
00217 int max_speakers = 8;
00218 int realmax_speakers = 8;
00219
00220 AudioOutputSettings settings;
00221
00222 for (AudioOutput::ADCVect::const_iterator it = m_outputlist->begin();
00223 it != m_outputlist->end(); ++it)
00224 {
00225 if (it->name == out)
00226 {
00227 settings = it->settings;
00228 break;
00229 }
00230 }
00231
00232 realmax_speakers = max_speakers = settings.BestSupportedChannels();
00233
00234 bool bAC3 = settings.canFeature(FEATURE_AC3);
00235 bool bDTS = settings.canFeature(FEATURE_DTS);
00236 bool bLPCM = settings.canFeature(FEATURE_LPCM);
00237 bool bEAC3 = settings.canFeature(FEATURE_EAC3);
00238 bool bTRUEHD = settings.canFeature(FEATURE_TRUEHD);
00239 bool bDTSHD = settings.canFeature(FEATURE_DTSHD);
00240
00241 bAC3 ? m_ac3Check->Show() : m_ac3Check->Hide();
00242 bDTS ? m_dtsCheck->Show() : m_dtsCheck->Hide();
00243 bEAC3 ? m_eac3Check->Show() : m_eac3Check->Hide();
00244 bTRUEHD ? m_truehdCheck->Show() : m_truehdCheck->Hide();
00245 bDTSHD ? m_dtshdCheck->Show() : m_dtshdCheck->Hide();
00246
00247 bAC3 &= (m_ac3Check->GetCheckState() == MythUIStateType::Full);
00248 bDTS &= (m_dtsCheck->GetCheckState() == MythUIStateType::Full);
00249
00250 if (max_speakers > 2 && !bLPCM)
00251 max_speakers = 2;
00252 if (max_speakers == 2 && bAC3)
00253 {
00254 max_speakers = 6;
00255 if (AC3)
00256 {
00257 restore = true;
00258 }
00259 }
00260
00261 int cur_speakers = m_maxspeakers;
00262
00263 if (m_speakerNumberButtonList->GetItemCurrent() != NULL)
00264 {
00265 cur_speakers = qVariantValue<int>
00266 (m_speakerNumberButtonList->GetItemCurrent()->GetData());
00267 }
00268 if (cur_speakers > m_maxspeakers)
00269 {
00270 m_maxspeakers = cur_speakers;
00271 }
00272 if (restore)
00273 {
00274 cur_speakers = m_maxspeakers;
00275 }
00276
00277 if (cur_speakers > max_speakers)
00278 {
00279 LOG(VB_AUDIO, LOG_INFO, QString("Reset device %1").arg(out));
00280 cur_speakers = max_speakers;
00281 }
00282
00283
00284 m_speakerNumberButtonList->Reset();
00285 for (int i = 1; i <= max_speakers; i++)
00286 {
00287 if (settings.IsSupportedChannels(i))
00288 {
00289 switch (i)
00290 {
00291 case 2:
00292 {
00293 MythUIButtonListItem *stereo =
00294 new MythUIButtonListItem(m_speakerNumberButtonList,
00295 QObject::tr("Stereo"));
00296 stereo->SetData(2);
00297 break;
00298 }
00299 case 6:
00300 {
00301 MythUIButtonListItem *sixchan =
00302 new MythUIButtonListItem(m_speakerNumberButtonList,
00303 QObject::tr("5.1 Channel Audio"));
00304 sixchan->SetData(6);
00305 break;
00306 }
00307 case 8:
00308 {
00309 MythUIButtonListItem *eightchan =
00310 new MythUIButtonListItem(m_speakerNumberButtonList,
00311 QObject::tr("7.1 Channel Audio"));
00312 eightchan->SetData(8);
00313 break;
00314 }
00315 default:
00316 continue;
00317 }
00318 }
00319 }
00320 m_speakerNumberButtonList->SetValueByData(qVariantFromValue(cur_speakers));
00321
00322
00323
00324
00325 settings.SetBestSupportedChannels(cur_speakers);
00326 settings.setFeature(bAC3, FEATURE_AC3);
00327 settings.setFeature(bLPCM && realmax_speakers > 2, FEATURE_LPCM);
00328
00329 return settings;
00330 }
00331
00332 AudioOutputSettings AudioSetupWizard::UpdateCapabilities(
00333 MythUIButtonListItem* item)
00334 {
00335 bool restore = false;
00336 if (item)
00337 {
00338 restore = item->GetText() != m_lastAudioDevice;
00339 m_lastAudioDevice = item->GetText();
00340 }
00341 return UpdateCapabilities(restore);
00342 }
00343
00344 AudioOutputSettings AudioSetupWizard::UpdateCapabilitiesAC3(void)
00345 {
00346 return UpdateCapabilities(false, true);
00347 }
00348
00349 void AudioSetupWizard::slotNext(void)
00350 {
00351 if (m_testThread)
00352 {
00353 toggleSpeakers();
00354 }
00355
00356 save();
00357
00358 MythScreenStack *mainStack = GetMythMainWindow()->GetMainStack();
00359 VideoSetupWizard *sw = new VideoSetupWizard(mainStack, m_generalScreen,
00360 this, "videosetupwizard");
00361
00362 if (sw->Create())
00363 {
00364 mainStack->AddScreen(sw);
00365 }
00366 else
00367 delete sw;
00368 }
00369
00370 void AudioSetupWizard::save(void)
00371 {
00372
00373 gCoreContext->SaveSetting("StereoPCM", false);
00374 gCoreContext->SaveSetting("Audio48kOverride", false);
00375 gCoreContext->SaveSetting("HBRPassthru", true);
00376 gCoreContext->SaveSetting("PassThruDeviceOverride", false);
00377 gCoreContext->SaveSetting("PassThruOutputDevice", QString::null);
00378
00379 int channels = qVariantValue<int>
00380 (m_speakerNumberButtonList->GetItemCurrent()->GetData());
00381 gCoreContext->SaveSetting("MaxChannels", channels);
00382
00383 QString device =
00384 m_audioDeviceButtonList->GetItemCurrent()->GetText();
00385 gCoreContext->SaveSetting("AudioOutputDevice", device);
00386
00387 bool ac3State = (m_ac3Check->GetCheckState() == MythUIStateType::Full);
00388 gCoreContext->SaveSetting("AC3PassThru", ac3State);
00389
00390 bool dtsState = (m_dtsCheck->GetCheckState() == MythUIStateType::Full);
00391 gCoreContext->SaveSetting("DTSPassThru", dtsState);
00392
00393 bool eac3State = (m_eac3Check->GetCheckState() == MythUIStateType::Full);
00394 gCoreContext->SaveSetting("EAC3PassThru", eac3State);
00395
00396 bool truehdState = (m_truehdCheck->GetCheckState() == MythUIStateType::Full);
00397 gCoreContext->SaveSetting("TrueHDPassThru", truehdState);
00398
00399 bool dtshdState = (m_dtshdCheck->GetCheckState() == MythUIStateType::Full);
00400 gCoreContext->SaveSetting("DTSHDPassThru", dtshdState);
00401 }
00402
00403 void AudioSetupWizard::slotPrevious(void)
00404 {
00405 Close();
00406 }
00407
00408 bool AudioSetupWizard::keyPressEvent(QKeyEvent *event)
00409 {
00410 if (GetFocusWidget()->keyPressEvent(event))
00411 return true;
00412
00413 bool handled = false;
00414
00415 if (!handled && MythScreenType::keyPressEvent(event))
00416 handled = true;
00417
00418 return handled;
00419 }
00420
00421 void AudioSetupWizard::toggleSpeakers(void)
00422 {
00423 if (m_testThread)
00424 {
00425 m_testThread->cancel();
00426 m_testThread->wait();
00427 delete m_testThread;
00428 m_testThread = NULL;
00429 m_testSpeakerButton->SetText(tr("Test Speakers"));
00430 return;
00431 }
00432
00433 AudioOutputSettings settings = UpdateCapabilities(false);
00434 QString out = m_audioDeviceButtonList->GetItemCurrent()->GetText();
00435 int channels =
00436 qVariantValue<int> (m_speakerNumberButtonList->GetItemCurrent()->GetData());
00437
00438 m_testThread =
00439 new AudioTestThread(this, out, out, channels, settings, false);
00440 if (!m_testThread->result().isEmpty())
00441 {
00442 QString msg = QObject::tr("Audio device is invalid or not useable.");
00443 MythPopupBox::showOkPopup(
00444 GetMythMainWindow(), QObject::tr("Warning"), msg);
00445 delete m_testThread;
00446 m_testThread = NULL;
00447 }
00448 else
00449 {
00450 m_testThread->start();
00451 m_testSpeakerButton->SetText(tr("Stop Speaker Test"));
00452 }
00453 }