00001
00002
00003
00004
00005
00006
00007
00008 #include <cmath>
00009
00010
00011 #include "mythdbcon.h"
00012 #include "mythlogging.h"
00013 #include "diseqcsettings.h"
00014
00015
00016
00017 static GlobalLineEdit *DiSEqCLatitude(void)
00018 {
00019 GlobalLineEdit *gc = new GlobalLineEdit("latitude");
00020 gc->setLabel("Latitude");
00021 gc->setHelpText(
00022 DeviceTree::tr("The Cartesian latitude for your location.") + " " +
00023 DeviceTree::tr("Use negative numbers for southern "
00024 "and western coordinates."));
00025 return gc;
00026 }
00027
00028 static GlobalLineEdit *DiSEqCLongitude(void)
00029 {
00030 GlobalLineEdit *gc = new GlobalLineEdit("longitude");
00031 gc->setLabel("Longitude");
00032 gc->setHelpText(
00033 DeviceTree::tr("The Cartesian longitude for your location.") + " " +
00034 DeviceTree::tr("Use negative numbers for southern "
00035 "and western coordinates."));
00036 return gc;
00037 }
00038
00040
00041 class DeviceTypeSetting : public ComboBoxSetting, public Storage
00042 {
00043 public:
00044 DeviceTypeSetting(DiSEqCDevDevice &device) :
00045 ComboBoxSetting(this), m_device(device)
00046 {
00047 setLabel(DeviceTree::tr("Device Type"));
00048 addSelection(DeviceTree::tr("Switch"),
00049 QString::number((uint) DiSEqCDevDevice::kTypeSwitch));
00050 addSelection(DeviceTree::tr("Rotor"),
00051 QString::number((uint) DiSEqCDevDevice::kTypeRotor));
00052 addSelection(DeviceTree::tr("LNB"),
00053 QString::number((uint) DiSEqCDevDevice::kTypeLNB));
00054 }
00055
00056 virtual void Load(void)
00057 {
00058 QString tmp = QString::number((uint) m_device.GetDeviceType());
00059 setValue(getValueIndex(tmp));
00060 }
00061
00062 virtual void Save(void)
00063 {
00064 m_device.SetDeviceType(
00065 (DiSEqCDevDevice::dvbdev_t) getValue().toUInt());
00066 }
00067
00068 virtual void Save(QString ) { }
00069
00070 private:
00071 DiSEqCDevDevice &m_device;
00072 };
00073
00075
00076 class DeviceDescrSetting : public LineEditSetting, public Storage
00077 {
00078 public:
00079 DeviceDescrSetting(DiSEqCDevDevice &device) :
00080 LineEditSetting(this), m_device(device)
00081 {
00082 setLabel(DeviceTree::tr("Description"));
00083 QString help = DeviceTree::tr(
00084 "Optional descriptive name for this device, to "
00085 "make it easier to configure settings later.");
00086 setHelpText(help);
00087 }
00088
00089 virtual void Load(void)
00090 {
00091 setValue(m_device.GetDescription());
00092 }
00093
00094 virtual void Save(void)
00095 {
00096 m_device.SetDescription(getValue());
00097 }
00098
00099 virtual void Save(QString ) { }
00100
00101 private:
00102 DiSEqCDevDevice &m_device;
00103 };
00104
00105
00107
00108 class DeviceRepeatSetting : public SpinBoxSetting, public Storage
00109 {
00110 public:
00111 DeviceRepeatSetting(DiSEqCDevDevice &device) :
00112 SpinBoxSetting(this, 0, 5, 1), m_device(device)
00113 {
00114 setLabel(DeviceTree::tr("Repeat Count"));
00115 QString help = DeviceTree::tr(
00116 "Number of times to repeat DiSEqC commands sent to this device. "
00117 "Larger values may help with less reliable devices.");
00118 setHelpText(help);
00119 }
00120
00121 virtual void Load(void)
00122 {
00123 setValue(m_device.GetRepeatCount());
00124 }
00125
00126 virtual void Save(void)
00127 {
00128 m_device.SetRepeatCount(getValue().toUInt());
00129 }
00130
00131 virtual void Save(QString ) { }
00132
00133 private:
00134 DiSEqCDevDevice &m_device;
00135 };
00136
00138
00139 class SwitchTypeSetting : public ComboBoxSetting, public Storage
00140 {
00141 public:
00142 SwitchTypeSetting(DiSEqCDevSwitch &switch_dev) :
00143 ComboBoxSetting(this), m_switch(switch_dev)
00144 {
00145 setLabel(DeviceTree::tr("Switch Type"));
00146 setHelpText(DeviceTree::tr("Select the type of switch from the list."));
00147
00148 addSelection(DeviceTree::tr("Tone"),
00149 QString::number((uint) DiSEqCDevSwitch::kTypeTone));
00150 addSelection(DeviceTree::tr("Voltage"),
00151 QString::number((uint) DiSEqCDevSwitch::kTypeVoltage));
00152 addSelection(DeviceTree::tr("Mini DiSEqC"),
00153 QString::number((uint) DiSEqCDevSwitch::kTypeMiniDiSEqC));
00154 addSelection(DeviceTree::tr("DiSEqC"),
00155 QString::number((uint)
00156 DiSEqCDevSwitch::kTypeDiSEqCCommitted));
00157 addSelection(DeviceTree::tr("DiSEqC (Uncommitted)"),
00158 QString::number((uint)
00159 DiSEqCDevSwitch::kTypeDiSEqCUncommitted));
00160 addSelection(DeviceTree::tr("Legacy SW21"),
00161 QString::number((uint) DiSEqCDevSwitch::kTypeLegacySW21));
00162 addSelection(DeviceTree::tr("Legacy SW42"),
00163 QString::number((uint) DiSEqCDevSwitch::kTypeLegacySW42));
00164 addSelection(DeviceTree::tr("Legacy SW64"),
00165 QString::number((uint) DiSEqCDevSwitch::kTypeLegacySW64));
00166 }
00167
00168 virtual void Load(void)
00169 {
00170 setValue(getValueIndex(QString::number((uint) m_switch.GetType())));
00171 }
00172
00173 virtual void Save(void)
00174 {
00175 m_switch.SetType((DiSEqCDevSwitch::dvbdev_switch_t)
00176 getValue().toUInt());
00177 }
00178
00179 virtual void Save(QString ) { }
00180
00181 private:
00182 DiSEqCDevSwitch &m_switch;
00183 };
00184
00186
00187 class SwitchAddressSetting : public LineEditSetting, public Storage
00188 {
00189 public:
00190 SwitchAddressSetting(DiSEqCDevSwitch &switch_dev) :
00191 LineEditSetting(this), m_switch(switch_dev)
00192 {
00193 setLabel(DeviceTree::tr("Address of switch"));
00194 setHelpText(DeviceTree::tr("The DiSEqC address of the switch."));
00195 }
00196
00197 virtual void Load(void)
00198 {
00199 setValue(QString("0x%1").arg(m_switch.GetAddress(), 0, 16));
00200 }
00201
00202 virtual void Save(void)
00203 {
00204 m_switch.SetAddress(getValue().toUInt(0, 16));
00205 }
00206
00207 private:
00208 DiSEqCDevSwitch &m_switch;
00209 };
00210
00212
00213 class SwitchPortsSetting : public LineEditSetting, public Storage
00214 {
00215 public:
00216 SwitchPortsSetting(DiSEqCDevSwitch &switch_dev) :
00217 LineEditSetting(this), m_switch(switch_dev)
00218 {
00219 setLabel(DeviceTree::tr("Number of ports"));
00220 setHelpText(DeviceTree::tr("The number of ports this switch has."));
00221 }
00222
00223 virtual void Load(void)
00224 {
00225 setValue(QString::number(m_switch.GetNumPorts()));
00226 }
00227
00228 virtual void Save(void)
00229 {
00230 m_switch.SetNumPorts(getValue().toUInt());
00231 }
00232
00233 virtual void Save(QString ) { }
00234
00235 private:
00236 DiSEqCDevSwitch &m_switch;
00237 };
00238
00240
00241 SwitchConfig::SwitchConfig(DiSEqCDevSwitch &switch_dev)
00242 {
00243 ConfigurationGroup *group =
00244 new VerticalConfigurationGroup(false, false);
00245 group->setLabel(DeviceTree::tr("Switch Configuration"));
00246
00247 group->addChild(new DeviceDescrSetting(switch_dev));
00248 group->addChild(new DeviceRepeatSetting(switch_dev));
00249 m_type = new SwitchTypeSetting(switch_dev);
00250 group->addChild(m_type);
00251 m_address = new SwitchAddressSetting(switch_dev);
00252 group->addChild(m_address);
00253 m_ports = new SwitchPortsSetting(switch_dev);
00254 group->addChild(m_ports);
00255
00256 connect(m_type, SIGNAL(valueChanged(const QString&)),
00257 this, SLOT( update(void)));
00258
00259 addChild(group);
00260 }
00261
00262 void SwitchConfig::update(void)
00263 {
00264 switch ((DiSEqCDevSwitch::dvbdev_switch_t) m_type->getValue().toUInt())
00265 {
00266 case DiSEqCDevSwitch::kTypeTone:
00267 case DiSEqCDevSwitch::kTypeVoltage:
00268 case DiSEqCDevSwitch::kTypeMiniDiSEqC:
00269 case DiSEqCDevSwitch::kTypeLegacySW21:
00270 case DiSEqCDevSwitch::kTypeLegacySW42:
00271 m_address->setValue(QString("0x10"));
00272 m_address->setEnabled(false);
00273 m_ports->setValue("2");
00274 m_ports->setEnabled(false);
00275 break;
00276 case DiSEqCDevSwitch::kTypeLegacySW64:
00277 m_address->setValue(QString("0x10"));
00278 m_address->setEnabled(false);
00279 m_ports->setValue("3");
00280 m_ports->setEnabled(false);
00281 break;
00282 case DiSEqCDevSwitch::kTypeDiSEqCCommitted:
00283 case DiSEqCDevSwitch::kTypeDiSEqCUncommitted:
00284 m_address->setEnabled(true);
00285 m_ports->setEnabled(true);
00286 break;
00287 }
00288 }
00289
00291
00292 class RotorTypeSetting : public ComboBoxSetting, public Storage
00293 {
00294 public:
00295 RotorTypeSetting(DiSEqCDevRotor &rotor) :
00296 ComboBoxSetting(this), m_rotor(rotor)
00297 {
00298 setLabel(DeviceTree::tr("Rotor Type"));
00299 setHelpText(DeviceTree::tr("Select the type of rotor from the list."));
00300 addSelection(DeviceTree::tr("DiSEqC 1.2"),
00301 QString::number((uint) DiSEqCDevRotor::kTypeDiSEqC_1_2));
00302 addSelection(DeviceTree::tr("DiSEqC 1.3 (GotoX/USALS)"),
00303 QString::number((uint) DiSEqCDevRotor::kTypeDiSEqC_1_3));
00304 }
00305
00306 virtual void Load(void)
00307 {
00308 setValue(getValueIndex(QString::number((uint)m_rotor.GetType())));
00309 }
00310
00311 virtual void Save(void)
00312 {
00313 m_rotor.SetType((DiSEqCDevRotor::dvbdev_rotor_t)getValue().toUInt());
00314 }
00315
00316 virtual void Save(QString ) { }
00317
00318 private:
00319 DiSEqCDevRotor &m_rotor;
00320 };
00321
00323
00324 class RotorLoSpeedSetting : public LineEditSetting, public Storage
00325 {
00326 public:
00327 RotorLoSpeedSetting(DiSEqCDevRotor &rotor) :
00328 LineEditSetting(this), m_rotor(rotor)
00329 {
00330 setLabel(DeviceTree::tr("Rotor Low Speed (deg/sec)"));
00331 QString help = DeviceTree::tr(
00332 "To allow the approximate monitoring of rotor movement, enter "
00333 "the rated angular speed of the rotor when powered at 13V.");
00334 setHelpText(help);
00335 }
00336
00337 virtual void Load(void)
00338 {
00339 setValue(QString::number(m_rotor.GetLoSpeed()));
00340 }
00341
00342 virtual void Save(void)
00343 {
00344 m_rotor.SetLoSpeed(getValue().toDouble());
00345 }
00346
00347 virtual void Save(QString ) { }
00348
00349 private:
00350 DiSEqCDevRotor &m_rotor;
00351 };
00352
00354
00355 class RotorHiSpeedSetting : public LineEditSetting, public Storage
00356 {
00357 public:
00358 RotorHiSpeedSetting(DiSEqCDevRotor &rotor) :
00359 LineEditSetting(this), m_rotor(rotor)
00360 {
00361 setLabel(DeviceTree::tr("Rotor High Speed (deg/sec)"));
00362 QString help = DeviceTree::tr(
00363 "To allow the approximate monitoring of rotor movement, enter "
00364 "the rated angular speed of the rotor when powered at 18V.");
00365 setHelpText(help);
00366 }
00367
00368 virtual void Load(void)
00369 {
00370 setValue(QString::number(m_rotor.GetHiSpeed()));
00371 }
00372
00373 virtual void Save(void)
00374 {
00375 m_rotor.SetHiSpeed(getValue().toDouble());
00376 }
00377
00378 virtual void Save(QString ) { }
00379
00380 private:
00381 DiSEqCDevRotor &m_rotor;
00382 };
00383
00385
00386 static QString AngleToString(double angle)
00387 {
00388 QString str = QString::null;
00389 if (angle >= 0.0)
00390 str = QString::number(angle) +
00391 DeviceTree::tr("E", "Eastern Hemisphere");
00392 else
00393 str = QString::number(-angle) +
00394 DeviceTree::tr("W", "Western Hemisphere");
00395 return str;
00396 }
00397
00398 static double AngleToEdit(double angle, QString &hemi)
00399 {
00400 if (angle > 0.0)
00401 {
00402 hemi = "E";
00403 return angle;
00404 }
00405
00406 hemi = "W";
00407 return -angle;
00408 }
00409
00410 static double AngleToFloat(const QString &angle, bool translated = true)
00411 {
00412 if (angle.length() < 2)
00413 return 0.0;
00414
00415 double pos;
00416 QChar postfix = angle.at(angle.length() - 1);
00417 if (postfix.isLetter())
00418 {
00419 pos = angle.left(angle.length() - 1).toDouble();
00420 if ((translated &&
00421 (postfix.toUpper() ==
00422 DeviceTree::tr("W", "Western Hemisphere")[0])) ||
00423 (!translated && (postfix.toUpper() == 'W')))
00424 {
00425 pos = -pos;
00426 }
00427 }
00428 else
00429 pos = angle.toDouble();
00430
00431 return pos;
00432 }
00433
00434 RotorPosMap::RotorPosMap(DiSEqCDevRotor &rotor) :
00435 ListBoxSetting(this), m_rotor(rotor)
00436 {
00437 connect(this, SIGNAL(editButtonPressed(int)), SLOT(edit(void)));
00438 connect(this, SIGNAL(deleteButtonPressed(int)), SLOT(del(void)));
00439 connect(this, SIGNAL(accepted(int)), SLOT(edit(void)));
00440 }
00441
00442 void RotorPosMap::Load(void)
00443 {
00444 m_posmap = m_rotor.GetPosMap();
00445 PopulateList();
00446 }
00447
00448 void RotorPosMap::Save(void)
00449 {
00450 m_rotor.SetPosMap(m_posmap);
00451 }
00452
00453 void RotorPosMap::edit(void)
00454 {
00455 uint id = getValue().toUInt();
00456
00457 QString angle;
00458 if (MythPopupBox::showGetTextPopup(
00459 GetMythMainWindow(),
00460 DeviceTree::tr("Position Index %1").arg(id),
00461 DeviceTree::tr("Orbital Position"), angle))
00462 {
00463 m_posmap[id] = AngleToFloat(angle);
00464 PopulateList();
00465 }
00466 }
00467
00468 void RotorPosMap::del(void)
00469 {
00470 uint id = getValue().toUInt();
00471 m_posmap.erase(m_posmap.find(id));
00472 PopulateList();
00473 }
00474
00475 void RotorPosMap::PopulateList(void)
00476 {
00477 int old_sel = getValueIndex(getValue());
00478 clearSelections();
00479 uint num_pos = 64;
00480 for (uint pos = 1; pos < num_pos; pos++)
00481 {
00482 uint_to_dbl_t::const_iterator it = m_posmap.find(pos);
00483 QString posval = DeviceTree::tr("None");
00484 if (it != m_posmap.end())
00485 posval = AngleToString(*it);
00486
00487 addSelection(DeviceTree::tr("Position #%1 (%2)").arg(pos).arg(posval),
00488 QString::number(pos));
00489 }
00490 setCurrentItem(old_sel);
00491 }
00492
00494
00495 class RotorPosConfig : public ConfigurationDialog
00496 {
00497 public:
00498 RotorPosConfig(DiSEqCDevRotor &rotor)
00499 {
00500 setLabel(DeviceTree::tr("Rotor Position Map"));
00501 addChild(new RotorPosMap(rotor));
00502 }
00503
00504 virtual DialogCode exec(void)
00505 {
00506 while (ConfigurationDialog::exec() == kDialogCodeAccepted);
00507 return kDialogCodeRejected;
00508 }
00509 };
00510
00512
00513 RotorConfig::RotorConfig(DiSEqCDevRotor &rotor) : m_rotor(rotor)
00514 {
00515 ConfigurationGroup *group =
00516 new VerticalConfigurationGroup(false, false);
00517 group->setLabel(DeviceTree::tr("Rotor Configuration"));
00518
00519 group->addChild(new DeviceDescrSetting(rotor));
00520 group->addChild(new DeviceRepeatSetting(rotor));
00521
00522 ConfigurationGroup *tgroup =
00523 new HorizontalConfigurationGroup(false, false, true, true);
00524
00525 RotorTypeSetting *rtype = new RotorTypeSetting(rotor);
00526 connect(rtype, SIGNAL(valueChanged(const QString&)),
00527 this, SLOT( SetType( const QString&)));
00528 tgroup->addChild(rtype);
00529
00530 m_pos = new TransButtonSetting();
00531 m_pos->setLabel(DeviceTree::tr("Positions"));
00532 m_pos->setHelpText(DeviceTree::tr("Rotor position setup."));
00533 m_pos->setEnabled(rotor.GetType() == DiSEqCDevRotor::kTypeDiSEqC_1_2);
00534 connect(m_pos, SIGNAL(pressed(void)),
00535 this, SLOT( RunRotorPositionsDialog(void)));
00536 tgroup->addChild(m_pos);
00537
00538 group->addChild(tgroup);
00539 group->addChild(new RotorLoSpeedSetting(rotor));
00540 group->addChild(new RotorHiSpeedSetting(rotor));
00541 group->addChild(DiSEqCLatitude());
00542 group->addChild(DiSEqCLongitude());
00543
00544 addChild(group);
00545 }
00546
00547 void RotorConfig::SetType(const QString &type)
00548 {
00549 DiSEqCDevRotor::dvbdev_rotor_t rtype;
00550 rtype = (DiSEqCDevRotor::dvbdev_rotor_t) type.toUInt();
00551 m_pos->setEnabled(rtype == DiSEqCDevRotor::kTypeDiSEqC_1_2);
00552 }
00553
00554 void RotorConfig::RunRotorPositionsDialog(void)
00555 {
00556 RotorPosConfig config(m_rotor);
00557 config.exec();
00558 config.Save();
00559 }
00560
00562
00563 class lnb_preset
00564 {
00565 public:
00566 lnb_preset(const QString &_name, DiSEqCDevLNB::dvbdev_lnb_t _type,
00567 uint _lof_sw = 0, uint _lof_lo = 0,
00568 uint _lof_hi = 0, bool _pol_inv = false) :
00569 name(_name), type(_type),
00570 lof_sw(_lof_sw), lof_lo(_lof_lo),
00571 lof_hi(_lof_hi), pol_inv(_pol_inv) {}
00572
00573 public:
00574 QString name;
00575 DiSEqCDevLNB::dvbdev_lnb_t type;
00576 uint lof_sw;
00577 uint lof_lo;
00578 uint lof_hi;
00579 bool pol_inv;
00580 };
00581
00582 static lnb_preset lnb_presets[] =
00583 {
00584
00585 lnb_preset(DeviceTree::tr("Single (Europe)"),
00586 DiSEqCDevLNB::kTypeVoltageControl, 0, 9750000),
00587 lnb_preset(DeviceTree::tr("Universal (Europe)"),
00588 DiSEqCDevLNB::kTypeVoltageAndToneControl,
00589 11700000, 9750000, 10600000),
00590 lnb_preset(DeviceTree::tr("Circular (N. America)"),
00591 DiSEqCDevLNB::kTypeVoltageControl, 0, 11250000),
00592 lnb_preset(DeviceTree::tr("Linear (N. America)"),
00593 DiSEqCDevLNB::kTypeVoltageControl, 0, 10750000),
00594 lnb_preset(DeviceTree::tr("C Band"),
00595 DiSEqCDevLNB::kTypeVoltageControl, 0, 5150000),
00596 lnb_preset(DeviceTree::tr("DishPro Bandstacked"),
00597 DiSEqCDevLNB::kTypeBandstacked, 0, 11250000, 14350000),
00598 lnb_preset(QString::null, DiSEqCDevLNB::kTypeVoltageControl),
00599 };
00600
00601 static uint FindPreset(const DiSEqCDevLNB &lnb)
00602 {
00603 uint i;
00604 for (i = 0; !lnb_presets[i].name.isEmpty(); i++)
00605 {
00606 if (lnb_presets[i].type == lnb.GetType() &&
00607 lnb_presets[i].lof_sw == lnb.GetLOFSwitch() &&
00608 lnb_presets[i].lof_lo == lnb.GetLOFLow() &&
00609 lnb_presets[i].lof_hi == lnb.GetLOFHigh() &&
00610 lnb_presets[i].pol_inv== lnb.IsPolarityInverted())
00611 {
00612 break;
00613 }
00614 }
00615 return i;
00616 }
00617
00618 class LNBPresetSetting : public ComboBoxSetting, public Storage
00619 {
00620 public:
00621 LNBPresetSetting(DiSEqCDevLNB &lnb) : ComboBoxSetting(this), m_lnb(lnb)
00622 {
00623 setLabel(DeviceTree::tr("LNB Preset"));
00624 QString help = DeviceTree::tr(
00625 "Select the LNB preset from the list, or choose "
00626 "'Custom' and set the advanced settings below.");
00627 setHelpText(help);
00628
00629 uint i = 0;
00630 for (; !lnb_presets[i].name.isEmpty(); i++)
00631 addSelection(lnb_presets[i].name, QString::number(i));
00632 addSelection(DeviceTree::tr("Custom"), QString::number(i));
00633 }
00634
00635 virtual void Load(void)
00636 {
00637 setValue(FindPreset(m_lnb));
00638 }
00639
00640 virtual void Save(void)
00641 {
00642 }
00643
00644 virtual void Save(QString )
00645 {
00646 }
00647
00648 private:
00649 DiSEqCDevLNB &m_lnb;
00650 };
00651
00653
00654 class LNBTypeSetting : public ComboBoxSetting, public Storage
00655 {
00656 public:
00657 LNBTypeSetting(DiSEqCDevLNB &lnb) : ComboBoxSetting(this), m_lnb(lnb)
00658 {
00659 setLabel(DeviceTree::tr("LNB Type"));
00660 setHelpText(DeviceTree::tr("Select the type of LNB from the list."));
00661 addSelection(DeviceTree::tr("Legacy (Fixed)"),
00662 QString::number((uint) DiSEqCDevLNB::kTypeFixed));
00663 addSelection(DeviceTree::tr("Standard (Voltage)"),
00664 QString::number((uint) DiSEqCDevLNB::
00665 kTypeVoltageControl));
00666 addSelection(DeviceTree::tr("Universal (Voltage & Tone)"),
00667 QString::number((uint) DiSEqCDevLNB::
00668 kTypeVoltageAndToneControl));
00669 addSelection(DeviceTree::tr("Bandstacked"),
00670 QString::number((uint) DiSEqCDevLNB::kTypeBandstacked));
00671 }
00672
00673 virtual void Load(void)
00674 {
00675 setValue(getValueIndex(QString::number((uint) m_lnb.GetType())));
00676 }
00677
00678 virtual void Save(void)
00679 {
00680 m_lnb.SetType((DiSEqCDevLNB::dvbdev_lnb_t) getValue().toUInt());
00681 }
00682
00683 virtual void Save(QString ) { }
00684
00685 private:
00686 DiSEqCDevLNB &m_lnb;
00687 };
00688
00690
00691 class LNBLOFSwitchSetting : public LineEditSetting, public Storage
00692 {
00693 public:
00694 LNBLOFSwitchSetting(DiSEqCDevLNB &lnb) : LineEditSetting(this), m_lnb(lnb)
00695 {
00696 setLabel(DeviceTree::tr("LNB LOF Switch (MHz)"));
00697 QString help = DeviceTree::tr(
00698 "This defines at what frequency the LNB will do a "
00699 "switch from high to low setting, and vice versa.");
00700 setHelpText(help);
00701 }
00702
00703 virtual void Load(void)
00704 {
00705 setValue(QString::number(m_lnb.GetLOFSwitch() / 1000));
00706 }
00707
00708 virtual void Save(void)
00709 {
00710 m_lnb.SetLOFSwitch(getValue().toUInt() * 1000);
00711 }
00712
00713 virtual void Save(QString ) { }
00714
00715 private:
00716 DiSEqCDevLNB &m_lnb;
00717 };
00718
00720
00721 class LNBLOFLowSetting : public LineEditSetting, public Storage
00722 {
00723 public:
00724 LNBLOFLowSetting(DiSEqCDevLNB &lnb) : LineEditSetting(this), m_lnb(lnb)
00725 {
00726 setLabel(DeviceTree::tr("LNB LOF Low (MHz)"));
00727 QString help = DeviceTree::tr(
00728 "This defines the offset the frequency coming "
00729 "from the LNB will be in low setting. For bandstacked "
00730 "LNBs this is the vertical/right polarization band.");
00731 setHelpText(help);
00732 }
00733
00734 virtual void Load(void)
00735 {
00736 setValue(QString::number(m_lnb.GetLOFLow() / 1000));
00737 }
00738
00739 virtual void Save(void)
00740 {
00741 m_lnb.SetLOFLow(getValue().toUInt() * 1000);
00742 }
00743
00744 virtual void Save(QString ) { }
00745
00746 private:
00747 DiSEqCDevLNB &m_lnb;
00748 };
00749
00751
00752 class LNBLOFHighSetting : public LineEditSetting, public Storage
00753 {
00754 public:
00755 LNBLOFHighSetting(DiSEqCDevLNB &lnb) : LineEditSetting(this), m_lnb(lnb)
00756 {
00757 setLabel(DeviceTree::tr("LNB LOF High (MHz)"));
00758 QString help = DeviceTree::tr(
00759 "This defines the offset the frequency coming from "
00760 "the LNB will be in high setting. For bandstacked "
00761 "LNBs this is the horizontal/left polarization band.");
00762 setHelpText(help);
00763 }
00764
00765 virtual void Load(void)
00766 {
00767 setValue(QString::number(m_lnb.GetLOFHigh() / 1000));
00768 }
00769
00770 virtual void Save(void)
00771 {
00772 m_lnb.SetLOFHigh(getValue().toUInt() * 1000);
00773 }
00774
00775 virtual void Save(QString ) { }
00776
00777 private:
00778 DiSEqCDevLNB &m_lnb;
00779 };
00780
00781 class LNBPolarityInvertedSetting : public CheckBoxSetting, public Storage
00782 {
00783 public:
00784 LNBPolarityInvertedSetting(DiSEqCDevLNB &lnb) :
00785 CheckBoxSetting(this), m_lnb(lnb)
00786 {
00787 setLabel(DeviceTree::tr("LNB Reversed"));
00788 QString help = DeviceTree::tr(
00789 "This defines whether the signal reaching the LNB "
00790 "is reversed from normal polarization. This happens "
00791 "to circular signals bouncing twice on a toroidal "
00792 "dish.");
00793 setHelpText(help);
00794 }
00795
00796 virtual void Load(void)
00797 {
00798 setValue(m_lnb.IsPolarityInverted());
00799 }
00800
00801 virtual void Save(void)
00802 {
00803 m_lnb.SetPolarityInverted(boolValue());
00804 }
00805
00806 virtual void Save(QString ) { }
00807
00808 private:
00809 DiSEqCDevLNB &m_lnb;
00810 };
00811
00813
00814 LNBConfig::LNBConfig(DiSEqCDevLNB &lnb)
00815 {
00816 ConfigurationGroup *group =
00817 new VerticalConfigurationGroup(false, false);
00818 group->setLabel(DeviceTree::tr("LNB Configuration"));
00819
00820 group->addChild(new DeviceDescrSetting(lnb));
00821 LNBPresetSetting *preset = new LNBPresetSetting(lnb);
00822 group->addChild(preset);
00823 m_type = new LNBTypeSetting(lnb);
00824 group->addChild(m_type);
00825 m_lof_switch = new LNBLOFSwitchSetting(lnb);
00826 group->addChild(m_lof_switch);
00827 m_lof_lo = new LNBLOFLowSetting(lnb);
00828 group->addChild(m_lof_lo);
00829 m_lof_hi = new LNBLOFHighSetting(lnb);
00830 group->addChild(m_lof_hi);
00831 m_pol_inv = new LNBPolarityInvertedSetting(lnb);
00832 group->addChild(m_pol_inv);
00833 connect(m_type, SIGNAL(valueChanged(const QString&)),
00834 this, SLOT( UpdateType( void)));
00835 connect(preset, SIGNAL(valueChanged(const QString&)),
00836 this, SLOT( SetPreset( const QString&)));
00837 addChild(group);
00838 }
00839
00840 void LNBConfig::SetPreset(const QString &value)
00841 {
00842 uint index = value.toUInt();
00843 if (index >= (sizeof(lnb_presets) / sizeof(lnb_preset)))
00844 return;
00845
00846 lnb_preset &preset = lnb_presets[index];
00847 if (preset.name.isEmpty())
00848 {
00849 m_type->setEnabled(true);
00850 UpdateType();
00851 }
00852 else
00853 {
00854 m_type->setValue(m_type->getValueIndex(
00855 QString::number((uint)preset.type)));
00856 m_lof_switch->setValue(QString::number(preset.lof_sw / 1000));
00857 m_lof_lo->setValue(QString::number(preset.lof_lo / 1000));
00858 m_lof_hi->setValue(QString::number(preset.lof_hi / 1000));
00859 m_pol_inv->setValue(preset.pol_inv);
00860 m_type->setEnabled(false);
00861 m_lof_switch->setEnabled(false);
00862 m_lof_hi->setEnabled(false);
00863 m_lof_lo->setEnabled(false);
00864 m_pol_inv->setEnabled(false);
00865 }
00866 }
00867
00868 void LNBConfig::UpdateType(void)
00869 {
00870 if (!m_type->isEnabled())
00871 return;
00872
00873 switch ((DiSEqCDevLNB::dvbdev_lnb_t) m_type->getValue().toUInt())
00874 {
00875 case DiSEqCDevLNB::kTypeFixed:
00876 case DiSEqCDevLNB::kTypeVoltageControl:
00877 m_lof_switch->setEnabled(false);
00878 m_lof_hi->setEnabled(false);
00879 m_lof_lo->setEnabled(true);
00880 m_pol_inv->setEnabled(true);
00881 break;
00882 case DiSEqCDevLNB::kTypeVoltageAndToneControl:
00883 m_lof_switch->setEnabled(true);
00884 m_lof_hi->setEnabled(true);
00885 m_lof_lo->setEnabled(true);
00886 m_pol_inv->setEnabled(true);
00887 break;
00888 case DiSEqCDevLNB::kTypeBandstacked:
00889 m_lof_switch->setEnabled(false);
00890 m_lof_hi->setEnabled(true);
00891 m_lof_lo->setEnabled(true);
00892 m_pol_inv->setEnabled(true);
00893 break;
00894 }
00895 }
00896
00898
00899 DeviceTree::DeviceTree(DiSEqCDevTree &tree) :
00900 ListBoxSetting(this), m_tree(tree)
00901 {
00902 connect(this, SIGNAL(editButtonPressed(int)), SLOT(edit(void)));
00903 connect(this, SIGNAL(deleteButtonPressed(int)), SLOT(del(void)));
00904 connect(this, SIGNAL(accepted(int)), SLOT(edit(void)));
00905 }
00906
00907 void DeviceTree::Load(void)
00908 {
00909 PopulateTree();
00910 }
00911
00912 void DeviceTree::Save(void)
00913 {
00914 }
00915
00916 bool DeviceTree::EditNodeDialog(uint nodeid)
00917 {
00918 DiSEqCDevDevice *dev = m_tree.FindDevice(nodeid);
00919 if (!dev)
00920 {
00921 LOG(VB_GENERAL, LOG_ERR, QString("DeviceTree::EditNodeDialog(%1) "
00922 "-- device not found").arg(nodeid));
00923 return false;
00924 }
00925
00926 bool changed = false;
00927 switch (dev->GetDeviceType())
00928 {
00929 case DiSEqCDevDevice::kTypeSwitch:
00930 {
00931 DiSEqCDevSwitch *sw = dynamic_cast<DiSEqCDevSwitch*>(dev);
00932 if (sw)
00933 {
00934 SwitchConfig config(*sw);
00935 changed = (config.exec() == MythDialog::Accepted);
00936 }
00937 }
00938 break;
00939
00940 case DiSEqCDevDevice::kTypeRotor:
00941 {
00942 DiSEqCDevRotor *rotor = dynamic_cast<DiSEqCDevRotor*>(dev);
00943 if (rotor)
00944 {
00945 RotorConfig config(*rotor);
00946 changed = (config.exec() == MythDialog::Accepted);
00947 }
00948 }
00949 break;
00950
00951 case DiSEqCDevDevice::kTypeLNB:
00952 {
00953 DiSEqCDevLNB *lnb = dynamic_cast<DiSEqCDevLNB*>(dev);
00954 if (lnb)
00955 {
00956 LNBConfig config(*lnb);
00957 changed = (config.exec() == MythDialog::Accepted);
00958 }
00959 }
00960 break;
00961
00962 default:
00963 break;
00964 }
00965
00966 if (changed)
00967 PopulateTree();
00968
00969 return changed;
00970 }
00971
00972 bool DeviceTree::RunTypeDialog(DiSEqCDevDevice::dvbdev_t &type)
00973 {
00974 MythPopupBox *popup = new MythPopupBox(GetMythMainWindow(), "");
00975 popup->addLabel(tr("Select Type of Device"));
00976
00977 MythListBox *list = new MythListBox(popup);
00978 list->insertItem(tr("Switch"));
00979 list->insertItem(tr("Rotor"));
00980 list->insertItem(tr("LNB"));
00981 list->setCurrentRow(0, QItemSelectionModel::Select);
00982
00983 popup->addWidget(list);
00984 connect(list, SIGNAL(accepted(int)),
00985 popup, SLOT( AcceptItem(int)));
00986 list->setFocus();
00987
00988 DialogCode res = popup->ExecPopup();
00989 type = (DiSEqCDevDevice::dvbdev_t)(list->currentRow());
00990
00991 popup->hide();
00992 popup->deleteLater();
00993
00994 return kDialogCodeRejected != res;
00995 }
00996
00997 void DeviceTree::CreateRootNodeDialog(void)
00998 {
00999 DiSEqCDevDevice::dvbdev_t type;
01000 if (!RunTypeDialog(type))
01001 return;
01002
01003 DiSEqCDevDevice *dev = DiSEqCDevDevice::CreateByType(m_tree, type);
01004 if (dev)
01005 {
01006 m_tree.SetRoot(dev);
01007
01008 if (!EditNodeDialog(dev->GetDeviceID()))
01009 m_tree.SetRoot(NULL);
01010
01011 PopulateTree();
01012 }
01013 }
01014
01015 void DeviceTree::CreateNewNodeDialog(uint parentid, uint child_num)
01016 {
01017 DiSEqCDevDevice *parent = m_tree.FindDevice(parentid);
01018 if (!parent)
01019 return;
01020
01021 DiSEqCDevDevice::dvbdev_t type;
01022 if (RunTypeDialog(type))
01023 {
01024 DiSEqCDevDevice *dev = DiSEqCDevDevice::CreateByType(m_tree, type);
01025 if (!dev)
01026 return;
01027
01028 if (parent->SetChild(child_num, dev))
01029 {
01030 if (!EditNodeDialog(dev->GetDeviceID()))
01031 parent->SetChild(child_num, NULL);
01032 PopulateTree();
01033 }
01034 else
01035 {
01036 delete dev;
01037 }
01038 }
01039 }
01040
01041 void DeviceTree::edit(void)
01042 {
01043 QString id = getValue();
01044 if (id.indexOf(':') == -1)
01045 {
01046 EditNodeDialog(id.toUInt());
01047 }
01048 else
01049 {
01050 QStringList vals = id.split(':');
01051 if (vals[0].isEmpty())
01052 CreateRootNodeDialog();
01053 else
01054 CreateNewNodeDialog(vals[0].toUInt(), vals[1].toUInt());
01055 }
01056 setFocus();
01057 }
01058
01059 void DeviceTree::del(void)
01060 {
01061 QString id = getValue();
01062
01063 if (id.indexOf(':') == -1)
01064 {
01065 uint nodeid = id.toUInt();
01066 DiSEqCDevDevice *dev = m_tree.FindDevice(nodeid);
01067 if (dev)
01068 {
01069 DiSEqCDevDevice *parent = dev->GetParent();
01070 if (parent)
01071 parent->SetChild(dev->GetOrdinal(), NULL);
01072 else
01073 m_tree.SetRoot(NULL);
01074
01075 PopulateTree();
01076 }
01077 }
01078
01079 setFocus();
01080 }
01081
01082 void DeviceTree::PopulateTree(void)
01083 {
01084 int old_sel = getValueIndex(getValue());
01085 clearSelections();
01086 PopulateTree(m_tree.Root());
01087 setCurrentItem(old_sel);
01088 }
01089
01090 void DeviceTree::PopulateTree(DiSEqCDevDevice *node,
01091 DiSEqCDevDevice *parent,
01092 uint childnum,
01093 uint depth)
01094 {
01095 QString indent;
01096 indent.fill(' ', 8 * depth);
01097
01098 if (node)
01099 {
01100 QString id = QString::number(node->GetDeviceID());
01101 addSelection(indent + node->GetDescription(), id);
01102 uint num_ch = node->GetChildCount();
01103 for (uint ch = 0; ch < num_ch; ch++)
01104 PopulateTree(node->GetChild(ch), node, ch, depth+1);
01105 }
01106 else
01107 {
01108 QString id;
01109 if (parent)
01110 id = QString::number(parent->GetDeviceID());
01111 id += ":" + QString::number(childnum);
01112
01113 addSelection(indent + "(Unconnected)", id);
01114 }
01115 }
01116
01118
01119 DTVDeviceTreeWizard::DTVDeviceTreeWizard(DiSEqCDevTree &tree)
01120 {
01121 setLabel(DeviceTree::tr("DiSEqC Device Tree"));
01122 addChild(new DeviceTree(tree));
01123 }
01124
01125 DialogCode DTVDeviceTreeWizard::exec(void)
01126 {
01127 while (ConfigurationDialog::exec() == kDialogCodeAccepted);
01128 return kDialogCodeRejected;
01129 }
01130
01132
01133 class SwitchSetting : public ComboBoxSetting, public Storage
01134 {
01135 public:
01136 SwitchSetting(DiSEqCDevDevice &node, DiSEqCDevSettings &settings)
01137 : ComboBoxSetting(this), m_node(node), m_settings(settings)
01138 {
01139 setLabel(node.GetDescription());
01140 setHelpText(DeviceTree::tr("Choose a port to use for this switch."));
01141
01142 uint num_children = node.GetChildCount();
01143 for (uint ch = 0; ch < num_children; ch++)
01144 {
01145 QString val = QString("%1").arg(ch);
01146 QString descr = DeviceTree::tr("Port %1").arg(ch+1);
01147 DiSEqCDevDevice *child = node.GetChild(ch);
01148 if (child)
01149 descr += QString(" (%2)").arg(child->GetDescription());
01150 addSelection(descr, val);
01151 }
01152 }
01153
01154 virtual void Load(void)
01155 {
01156 double value = m_settings.GetValue(m_node.GetDeviceID());
01157 setValue((uint)value);
01158 }
01159
01160 virtual void Save(void)
01161 {
01162 m_settings.SetValue(m_node.GetDeviceID(), getValue().toDouble());
01163 }
01164
01165 virtual void Save(QString ) {}
01166
01167 private:
01168 DiSEqCDevDevice &m_node;
01169 DiSEqCDevSettings &m_settings;
01170 };
01171
01173
01174 class RotorSetting : public ComboBoxSetting, public Storage
01175 {
01176 public:
01177 RotorSetting(DiSEqCDevDevice &node, DiSEqCDevSettings &settings)
01178 : ComboBoxSetting(this), m_node(node), m_settings(settings)
01179 {
01180 setLabel(node.GetDescription());
01181 setHelpText(DeviceTree::tr("Choose a satellite position."));
01182
01183 DiSEqCDevRotor *rotor = dynamic_cast<DiSEqCDevRotor*>(&m_node);
01184 if (rotor)
01185 m_posmap = rotor->GetPosMap();
01186 }
01187
01188 virtual void Load(void)
01189 {
01190 clearSelections();
01191
01192 uint_to_dbl_t::const_iterator it;
01193 for (it = m_posmap.begin(); it != m_posmap.end(); ++it)
01194 addSelection(AngleToString(*it), QString::number(*it));
01195
01196 double angle = m_settings.GetValue(m_node.GetDeviceID());
01197 setValue(getValueIndex(QString::number(angle)));
01198 }
01199
01200 virtual void Save(void)
01201 {
01202 m_settings.SetValue(m_node.GetDeviceID(), getValue().toDouble());
01203 }
01204
01205 virtual void Save(QString ) { }
01206
01207 private:
01208 DiSEqCDevDevice &m_node;
01209 DiSEqCDevSettings &m_settings;
01210 uint_to_dbl_t m_posmap;
01211 };
01212
01214
01215 class USALSRotorSetting : public HorizontalConfigurationGroup
01216 {
01217 public:
01218 USALSRotorSetting(DiSEqCDevDevice &node, DiSEqCDevSettings &settings) :
01219 HorizontalConfigurationGroup(false, false, true, true),
01220 numeric(new TransLineEditSetting()),
01221 hemisphere(new TransComboBoxSetting(false)),
01222 m_node(node), m_settings(settings)
01223 {
01224 QString help =
01225 DeviceTree::tr(
01226 "Locates the satellite you wish to point to "
01227 "with the longitude along the Clarke Belt of "
01228 "the satellite [-180..180] and its hemisphere.");
01229
01230 numeric->setLabel(DeviceTree::tr("Longitude (degrees)"));
01231 numeric->setHelpText(help);
01232 hemisphere->setLabel(DeviceTree::tr("Hemisphere"));
01233 hemisphere->addSelection(DeviceTree::tr("Eastern"), "E", false);
01234 hemisphere->addSelection(DeviceTree::tr("Western"), "W", true);
01235 hemisphere->setHelpText(help);
01236
01237 addChild(numeric);
01238 addChild(hemisphere);
01239 }
01240
01241 virtual void Load(void)
01242 {
01243 double val = m_settings.GetValue(m_node.GetDeviceID());
01244 QString hemi = QString::null;
01245 double eval = AngleToEdit(val, hemi);
01246 numeric->setValue(QString::number(eval));
01247 hemisphere->setValue(hemisphere->getValueIndex(hemi));
01248 }
01249
01250 virtual void Save(void)
01251 {
01252 QString val = QString::number(numeric->getValue().toDouble());
01253 val += hemisphere->getValue();
01254 m_settings.SetValue(m_node.GetDeviceID(), AngleToFloat(val, false));
01255 }
01256
01257 virtual void Save(QString ) { }
01258
01259 private:
01260 TransLineEditSetting *numeric;
01261 TransComboBoxSetting *hemisphere;
01262 DiSEqCDevDevice &m_node;
01263 DiSEqCDevSettings &m_settings;
01264 };
01265
01267
01268 DTVDeviceConfigGroup::DTVDeviceConfigGroup(
01269 DiSEqCDevSettings &settings, uint cardid, bool switches_enabled) :
01270 VerticalConfigurationGroup(false, false, true, true),
01271 m_settings(settings), m_switches_enabled(switches_enabled)
01272 {
01273 setLabel(DeviceTree::tr("DTV Device Configuration"));
01274
01275
01276 m_tree.Load(cardid);
01277
01278
01279 AddNodes(this, QString::null, m_tree.Root());
01280 }
01281
01282 DTVDeviceConfigGroup::~DTVDeviceConfigGroup(void)
01283 {
01284 }
01285
01286 void DTVDeviceConfigGroup::AddNodes(
01287 ConfigurationGroup *group, const QString &trigger, DiSEqCDevDevice *node)
01288 {
01289 if (!node)
01290 return;
01291
01292 Setting *setting = NULL;
01293 switch (node->GetDeviceType())
01294 {
01295 case DiSEqCDevDevice::kTypeSwitch:
01296 setting = new SwitchSetting(*node, m_settings);
01297 setting->setEnabled(m_switches_enabled);
01298 break;
01299 case DiSEqCDevDevice::kTypeRotor:
01300 {
01301 DiSEqCDevRotor *rotor = dynamic_cast<DiSEqCDevRotor*>(node);
01302 if (rotor && (rotor->GetType() == DiSEqCDevRotor::kTypeDiSEqC_1_2))
01303 setting = new RotorSetting(*node, m_settings);
01304 else
01305 setting = new USALSRotorSetting(*node, m_settings);
01306 break;
01307 }
01308 default:
01309 break;
01310 }
01311
01312 if (!setting)
01313 {
01314 AddChild(group, trigger, new TransLabelSetting());
01315 return;
01316 }
01317
01318 m_devs[node->GetDeviceID()] = setting;
01319
01320 uint num_ch = node->GetChildCount();
01321 if (DiSEqCDevDevice::kTypeSwitch == node->GetDeviceType())
01322 {
01323 bool useframe = (node != m_tree.Root());
01324 bool zerospace = !useframe;
01325 TriggeredConfigurationGroup *cgrp = new TriggeredConfigurationGroup(
01326 false, useframe, true, true, false, false, true, zerospace);
01327
01328 cgrp->addChild(setting);
01329 cgrp->setTrigger(setting);
01330
01331 for (uint i = 0; i < num_ch; i++)
01332 AddNodes(cgrp, QString::number(i), node->GetChild(i));
01333
01334 AddChild(group, trigger, cgrp);
01335 return;
01336 }
01337
01338 if (!num_ch)
01339 {
01340 AddChild(group, trigger, setting);
01341 return;
01342 }
01343
01344 VerticalConfigurationGroup *cgrp =
01345 new VerticalConfigurationGroup(false, false, true, true);
01346
01347 AddChild(cgrp, QString::null, setting);
01348 for (uint i = 0; i < num_ch; i++)
01349 AddNodes(cgrp, QString::null, node->GetChild(i));
01350
01351 AddChild(group, trigger, cgrp);
01352 }
01353
01354 void DTVDeviceConfigGroup::AddChild(
01355 ConfigurationGroup *group, const QString &trigger, Setting *setting)
01356 {
01357 TriggeredConfigurationGroup *grp =
01358 dynamic_cast<TriggeredConfigurationGroup*>(group);
01359
01360 if (grp && !trigger.isEmpty())
01361 grp->addTarget(trigger, setting);
01362 else
01363 group->addChild(setting);
01364 }
01365
01367
01368 enum OLD_DISEQC_TYPES
01369 {
01370 DISEQC_SINGLE = 0,
01371 DISEQC_MINI_2 = 1,
01372 DISEQC_SWITCH_2_1_0 = 2,
01373 DISEQC_SWITCH_2_1_1 = 3,
01374 DISEQC_SWITCH_4_1_0 = 4,
01375 DISEQC_SWITCH_4_1_1 = 5,
01376 DISEQC_POSITIONER_1_2 = 6,
01377 DISEQC_POSITIONER_X = 7,
01378 DISEQC_POSITIONER_1_2_SWITCH_2 = 8,
01379 DISEQC_POSITIONER_X_SWITCH_2 = 9,
01380 DISEQC_SW21 = 10,
01381 DISEQC_SW64 = 11,
01382 };
01383
01384
01385 bool convert_diseqc_db(void)
01386 {
01387 MSqlQuery cquery(MSqlQuery::InitCon());
01388 cquery.prepare(
01389 "SELECT cardid, dvb_diseqc_type "
01390 "FROM capturecard"
01391 "WHERE dvb_diseqc_type IS NOT NULL AND "
01392 " diseqcid IS NULL");
01393
01394
01395 if (!cquery.exec())
01396 return false;
01397
01398 MSqlQuery iquery(MSqlQuery::InitCon());
01399 iquery.prepare(
01400 "SELECT cardinputid, diseqc_port, diseqc_pos, "
01401 " lnb_lof_switch, lnb_lof_hi, lnb_lof_lo "
01402 "FROM cardinput "
01403 "WHERE cardinput.cardid = :CARDID");
01404
01405 while (cquery.next())
01406 {
01407 uint cardid = cquery.value(0).toUInt();
01408 OLD_DISEQC_TYPES type = (OLD_DISEQC_TYPES) cquery.value(1).toUInt();
01409
01410 DiSEqCDevTree tree;
01411 DiSEqCDevDevice *root = NULL;
01412 uint add_lnbs = 0;
01413 DiSEqCDevLNB::dvbdev_lnb_t lnb_type =
01414 DiSEqCDevLNB::kTypeVoltageAndToneControl;
01415
01416
01417 switch (type)
01418 {
01419 case DISEQC_SINGLE:
01420 {
01421
01422 root = DiSEqCDevDevice::CreateByType(
01423 tree, DiSEqCDevDevice::kTypeLNB);
01424 break;
01425 }
01426
01427 case DISEQC_MINI_2:
01428 {
01429
01430 root = DiSEqCDevDevice::CreateByType(
01431 tree, DiSEqCDevDevice::kTypeSwitch);
01432 DiSEqCDevSwitch *sw = dynamic_cast<DiSEqCDevSwitch*>(root);
01433 if (sw)
01434 {
01435 sw->SetType(DiSEqCDevSwitch::kTypeTone);
01436 sw->SetNumPorts(2);
01437 add_lnbs = 2;
01438 }
01439 break;
01440 }
01441
01442 case DISEQC_SWITCH_2_1_0:
01443 case DISEQC_SWITCH_2_1_1:
01444 {
01445
01446 root = DiSEqCDevDevice::CreateByType(
01447 tree, DiSEqCDevDevice::kTypeSwitch);
01448 DiSEqCDevSwitch *sw = dynamic_cast<DiSEqCDevSwitch*>(root);
01449 if (sw)
01450 {
01451 sw->SetType(DiSEqCDevSwitch::kTypeDiSEqCCommitted);
01452 sw->SetAddress(0x10);
01453 sw->SetNumPorts(2);
01454 add_lnbs = 2;
01455 }
01456 break;
01457 }
01458
01459 case DISEQC_SWITCH_4_1_0:
01460 case DISEQC_SWITCH_4_1_1:
01461 {
01462
01463 root = DiSEqCDevDevice::CreateByType(
01464 tree, DiSEqCDevDevice::kTypeSwitch);
01465 DiSEqCDevSwitch *sw = dynamic_cast<DiSEqCDevSwitch*>(root);
01466 if (sw)
01467 {
01468 sw->SetType(DiSEqCDevSwitch::kTypeDiSEqCCommitted);
01469 sw->SetAddress(0x10);
01470 sw->SetNumPorts(4);
01471 add_lnbs = 4;
01472 }
01473 break;
01474 }
01475
01476 case DISEQC_POSITIONER_1_2:
01477 {
01478
01479 root = DiSEqCDevDevice::CreateByType(
01480 tree, DiSEqCDevDevice::kTypeRotor);
01481 DiSEqCDevRotor *rotor = dynamic_cast<DiSEqCDevRotor*>(root);
01482 if (rotor)
01483 {
01484 rotor->SetType(DiSEqCDevRotor::kTypeDiSEqC_1_2);
01485 add_lnbs = 1;
01486 }
01487 break;
01488 }
01489
01490 case DISEQC_POSITIONER_X:
01491 {
01492
01493 root = DiSEqCDevDevice::CreateByType(
01494 tree, DiSEqCDevDevice::kTypeRotor);
01495 DiSEqCDevRotor *rotor = dynamic_cast<DiSEqCDevRotor*>(root);
01496 if (rotor)
01497 {
01498 rotor->SetType(DiSEqCDevRotor::kTypeDiSEqC_1_3);
01499 add_lnbs = 1;
01500 }
01501 break;
01502 }
01503
01504 case DISEQC_POSITIONER_1_2_SWITCH_2:
01505 {
01506
01507 root = DiSEqCDevDevice::CreateByType(
01508 tree, DiSEqCDevDevice::kTypeSwitch);
01509 DiSEqCDevSwitch *sw = dynamic_cast<DiSEqCDevSwitch*>(root);
01510 if (sw)
01511 {
01512 sw->SetType(DiSEqCDevSwitch::kTypeDiSEqCUncommitted);
01513 sw->SetNumPorts(10);
01514 add_lnbs = 10;
01515 }
01516 break;
01517 }
01518
01519 case DISEQC_SW21:
01520 {
01521
01522 root = DiSEqCDevDevice::CreateByType(
01523 tree, DiSEqCDevDevice::kTypeSwitch);
01524 DiSEqCDevSwitch *sw = dynamic_cast<DiSEqCDevSwitch*>(root);
01525 if (sw)
01526 {
01527 sw->SetType(DiSEqCDevSwitch::kTypeLegacySW21);
01528 sw->SetNumPorts(2);
01529 add_lnbs = 2;
01530 lnb_type = DiSEqCDevLNB::kTypeFixed;
01531 }
01532 break;
01533 }
01534
01535 case DISEQC_SW64:
01536 {
01537
01538 root = DiSEqCDevDevice::CreateByType(
01539 tree, DiSEqCDevDevice::kTypeSwitch);
01540 DiSEqCDevSwitch *sw = dynamic_cast<DiSEqCDevSwitch*>(root);
01541 if (sw)
01542 {
01543 sw->SetType(DiSEqCDevSwitch::kTypeLegacySW64);
01544 sw->SetNumPorts(3);
01545 add_lnbs = 3;
01546 lnb_type = DiSEqCDevLNB::kTypeFixed;
01547 }
01548 break;
01549 }
01550
01551 default:
01552 {
01553 LOG(VB_GENERAL, LOG_ERR, "Unknown DiSEqC device type " +
01554 QString("%1 ignoring card %2").arg(type).arg(cardid));
01555 break;
01556 }
01557 }
01558
01559 if (!root)
01560 continue;
01561
01562 tree.SetRoot(root);
01563
01564
01565 for (uint i = 0; i < add_lnbs; i++)
01566 {
01567 DiSEqCDevLNB *lnb = dynamic_cast<DiSEqCDevLNB*>
01568 (DiSEqCDevDevice::CreateByType(
01569 tree, DiSEqCDevDevice::kTypeLNB));
01570 if (lnb)
01571 {
01572 lnb->SetType(lnb_type);
01573 lnb->SetDescription(QString("LNB #%1").arg(i+1));
01574 if (!root->SetChild(i, lnb))
01575 delete lnb;
01576 }
01577 }
01578
01579
01580 tree.Store(cardid);
01581
01582
01583 DiSEqCDevSettings set;
01584 iquery.bindValue(":CARDID", cardid);
01585
01586 if (!iquery.exec())
01587 return false;
01588
01589 while (iquery.next())
01590 {
01591 uint inputid = iquery.value(0).toUInt();
01592 uint port = iquery.value(1).toUInt();
01593 double pos = iquery.value(2).toDouble();
01594 DiSEqCDevLNB *lnb = NULL;
01595
01596
01597 switch (type)
01598 {
01599 case DISEQC_SINGLE:
01600 lnb = dynamic_cast<DiSEqCDevLNB*>(root);
01601 break;
01602
01603 case DISEQC_MINI_2:
01604 case DISEQC_SWITCH_2_1_0:
01605 case DISEQC_SWITCH_2_1_1:
01606 case DISEQC_SWITCH_4_1_0:
01607 case DISEQC_SWITCH_4_1_1:
01608 case DISEQC_SW21:
01609 case DISEQC_SW64:
01610 case DISEQC_POSITIONER_1_2_SWITCH_2:
01611 lnb = dynamic_cast<DiSEqCDevLNB*>(root->GetChild(port));
01612 set.SetValue(root->GetDeviceID(), port);
01613 break;
01614
01615 case DISEQC_POSITIONER_1_2:
01616 case DISEQC_POSITIONER_X:
01617 lnb = dynamic_cast<DiSEqCDevLNB*>(root->GetChild(0));
01618 set.SetValue(root->GetDeviceID(), pos);
01619 break;
01620
01621 default:
01622 break;
01623 }
01624
01625
01626 if (lnb)
01627 {
01628 lnb->SetLOFSwitch(iquery.value(3).toUInt());
01629 lnb->SetLOFHigh(iquery.value(4).toUInt());
01630 lnb->SetLOFLow(iquery.value(5).toUInt());
01631 }
01632
01633
01634 set.Store(inputid);
01635 }
01636
01637
01638 tree.Store(cardid);
01639
01640
01641 DiSEqCDev trees;
01642 trees.InvalidateTrees();
01643 }
01644
01645 return true;
01646 }