1 #include <QCoreApplication>
27 #define LOC QString("Frontend API: ")
46 if (Message.isEmpty())
50 auto Timeout = std::chrono::seconds(_Timeout);
51 if (Timeout > 0s && Timeout < 1000s)
52 data << QString::number(Timeout.count());
61 const QString &Message,
62 const QString &Origin,
63 const QString &Description,
66 const QString &ProgressText,
73 if (Message.isEmpty())
81 Origin.isNull() ? tr(
"FrontendServices") : Origin,
82 Description, Image, Extra,
83 ProgressText, Progress, std::chrono::seconds(Timeout),
94 static const QStringList kValueActions =
102 if (!Value.isEmpty() && kValueActions.contains(
Action))
112 if (!Width || !Height)
114 LOG(VB_GENERAL, LOG_ERR,
LOC +
"Invalid screenshot parameters.");
119 args << QString::number(Width) << QString::number(Height);
126 auto* ke =
new QKeyEvent(QEvent::KeyPress, 0, Qt::NoModifier,
Action);
132 const QDateTime &StartTime)
134 QDateTime starttime = StartTime;
136 if ((RecordedId <= 0) &&
137 (ChanId <= 0 || !StartTime.isValid()))
138 throw QString(
"Recorded ID or Channel ID and StartTime appears invalid.");
147 if (
GetMythUI()->GetCurrentLocation().toLower() ==
"playback")
149 QString message = QString(
"NETWORK_CONTROL STOP");
155 while (!timer.hasExpired(10000) &&
156 (
GetMythUI()->GetCurrentLocation().toLower() ==
"playback"))
157 std::this_thread::sleep_for(10ms);
160 if (
GetMythUI()->GetCurrentLocation().toLower() !=
"playbackbox")
166 while (!timer.hasExpired(10000) &&
167 (
GetMythUI()->GetCurrentLocation().toLower() !=
"playbackbox"))
168 std::this_thread::sleep_for(10ms);
172 std::this_thread::sleep_for(10ms);
175 if (
GetMythUI()->GetCurrentLocation().toLower() ==
"playbackbox")
177 LOG(VB_GENERAL, LOG_INFO,
LOC +
178 QString(
"PlayRecording, ChanID: %1 StartTime: %2")
181 QString message = QString(
"NETWORK_CONTROL PLAY PROGRAM %1 %2 %3")
183 .arg(starttime.toString(
"yyyyMMddhhmmss"))
198 LOG(VB_GENERAL, LOG_WARNING,
LOC +
199 QString(
"Ignoring PlayVideo request - frontend is busy."));
204 quint64
id = Id.toUInt(&ok);
207 LOG(VB_GENERAL, LOG_WARNING,
LOC + QString(
"Invalid video Id."));
216 LOG(VB_GENERAL, LOG_WARNING,
LOC +
217 QString(
"Didn't find any video metadata."));
221 if (metadata->GetHost().isEmpty())
223 LOG(VB_GENERAL, LOG_WARNING,
LOC +
224 QString(
"No host for video."));
229 metadata->GetFilename());
230 LOG(VB_GENERAL, LOG_INFO,
LOC +
231 QString(
"PlayVideo, id: %1 usebookmark: %2 url: '%3'")
235 args << mrl << metadata->GetPlot() << metadata->GetTitle()
236 << metadata->GetSubtitle() << metadata->GetDirector()
237 << QString::number(metadata->GetSeason())
238 << QString::number(metadata->GetEpisode())
239 << metadata->GetInetRef() << QString::number(metadata->GetLength().count())
240 << QString::number(metadata->GetYear())
241 << QString::number(metadata->GetID())
242 << QString::number(
static_cast<int>(UseBookmark));
263 while (contexts.hasNext())
266 if (!lContext.isEmpty() && contexts.key() != lContext)
270 QStringList actions = contexts.value();
271 for (
const QString &
action : qAsConst(actions))
273 QStringList split =
action.split(
",");
274 if (split.size() == 2)
275 list->ActionList().insert(split[0], split[1]);
288 if (
Action.startsWith(
"SELECTSUBTITLE_") ||
289 Action.startsWith(
"SELECTTTC_") ||
290 Action.startsWith(
"SELECTCC608_") ||
291 Action.startsWith(
"SELECTCC708_") ||
292 Action.startsWith(
"SELECTRAWTEXT_") ||
293 Action.startsWith(
"SELECTAUDIO_"))
298 LOG(VB_GENERAL, LOG_ERR,
LOC + QString(
"Action '%1'' is invalid.")
305 static bool s_initialised =
false;
309 s_initialised =
true;
313 QStringList contexts = bindings->GetContexts();
315 for (
const QString & context : qAsConst(contexts))
318 QStringList ctx_actions = bindings->GetActions(context);
321 for (
const QString & actions : qAsConst(ctx_actions))
323 QString desc = actions +
"," +
324 bindings->GetActionDescription(context, actions);
333 for (
const QString & actions : qAsConst(
gActionList))
334 LOG(VB_GENERAL, LOG_DEBUG,
LOC + QString(
"Action: %1").
arg(actions));
341 QObject *keyDest =
nullptr;
342 QKeyEvent *
event =
nullptr;
343 QMap <QString, int> keyMap;
347 keyMap[
"up"] = Qt::Key_Up;
348 keyMap[
"down"] = Qt::Key_Down;
349 keyMap[
"left"] = Qt::Key_Left;
350 keyMap[
"right"] = Qt::Key_Right;
351 keyMap[
"home"] = Qt::Key_Home;
352 keyMap[
"end"] = Qt::Key_End;
353 keyMap[
"enter"] = Qt::Key_Enter;
354 keyMap[
"return"] = Qt::Key_Return;
355 keyMap[
"pageup"] = Qt::Key_PageUp;
356 keyMap[
"pagedown"] = Qt::Key_PageDown;
357 keyMap[
"escape"] = Qt::Key_Escape;
358 keyMap[
"tab"] = Qt::Key_Tab;
359 keyMap[
"backtab"] = Qt::Key_Backtab;
360 keyMap[
"space"] = Qt::Key_Space;
361 keyMap[
"backspace"] = Qt::Key_Backspace;
362 keyMap[
"insert"] = Qt::Key_Insert;
363 keyMap[
"delete"] = Qt::Key_Delete;
364 keyMap[
"plus"] = Qt::Key_Plus;
365 keyMap[
"comma"] = Qt::Key_Comma;
366 keyMap[
"minus"] = Qt::Key_Minus;
367 keyMap[
"underscore"] = Qt::Key_Underscore;
368 keyMap[
"period"] = Qt::Key_Period;
369 keyMap[
"numbersign"] = Qt::Key_NumberSign;
370 keyMap[
"poundsign"] = Qt::Key_NumberSign;
371 keyMap[
"hash"] = Qt::Key_NumberSign;
372 keyMap[
"bracketleft"] = Qt::Key_BracketLeft;
373 keyMap[
"bracketright"] = Qt::Key_BracketRight;
374 keyMap[
"backslash"] = Qt::Key_Backslash;
375 keyMap[
"dollar"] = Qt::Key_Dollar;
376 keyMap[
"percent"] = Qt::Key_Percent;
377 keyMap[
"ampersand"] = Qt::Key_Ampersand;
378 keyMap[
"parenleft"] = Qt::Key_ParenLeft;
379 keyMap[
"parenright"] = Qt::Key_ParenRight;
380 keyMap[
"asterisk"] = Qt::Key_Asterisk;
381 keyMap[
"question"] = Qt::Key_Question;
382 keyMap[
"slash"] = Qt::Key_Slash;
383 keyMap[
"colon"] = Qt::Key_Colon;
384 keyMap[
"semicolon"] = Qt::Key_Semicolon;
385 keyMap[
"less"] = Qt::Key_Less;
386 keyMap[
"equal"] = Qt::Key_Equal;
387 keyMap[
"greater"] = Qt::Key_Greater;
388 keyMap[
"f1"] = Qt::Key_F1;
389 keyMap[
"f2"] = Qt::Key_F2;
390 keyMap[
"f3"] = Qt::Key_F3;
391 keyMap[
"f4"] = Qt::Key_F4;
392 keyMap[
"f5"] = Qt::Key_F5;
393 keyMap[
"f6"] = Qt::Key_F6;
394 keyMap[
"f7"] = Qt::Key_F7;
395 keyMap[
"f8"] = Qt::Key_F8;
396 keyMap[
"f9"] = Qt::Key_F9;
397 keyMap[
"f10"] = Qt::Key_F10;
398 keyMap[
"f11"] = Qt::Key_F11;
399 keyMap[
"f12"] = Qt::Key_F12;
400 keyMap[
"f13"] = Qt::Key_F13;
401 keyMap[
"f14"] = Qt::Key_F14;
402 keyMap[
"f15"] = Qt::Key_F15;
403 keyMap[
"f16"] = Qt::Key_F16;
404 keyMap[
"f17"] = Qt::Key_F17;
405 keyMap[
"f18"] = Qt::Key_F18;
406 keyMap[
"f19"] = Qt::Key_F19;
407 keyMap[
"f20"] = Qt::Key_F20;
408 keyMap[
"f21"] = Qt::Key_F21;
409 keyMap[
"f22"] = Qt::Key_F22;
410 keyMap[
"f23"] = Qt::Key_F23;
411 keyMap[
"f24"] = Qt::Key_F24;
415 LOG(VB_GENERAL, LOG_ERR,
LOC + QString(
"SendKey: No Key received"));
423 LOG(VB_GENERAL, LOG_ERR,
424 LOC + QString(
"SendKey: Application has no main window"));
428 if (keyMap.contains(sKey.toLower()))
430 keyCode = keyMap[sKey.toLower()];
433 else if (sKey.size() == 1)
435 keyCode = (int) sKey.toLatin1()[0] & 0x7f;
439 msg = QString(
"SendKey: Unknown Key = '%1'").arg(sKey);
445 event =
new QKeyEvent(QEvent::KeyPress, keyCode, Qt::NoModifier,
447 QCoreApplication::postEvent(keyDest, event);
449 event =
new QKeyEvent(QEvent::KeyRelease, keyCode, Qt::NoModifier,
451 QCoreApplication::postEvent(keyDest, event);
453 msg = QString(
"SendKey: Sent %1").arg(sKey);
456 LOG(VB_UPNP, LOG_INFO,
LOC + msg);