00001
00008 #include "backendselect.h"
00009 #include "mythdialogs.h"
00010 #include "mythconfigdialogs.h"
00011
00012 #include "libmythupnp/mythxmlclient.h"
00013
00014
00015 BackendSelect::BackendSelect(MythMainWindow *parent, DatabaseParams *params)
00016 : MythDialog(parent, "BackEnd Selection", TRUE)
00017 {
00018 m_parent = parent;
00019 m_DBparams = params;
00020
00021 CreateUI();
00022
00023 UPnp::PerformSearch(gBackendURI);
00024 UPnp::AddListener(this);
00025
00026 FillListBox();
00027
00028 m_backends->setFocus();
00029 }
00030
00031 BackendSelect::~BackendSelect()
00032 {
00033 UPnp::RemoveListener(this);
00034
00035 ItemMap::iterator it;
00036 for (it = m_devices.begin(); it != m_devices.end(); ++it)
00037 {
00038 ListBoxDevice *item = it.data();
00039
00040 if (item != NULL)
00041 delete item;
00042 }
00043
00044 m_devices.clear();
00045 }
00046
00047 void BackendSelect::Accept(void)
00048 {
00049 DeviceLocation *dev;
00050 QListBoxItem *selected = m_backends->selectedItem();
00051
00052 if (!selected)
00053 return;
00054
00055 dev = ((ListBoxDevice *)selected)->m_dev;
00056
00057 if (!dev)
00058 reject();
00059
00060 dev->AddRef();
00061 if (Connect(dev))
00062 accept();
00063 }
00064
00065 void BackendSelect::AddItem(DeviceLocation *dev)
00066 {
00067 if (!dev)
00068 return;
00069
00070 QString USN = dev->m_sUSN;
00071
00072
00073 if (m_devices.find(USN) == m_devices.end())
00074 {
00075 ListBoxDevice *item;
00076 QString name;
00077
00078 if (print_verbose_messages & VB_UPNP)
00079 name = dev->GetNameAndDetails(true);
00080 else
00081 name = dev->GetFriendlyName(true);
00082
00083 item = new ListBoxDevice(m_backends, name, dev);
00084 m_devices.insert(USN, item);
00085
00086
00087 if (m_backends->numRows() == 1)
00088 m_backends->setSelected(0, true);
00089 }
00090
00091 dev->Release();
00092 }
00093
00098 bool BackendSelect::Connect(DeviceLocation *dev)
00099 {
00100 QString error;
00101 QString message;
00102 UPnPResultCode stat;
00103 MythXMLClient *xml;
00104
00105 m_USN = dev->m_sUSN;
00106 xml = new MythXMLClient(dev->m_sLocation);
00107 stat = xml->GetConnectionInfo(m_PIN, m_DBparams, message);
00108 error = dev->GetFriendlyName(true);
00109 if (error == "<Unknown>")
00110 error = dev->m_sLocation;
00111 error += ". " + message;
00112 dev->Release();
00113
00114 switch (stat)
00115 {
00116 case UPnPResult_Success:
00117 VERBOSE(VB_UPNP, "Connect() - success. New hostname: "
00118 + m_DBparams->dbHostName);
00119 return true;
00120
00121 case UPnPResult_HumanInterventionRequired:
00122 VERBOSE(VB_UPNP, error);
00123 MythPopupBox::showOkPopup(m_parent, "", tr(message));
00124 break;
00125
00126 case UPnPResult_ActionNotAuthorized:
00127 VERBOSE(VB_UPNP, "Access denied for " + error + ". Wrong PIN?");
00128 message = "Please enter the backend access PIN";
00129 do
00130 {
00131 m_PIN = MythPopupBox::showPasswordPopup(
00132 m_parent, "Backend PIN entry", tr(message));
00133 stat = xml->GetConnectionInfo(m_PIN, m_DBparams, message);
00134 }
00135 while (stat == UPnPResult_ActionNotAuthorized);
00136 if (stat == UPnPResult_Success)
00137 return true;
00138
00139 default:
00140 VERBOSE(VB_UPNP, "GetConnectionInfo() failed for " + error);
00141 MythPopupBox::showOkPopup(m_parent, "", tr(message));
00142 }
00143
00144
00145 m_backends->setFocus();
00146 return false;
00147 }
00148
00149 void BackendSelect::CreateUI(void)
00150 {
00151
00152 QLabel *label;
00153 QGridLayout *layout;
00154 MythPushButton *cancel;
00155 MythPushButton *manual;
00156 MythPushButton *OK;
00157
00158
00159
00160 label = new QLabel(tr("Please select default Myth Backend Server"), this);
00161 label->setBackgroundOrigin(QWidget::WindowOrigin);
00162
00163 m_backends = new MythListBox(this);
00164 OK = new MythPushButton(tr("OK"), this);
00165 cancel = new MythPushButton(tr("Cancel"), this);
00166 manual = new MythPushButton(tr("Configure Manually"), this);
00167
00168
00169
00170 layout = new QGridLayout(this, 5, 5, 40);
00171 layout->addMultiCellWidget(label, 0, 0, 1, 3);
00172 layout->addMultiCellWidget(m_backends, 1, 1, 0, 4);
00173
00174 layout->addMultiCellWidget(manual, 4, 4, 0, 1);
00175
00176
00177 layout->addWidget(cancel, 4, 3);
00178 layout->addWidget(OK , 4, 4);
00179
00180
00181 connect(m_backends, SIGNAL(accepted(int)), SLOT(Accept()));
00182
00183 connect(manual, SIGNAL(clicked()), SLOT(Manual()));
00184 connect(cancel, SIGNAL(clicked()), SLOT(reject()));
00185 connect(OK, SIGNAL(clicked()), SLOT(Accept()));
00186 }
00187
00188 void BackendSelect::customEvent(QCustomEvent *e)
00189 {
00190 if (MythEvent::MythEventMessage != ((MythEvent::Type)(e->type())))
00191 return;
00192
00193
00194 MythEvent *me = (MythEvent *)e;
00195 QString message = me->Message();
00196 QString URI = me->ExtraData(0);
00197 QString URN = me->ExtraData(1);
00198 QString URL = me->ExtraData(2);
00199
00200
00201 VERBOSE(VB_UPNP, "BackendSelect::customEvent(" + message
00202 + ", " + URI + ", " + URN + ", " + URL + ")");
00203
00204 if (message.startsWith("SSDP_ADD") &&
00205 URI.startsWith("urn:schemas-mythtv-org:device:MasterMediaServer:"))
00206 {
00207 DeviceLocation *devLoc = UPnp::g_SSDPCache.Find(URI, URN);
00208
00209 if (devLoc != NULL)
00210 {
00211 devLoc->AddRef();
00212 AddItem(devLoc);
00213 }
00214 }
00215 else if (message.startsWith("SSDP_REMOVE"))
00216 {
00217
00218
00219 RemoveItem(URN);
00220 }
00221 }
00222
00223 void BackendSelect::FillListBox(void)
00224 {
00225 EntryMap::Iterator it;
00226 EntryMap ourMap;
00227 DeviceLocation *pDevLoc;
00228
00229
00230 SSDPCacheEntries *pEntries = UPnp::g_SSDPCache.Find(gBackendURI);
00231
00232 if (!pEntries)
00233 return;
00234
00235 pEntries->AddRef();
00236 pEntries->Lock();
00237
00238 EntryMap *pMap = pEntries->GetEntryMap();
00239
00240 for (it = pMap->begin(); it != pMap->end(); ++it)
00241 {
00242 pDevLoc = (DeviceLocation *)it.data();
00243
00244 if (!pDevLoc)
00245 continue;
00246
00247 pDevLoc->AddRef();
00248 ourMap.insert(pDevLoc->m_sUSN, pDevLoc);
00249 }
00250
00251
00252 pEntries->Unlock();
00253 pEntries->Release();
00254
00255 for (it = ourMap.begin(); it != ourMap.end(); ++it)
00256 {
00257 pDevLoc = (DeviceLocation *)it.data();
00258 AddItem(pDevLoc);
00259 }
00260 }
00261
00262 void BackendSelect::Manual(void)
00263 {
00264 done(kDialogCodeButton0);
00265 }
00266
00267 void BackendSelect::RemoveItem(QString USN)
00268 {
00269 ItemMap::iterator it = m_devices.find(USN);
00270
00271 if (it != m_devices.end())
00272 {
00273 ListBoxDevice *item = it.data();
00274
00275 if (item != NULL)
00276 delete item;
00277
00278 m_devices.remove(it);
00279 }
00280 }
00281
00282
00283
00284
00285