Documentation update
This commit is contained in:
@@ -114,16 +114,21 @@ The following control intents are also supported:
|
|||||||
|
|
||||||
Due to the way that Alexa skills operate there are some limitations. Full music Alexa skills require a catalog of content to be provided and this defeats
|
Due to the way that Alexa skills operate there are some limitations. Full music Alexa skills require a catalog of content to be provided and this defeats
|
||||||
the purpose of being able to search and stream from your own server directly. Because of this a custom skill type is used along with the AudioPlayer interface,
|
the purpose of being able to search and stream from your own server directly. Because of this a custom skill type is used along with the AudioPlayer interface,
|
||||||
but this has some limitations:
|
but this has some limitations in how the skill is invoked.
|
||||||
|
|
||||||
1. You need to open the skill to use it, say *Alexa, open Navisonic*.
|
The following voice commands should be successful (thanks to Raul824)
|
||||||
2. Some intents that you would expect to be able to use when a track is playing need a full skill invocation. For example if you want to get
|
|
||||||
information on the track that is playing you will need to invoke the skill and call the intent by saying the following while the track is playing:
|
|
||||||
|
|
||||||
- Alexa, open Navisonic
|
- Alexa ask Navisonic What is Playing?
|
||||||
- What is playing?
|
- Alexa ask Navisonic to star this song.
|
||||||
|
- Alexa ask Navisonic to unstar this song.
|
||||||
|
- Alexa ask Navisonic to play rock music
|
||||||
|
- Alexa ask Navisonic to play playlist "Playlist Name"
|
||||||
|
|
||||||
You will then be given information about the current track and it will automatically resume. This is also required for the *star* and *unstar* intents.
|
If you have any problems with these, you can open the skill manually with *Alexa, open Navisonic*. Similarly this can be done when a track is playing, for example
|
||||||
|
if you want to get information on the track that is playing you will need to invoke the skill and call the intent by saying the following while the track is playing:
|
||||||
|
|
||||||
|
- Alexa, open Navisonic
|
||||||
|
- What is playing?
|
||||||
|
|
||||||
|
|
||||||
Installation and Setup
|
Installation and Setup
|
||||||
|
|||||||
130
docs/_static/doctools.js
vendored
130
docs/_static/doctools.js
vendored
@@ -10,6 +10,13 @@
|
|||||||
*/
|
*/
|
||||||
"use strict";
|
"use strict";
|
||||||
|
|
||||||
|
const BLACKLISTED_KEY_CONTROL_ELEMENTS = new Set([
|
||||||
|
"TEXTAREA",
|
||||||
|
"INPUT",
|
||||||
|
"SELECT",
|
||||||
|
"BUTTON",
|
||||||
|
]);
|
||||||
|
|
||||||
const _ready = (callback) => {
|
const _ready = (callback) => {
|
||||||
if (document.readyState !== "loading") {
|
if (document.readyState !== "loading") {
|
||||||
callback();
|
callback();
|
||||||
@@ -18,73 +25,11 @@ const _ready = (callback) => {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
|
||||||
* highlight a given string on a node by wrapping it in
|
|
||||||
* span elements with the given class name.
|
|
||||||
*/
|
|
||||||
const _highlight = (node, addItems, text, className) => {
|
|
||||||
if (node.nodeType === Node.TEXT_NODE) {
|
|
||||||
const val = node.nodeValue;
|
|
||||||
const parent = node.parentNode;
|
|
||||||
const pos = val.toLowerCase().indexOf(text);
|
|
||||||
if (
|
|
||||||
pos >= 0 &&
|
|
||||||
!parent.classList.contains(className) &&
|
|
||||||
!parent.classList.contains("nohighlight")
|
|
||||||
) {
|
|
||||||
let span;
|
|
||||||
|
|
||||||
const closestNode = parent.closest("body, svg, foreignObject");
|
|
||||||
const isInSVG = closestNode && closestNode.matches("svg");
|
|
||||||
if (isInSVG) {
|
|
||||||
span = document.createElementNS("http://www.w3.org/2000/svg", "tspan");
|
|
||||||
} else {
|
|
||||||
span = document.createElement("span");
|
|
||||||
span.classList.add(className);
|
|
||||||
}
|
|
||||||
|
|
||||||
span.appendChild(document.createTextNode(val.substr(pos, text.length)));
|
|
||||||
parent.insertBefore(
|
|
||||||
span,
|
|
||||||
parent.insertBefore(
|
|
||||||
document.createTextNode(val.substr(pos + text.length)),
|
|
||||||
node.nextSibling
|
|
||||||
)
|
|
||||||
);
|
|
||||||
node.nodeValue = val.substr(0, pos);
|
|
||||||
|
|
||||||
if (isInSVG) {
|
|
||||||
const rect = document.createElementNS(
|
|
||||||
"http://www.w3.org/2000/svg",
|
|
||||||
"rect"
|
|
||||||
);
|
|
||||||
const bbox = parent.getBBox();
|
|
||||||
rect.x.baseVal.value = bbox.x;
|
|
||||||
rect.y.baseVal.value = bbox.y;
|
|
||||||
rect.width.baseVal.value = bbox.width;
|
|
||||||
rect.height.baseVal.value = bbox.height;
|
|
||||||
rect.setAttribute("class", className);
|
|
||||||
addItems.push({ parent: parent, target: rect });
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else if (node.matches && !node.matches("button, select, textarea")) {
|
|
||||||
node.childNodes.forEach((el) => _highlight(el, addItems, text, className));
|
|
||||||
}
|
|
||||||
};
|
|
||||||
const _highlightText = (thisNode, text, className) => {
|
|
||||||
let addItems = [];
|
|
||||||
_highlight(thisNode, addItems, text, className);
|
|
||||||
addItems.forEach((obj) =>
|
|
||||||
obj.parent.insertAdjacentElement("beforebegin", obj.target)
|
|
||||||
);
|
|
||||||
};
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Small JavaScript module for the documentation.
|
* Small JavaScript module for the documentation.
|
||||||
*/
|
*/
|
||||||
const Documentation = {
|
const Documentation = {
|
||||||
init: () => {
|
init: () => {
|
||||||
Documentation.highlightSearchWords();
|
|
||||||
Documentation.initDomainIndexTable();
|
Documentation.initDomainIndexTable();
|
||||||
Documentation.initOnKeyListeners();
|
Documentation.initOnKeyListeners();
|
||||||
},
|
},
|
||||||
@@ -126,51 +71,6 @@ const Documentation = {
|
|||||||
Documentation.LOCALE = catalog.locale;
|
Documentation.LOCALE = catalog.locale;
|
||||||
},
|
},
|
||||||
|
|
||||||
/**
|
|
||||||
* highlight the search words provided in the url in the text
|
|
||||||
*/
|
|
||||||
highlightSearchWords: () => {
|
|
||||||
const highlight =
|
|
||||||
new URLSearchParams(window.location.search).get("highlight") || "";
|
|
||||||
const terms = highlight.toLowerCase().split(/\s+/).filter(x => x);
|
|
||||||
if (terms.length === 0) return; // nothing to do
|
|
||||||
|
|
||||||
// There should never be more than one element matching "div.body"
|
|
||||||
const divBody = document.querySelectorAll("div.body");
|
|
||||||
const body = divBody.length ? divBody[0] : document.querySelector("body");
|
|
||||||
window.setTimeout(() => {
|
|
||||||
terms.forEach((term) => _highlightText(body, term, "highlighted"));
|
|
||||||
}, 10);
|
|
||||||
|
|
||||||
const searchBox = document.getElementById("searchbox");
|
|
||||||
if (searchBox === null) return;
|
|
||||||
searchBox.appendChild(
|
|
||||||
document
|
|
||||||
.createRange()
|
|
||||||
.createContextualFragment(
|
|
||||||
'<p class="highlight-link">' +
|
|
||||||
'<a href="javascript:Documentation.hideSearchWords()">' +
|
|
||||||
Documentation.gettext("Hide Search Matches") +
|
|
||||||
"</a></p>"
|
|
||||||
)
|
|
||||||
);
|
|
||||||
},
|
|
||||||
|
|
||||||
/**
|
|
||||||
* helper function to hide the search marks again
|
|
||||||
*/
|
|
||||||
hideSearchWords: () => {
|
|
||||||
document
|
|
||||||
.querySelectorAll("#searchbox .highlight-link")
|
|
||||||
.forEach((el) => el.remove());
|
|
||||||
document
|
|
||||||
.querySelectorAll("span.highlighted")
|
|
||||||
.forEach((el) => el.classList.remove("highlighted"));
|
|
||||||
const url = new URL(window.location);
|
|
||||||
url.searchParams.delete("highlight");
|
|
||||||
window.history.replaceState({}, "", url);
|
|
||||||
},
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* helper function to focus on search bar
|
* helper function to focus on search bar
|
||||||
*/
|
*/
|
||||||
@@ -210,15 +110,11 @@ const Documentation = {
|
|||||||
)
|
)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
const blacklistedElements = new Set([
|
|
||||||
"TEXTAREA",
|
|
||||||
"INPUT",
|
|
||||||
"SELECT",
|
|
||||||
"BUTTON",
|
|
||||||
]);
|
|
||||||
document.addEventListener("keydown", (event) => {
|
document.addEventListener("keydown", (event) => {
|
||||||
if (blacklistedElements.has(document.activeElement.tagName)) return; // bail for input elements
|
// bail for input elements
|
||||||
if (event.altKey || event.ctrlKey || event.metaKey) return; // bail with special keys
|
if (BLACKLISTED_KEY_CONTROL_ELEMENTS.has(document.activeElement.tagName)) return;
|
||||||
|
// bail with special keys
|
||||||
|
if (event.altKey || event.ctrlKey || event.metaKey) return;
|
||||||
|
|
||||||
if (!event.shiftKey) {
|
if (!event.shiftKey) {
|
||||||
switch (event.key) {
|
switch (event.key) {
|
||||||
@@ -240,10 +136,6 @@ const Documentation = {
|
|||||||
event.preventDefault();
|
event.preventDefault();
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case "Escape":
|
|
||||||
if (!DOCUMENTATION_OPTIONS.ENABLE_SEARCH_SHORTCUTS) break;
|
|
||||||
Documentation.hideSearchWords();
|
|
||||||
event.preventDefault();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
74
docs/_static/searchtools.js
vendored
74
docs/_static/searchtools.js
vendored
@@ -57,14 +57,14 @@ const _removeChildren = (element) => {
|
|||||||
const _escapeRegExp = (string) =>
|
const _escapeRegExp = (string) =>
|
||||||
string.replace(/[.*+\-?^${}()|[\]\\]/g, "\\$&"); // $& means the whole matched string
|
string.replace(/[.*+\-?^${}()|[\]\\]/g, "\\$&"); // $& means the whole matched string
|
||||||
|
|
||||||
const _displayItem = (item, highlightTerms, searchTerms) => {
|
const _displayItem = (item, searchTerms) => {
|
||||||
const docBuilder = DOCUMENTATION_OPTIONS.BUILDER;
|
const docBuilder = DOCUMENTATION_OPTIONS.BUILDER;
|
||||||
const docUrlRoot = DOCUMENTATION_OPTIONS.URL_ROOT;
|
const docUrlRoot = DOCUMENTATION_OPTIONS.URL_ROOT;
|
||||||
const docFileSuffix = DOCUMENTATION_OPTIONS.FILE_SUFFIX;
|
const docFileSuffix = DOCUMENTATION_OPTIONS.FILE_SUFFIX;
|
||||||
const docLinkSuffix = DOCUMENTATION_OPTIONS.LINK_SUFFIX;
|
const docLinkSuffix = DOCUMENTATION_OPTIONS.LINK_SUFFIX;
|
||||||
const showSearchSummary = DOCUMENTATION_OPTIONS.SHOW_SEARCH_SUMMARY;
|
const showSearchSummary = DOCUMENTATION_OPTIONS.SHOW_SEARCH_SUMMARY;
|
||||||
|
|
||||||
const [docName, title, anchor, descr] = item;
|
const [docName, title, anchor, descr, score, _filename] = item;
|
||||||
|
|
||||||
let listItem = document.createElement("li");
|
let listItem = document.createElement("li");
|
||||||
let requestUrl;
|
let requestUrl;
|
||||||
@@ -82,10 +82,9 @@ const _displayItem = (item, highlightTerms, searchTerms) => {
|
|||||||
requestUrl = docUrlRoot + docName + docFileSuffix;
|
requestUrl = docUrlRoot + docName + docFileSuffix;
|
||||||
linkUrl = docName + docLinkSuffix;
|
linkUrl = docName + docLinkSuffix;
|
||||||
}
|
}
|
||||||
const params = new URLSearchParams();
|
|
||||||
params.set("highlight", [...highlightTerms].join(" "));
|
|
||||||
let linkEl = listItem.appendChild(document.createElement("a"));
|
let linkEl = listItem.appendChild(document.createElement("a"));
|
||||||
linkEl.href = linkUrl + "?" + params.toString() + anchor;
|
linkEl.href = linkUrl + anchor;
|
||||||
|
linkEl.dataset.score = score;
|
||||||
linkEl.innerHTML = title;
|
linkEl.innerHTML = title;
|
||||||
if (descr)
|
if (descr)
|
||||||
listItem.appendChild(document.createElement("span")).innerHTML =
|
listItem.appendChild(document.createElement("span")).innerHTML =
|
||||||
@@ -96,7 +95,7 @@ const _displayItem = (item, highlightTerms, searchTerms) => {
|
|||||||
.then((data) => {
|
.then((data) => {
|
||||||
if (data)
|
if (data)
|
||||||
listItem.appendChild(
|
listItem.appendChild(
|
||||||
Search.makeSearchSummary(data, searchTerms, highlightTerms)
|
Search.makeSearchSummary(data, searchTerms)
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
Search.output.appendChild(listItem);
|
Search.output.appendChild(listItem);
|
||||||
@@ -116,15 +115,14 @@ const _finishSearch = (resultCount) => {
|
|||||||
const _displayNextItem = (
|
const _displayNextItem = (
|
||||||
results,
|
results,
|
||||||
resultCount,
|
resultCount,
|
||||||
highlightTerms,
|
|
||||||
searchTerms
|
searchTerms
|
||||||
) => {
|
) => {
|
||||||
// results left, load the summary and display it
|
// results left, load the summary and display it
|
||||||
// this is intended to be dynamic (don't sub resultsCount)
|
// this is intended to be dynamic (don't sub resultsCount)
|
||||||
if (results.length) {
|
if (results.length) {
|
||||||
_displayItem(results.pop(), highlightTerms, searchTerms);
|
_displayItem(results.pop(), searchTerms);
|
||||||
setTimeout(
|
setTimeout(
|
||||||
() => _displayNextItem(results, resultCount, highlightTerms, searchTerms),
|
() => _displayNextItem(results, resultCount, searchTerms),
|
||||||
5
|
5
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@@ -237,6 +235,12 @@ const Search = {
|
|||||||
* execute search (requires search index to be loaded)
|
* execute search (requires search index to be loaded)
|
||||||
*/
|
*/
|
||||||
query: (query) => {
|
query: (query) => {
|
||||||
|
const filenames = Search._index.filenames;
|
||||||
|
const docNames = Search._index.docnames;
|
||||||
|
const titles = Search._index.titles;
|
||||||
|
const allTitles = Search._index.alltitles;
|
||||||
|
const indexEntries = Search._index.indexentries;
|
||||||
|
|
||||||
// stem the search terms and add them to the correct list
|
// stem the search terms and add them to the correct list
|
||||||
const stemmer = new Stemmer();
|
const stemmer = new Stemmer();
|
||||||
const searchTerms = new Set();
|
const searchTerms = new Set();
|
||||||
@@ -264,6 +268,10 @@ const Search = {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
if (SPHINX_HIGHLIGHT_ENABLED) { // set in sphinx_highlight.js
|
||||||
|
localStorage.setItem("sphinx_highlight_terms", [...highlightTerms].join(" "))
|
||||||
|
}
|
||||||
|
|
||||||
// console.debug("SEARCH: searching for:");
|
// console.debug("SEARCH: searching for:");
|
||||||
// console.info("required: ", [...searchTerms]);
|
// console.info("required: ", [...searchTerms]);
|
||||||
// console.info("excluded: ", [...excludedTerms]);
|
// console.info("excluded: ", [...excludedTerms]);
|
||||||
@@ -272,6 +280,40 @@ const Search = {
|
|||||||
let results = [];
|
let results = [];
|
||||||
_removeChildren(document.getElementById("search-progress"));
|
_removeChildren(document.getElementById("search-progress"));
|
||||||
|
|
||||||
|
const queryLower = query.toLowerCase();
|
||||||
|
for (const [title, foundTitles] of Object.entries(allTitles)) {
|
||||||
|
if (title.toLowerCase().includes(queryLower) && (queryLower.length >= title.length/2)) {
|
||||||
|
for (const [file, id] of foundTitles) {
|
||||||
|
let score = Math.round(100 * queryLower.length / title.length)
|
||||||
|
results.push([
|
||||||
|
docNames[file],
|
||||||
|
titles[file] !== title ? `${titles[file]} > ${title}` : title,
|
||||||
|
id !== null ? "#" + id : "",
|
||||||
|
null,
|
||||||
|
score,
|
||||||
|
filenames[file],
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// search for explicit entries in index directives
|
||||||
|
for (const [entry, foundEntries] of Object.entries(indexEntries)) {
|
||||||
|
if (entry.includes(queryLower) && (queryLower.length >= entry.length/2)) {
|
||||||
|
for (const [file, id] of foundEntries) {
|
||||||
|
let score = Math.round(100 * queryLower.length / entry.length)
|
||||||
|
results.push([
|
||||||
|
docNames[file],
|
||||||
|
titles[file],
|
||||||
|
id ? "#" + id : "",
|
||||||
|
null,
|
||||||
|
score,
|
||||||
|
filenames[file],
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// lookup as object
|
// lookup as object
|
||||||
objectTerms.forEach((term) =>
|
objectTerms.forEach((term) =>
|
||||||
results.push(...Search.performObjectSearch(term, objectTerms))
|
results.push(...Search.performObjectSearch(term, objectTerms))
|
||||||
@@ -318,7 +360,7 @@ const Search = {
|
|||||||
// console.info("search results:", Search.lastresults);
|
// console.info("search results:", Search.lastresults);
|
||||||
|
|
||||||
// print the results
|
// print the results
|
||||||
_displayNextItem(results, results.length, highlightTerms, searchTerms);
|
_displayNextItem(results, results.length, searchTerms);
|
||||||
},
|
},
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -399,8 +441,8 @@ const Search = {
|
|||||||
// prepare search
|
// prepare search
|
||||||
const terms = Search._index.terms;
|
const terms = Search._index.terms;
|
||||||
const titleTerms = Search._index.titleterms;
|
const titleTerms = Search._index.titleterms;
|
||||||
const docNames = Search._index.docnames;
|
|
||||||
const filenames = Search._index.filenames;
|
const filenames = Search._index.filenames;
|
||||||
|
const docNames = Search._index.docnames;
|
||||||
const titles = Search._index.titles;
|
const titles = Search._index.titles;
|
||||||
|
|
||||||
const scoreMap = new Map();
|
const scoreMap = new Map();
|
||||||
@@ -497,11 +539,9 @@ const Search = {
|
|||||||
/**
|
/**
|
||||||
* helper function to return a node containing the
|
* helper function to return a node containing the
|
||||||
* search summary for a given text. keywords is a list
|
* search summary for a given text. keywords is a list
|
||||||
* of stemmed words, highlightWords is the list of normal, unstemmed
|
* of stemmed words.
|
||||||
* words. the first one is used to find the occurrence, the
|
|
||||||
* latter for highlighting it.
|
|
||||||
*/
|
*/
|
||||||
makeSearchSummary: (htmlText, keywords, highlightWords) => {
|
makeSearchSummary: (htmlText, keywords) => {
|
||||||
const text = Search.htmlToText(htmlText);
|
const text = Search.htmlToText(htmlText);
|
||||||
if (text === "") return null;
|
if (text === "") return null;
|
||||||
|
|
||||||
@@ -519,10 +559,6 @@ const Search = {
|
|||||||
summary.classList.add("context");
|
summary.classList.add("context");
|
||||||
summary.textContent = top + text.substr(startWithContext, 240).trim() + tail;
|
summary.textContent = top + text.substr(startWithContext, 240).trim() + tail;
|
||||||
|
|
||||||
highlightWords.forEach((highlightWord) =>
|
|
||||||
_highlightText(summary, highlightWord, "highlighted")
|
|
||||||
);
|
|
||||||
|
|
||||||
return summary;
|
return summary;
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|||||||
144
docs/_static/sphinx_highlight.js
vendored
Normal file
144
docs/_static/sphinx_highlight.js
vendored
Normal file
@@ -0,0 +1,144 @@
|
|||||||
|
/* Highlighting utilities for Sphinx HTML documentation. */
|
||||||
|
"use strict";
|
||||||
|
|
||||||
|
const SPHINX_HIGHLIGHT_ENABLED = true
|
||||||
|
|
||||||
|
/**
|
||||||
|
* highlight a given string on a node by wrapping it in
|
||||||
|
* span elements with the given class name.
|
||||||
|
*/
|
||||||
|
const _highlight = (node, addItems, text, className) => {
|
||||||
|
if (node.nodeType === Node.TEXT_NODE) {
|
||||||
|
const val = node.nodeValue;
|
||||||
|
const parent = node.parentNode;
|
||||||
|
const pos = val.toLowerCase().indexOf(text);
|
||||||
|
if (
|
||||||
|
pos >= 0 &&
|
||||||
|
!parent.classList.contains(className) &&
|
||||||
|
!parent.classList.contains("nohighlight")
|
||||||
|
) {
|
||||||
|
let span;
|
||||||
|
|
||||||
|
const closestNode = parent.closest("body, svg, foreignObject");
|
||||||
|
const isInSVG = closestNode && closestNode.matches("svg");
|
||||||
|
if (isInSVG) {
|
||||||
|
span = document.createElementNS("http://www.w3.org/2000/svg", "tspan");
|
||||||
|
} else {
|
||||||
|
span = document.createElement("span");
|
||||||
|
span.classList.add(className);
|
||||||
|
}
|
||||||
|
|
||||||
|
span.appendChild(document.createTextNode(val.substr(pos, text.length)));
|
||||||
|
parent.insertBefore(
|
||||||
|
span,
|
||||||
|
parent.insertBefore(
|
||||||
|
document.createTextNode(val.substr(pos + text.length)),
|
||||||
|
node.nextSibling
|
||||||
|
)
|
||||||
|
);
|
||||||
|
node.nodeValue = val.substr(0, pos);
|
||||||
|
|
||||||
|
if (isInSVG) {
|
||||||
|
const rect = document.createElementNS(
|
||||||
|
"http://www.w3.org/2000/svg",
|
||||||
|
"rect"
|
||||||
|
);
|
||||||
|
const bbox = parent.getBBox();
|
||||||
|
rect.x.baseVal.value = bbox.x;
|
||||||
|
rect.y.baseVal.value = bbox.y;
|
||||||
|
rect.width.baseVal.value = bbox.width;
|
||||||
|
rect.height.baseVal.value = bbox.height;
|
||||||
|
rect.setAttribute("class", className);
|
||||||
|
addItems.push({ parent: parent, target: rect });
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else if (node.matches && !node.matches("button, select, textarea")) {
|
||||||
|
node.childNodes.forEach((el) => _highlight(el, addItems, text, className));
|
||||||
|
}
|
||||||
|
};
|
||||||
|
const _highlightText = (thisNode, text, className) => {
|
||||||
|
let addItems = [];
|
||||||
|
_highlight(thisNode, addItems, text, className);
|
||||||
|
addItems.forEach((obj) =>
|
||||||
|
obj.parent.insertAdjacentElement("beforebegin", obj.target)
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Small JavaScript module for the documentation.
|
||||||
|
*/
|
||||||
|
const SphinxHighlight = {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* highlight the search words provided in localstorage in the text
|
||||||
|
*/
|
||||||
|
highlightSearchWords: () => {
|
||||||
|
if (!SPHINX_HIGHLIGHT_ENABLED) return; // bail if no highlight
|
||||||
|
|
||||||
|
// get and clear terms from localstorage
|
||||||
|
const url = new URL(window.location);
|
||||||
|
const highlight =
|
||||||
|
localStorage.getItem("sphinx_highlight_terms")
|
||||||
|
|| url.searchParams.get("highlight")
|
||||||
|
|| "";
|
||||||
|
localStorage.removeItem("sphinx_highlight_terms")
|
||||||
|
url.searchParams.delete("highlight");
|
||||||
|
window.history.replaceState({}, "", url);
|
||||||
|
|
||||||
|
// get individual terms from highlight string
|
||||||
|
const terms = highlight.toLowerCase().split(/\s+/).filter(x => x);
|
||||||
|
if (terms.length === 0) return; // nothing to do
|
||||||
|
|
||||||
|
// There should never be more than one element matching "div.body"
|
||||||
|
const divBody = document.querySelectorAll("div.body");
|
||||||
|
const body = divBody.length ? divBody[0] : document.querySelector("body");
|
||||||
|
window.setTimeout(() => {
|
||||||
|
terms.forEach((term) => _highlightText(body, term, "highlighted"));
|
||||||
|
}, 10);
|
||||||
|
|
||||||
|
const searchBox = document.getElementById("searchbox");
|
||||||
|
if (searchBox === null) return;
|
||||||
|
searchBox.appendChild(
|
||||||
|
document
|
||||||
|
.createRange()
|
||||||
|
.createContextualFragment(
|
||||||
|
'<p class="highlight-link">' +
|
||||||
|
'<a href="javascript:SphinxHighlight.hideSearchWords()">' +
|
||||||
|
_("Hide Search Matches") +
|
||||||
|
"</a></p>"
|
||||||
|
)
|
||||||
|
);
|
||||||
|
},
|
||||||
|
|
||||||
|
/**
|
||||||
|
* helper function to hide the search marks again
|
||||||
|
*/
|
||||||
|
hideSearchWords: () => {
|
||||||
|
document
|
||||||
|
.querySelectorAll("#searchbox .highlight-link")
|
||||||
|
.forEach((el) => el.remove());
|
||||||
|
document
|
||||||
|
.querySelectorAll("span.highlighted")
|
||||||
|
.forEach((el) => el.classList.remove("highlighted"));
|
||||||
|
localStorage.removeItem("sphinx_highlight_terms")
|
||||||
|
},
|
||||||
|
|
||||||
|
initEscapeListener: () => {
|
||||||
|
// only install a listener if it is really needed
|
||||||
|
if (!DOCUMENTATION_OPTIONS.ENABLE_SEARCH_SHORTCUTS) return;
|
||||||
|
|
||||||
|
document.addEventListener("keydown", (event) => {
|
||||||
|
// bail for input elements
|
||||||
|
if (BLACKLISTED_KEY_CONTROL_ELEMENTS.has(document.activeElement.tagName)) return;
|
||||||
|
// bail with special keys
|
||||||
|
if (event.shiftKey || event.altKey || event.ctrlKey || event.metaKey) return;
|
||||||
|
if (DOCUMENTATION_OPTIONS.ENABLE_SEARCH_SHORTCUTS && (event.key === "Escape")) {
|
||||||
|
SphinxHighlight.hideSearchWords();
|
||||||
|
event.preventDefault();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
_ready(SphinxHighlight.highlightSearchWords);
|
||||||
|
_ready(SphinxHighlight.initEscapeListener);
|
||||||
@@ -15,6 +15,7 @@
|
|||||||
<script src="_static/underscore.js"></script>
|
<script src="_static/underscore.js"></script>
|
||||||
<script src="_static/_sphinx_javascript_frameworks_compat.js"></script>
|
<script src="_static/_sphinx_javascript_frameworks_compat.js"></script>
|
||||||
<script src="_static/doctools.js"></script>
|
<script src="_static/doctools.js"></script>
|
||||||
|
<script src="_static/sphinx_highlight.js"></script>
|
||||||
<link rel="index" title="Index" href="#" />
|
<link rel="index" title="Index" href="#" />
|
||||||
<link rel="search" title="Search" href="search.html" />
|
<link rel="search" title="Search" href="search.html" />
|
||||||
</head><body>
|
</head><body>
|
||||||
@@ -479,7 +480,7 @@
|
|||||||
</div>
|
</div>
|
||||||
<div class="footer" role="contentinfo">
|
<div class="footer" role="contentinfo">
|
||||||
© Copyright 2022, Ross Stewart.
|
© Copyright 2022, Ross Stewart.
|
||||||
Created using <a href="https://www.sphinx-doc.org/">Sphinx</a> 5.1.1.
|
Created using <a href="https://www.sphinx-doc.org/">Sphinx</a> 5.3.0.
|
||||||
</div>
|
</div>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
218
docs/index.html
218
docs/index.html
@@ -16,6 +16,7 @@
|
|||||||
<script src="_static/underscore.js"></script>
|
<script src="_static/underscore.js"></script>
|
||||||
<script src="_static/_sphinx_javascript_frameworks_compat.js"></script>
|
<script src="_static/_sphinx_javascript_frameworks_compat.js"></script>
|
||||||
<script src="_static/doctools.js"></script>
|
<script src="_static/doctools.js"></script>
|
||||||
|
<script src="_static/sphinx_highlight.js"></script>
|
||||||
<link rel="index" title="Index" href="genindex.html" />
|
<link rel="index" title="Index" href="genindex.html" />
|
||||||
<link rel="search" title="Search" href="search.html" />
|
<link rel="search" title="Search" href="search.html" />
|
||||||
</head><body>
|
</head><body>
|
||||||
@@ -153,18 +154,21 @@ behind a reverse proxy, the web service also needs to be publicly accessible on
|
|||||||
</ul>
|
</ul>
|
||||||
<p>Due to the way that Alexa skills operate there are some limitations. Full music Alexa skills require a catalog of content to be provided and this defeats
|
<p>Due to the way that Alexa skills operate there are some limitations. Full music Alexa skills require a catalog of content to be provided and this defeats
|
||||||
the purpose of being able to search and stream from your own server directly. Because of this a custom skill type is used along with the AudioPlayer interface,
|
the purpose of being able to search and stream from your own server directly. Because of this a custom skill type is used along with the AudioPlayer interface,
|
||||||
but this has some limitations:</p>
|
but this has some limitations in how the skill is invoked.</p>
|
||||||
<ol class="arabic">
|
<p>The following voice commands should be successful (thanks to Raul824)</p>
|
||||||
<li><p>You need to open the skill to use it, say <em>Alexa, open Navisonic</em>.</p></li>
|
<ul class="simple">
|
||||||
<li><p>Some intents that you would expect to be able to use when a track is playing need a full skill invocation. For example if you want to get
|
<li><p>Alexa ask Navisonic What is Playing?</p></li>
|
||||||
information on the track that is playing you will need to invoke the skill and call the intent by saying the following while the track is playing:</p>
|
<li><p>Alexa ask Navisonic to star this song.</p></li>
|
||||||
|
<li><p>Alexa ask Navisonic to unstar this song.</p></li>
|
||||||
|
<li><p>Alexa ask Navisonic to play rock music</p></li>
|
||||||
|
<li><p>Alexa ask Navisonic to play playlist “Playlist Name”</p></li>
|
||||||
|
</ul>
|
||||||
|
<p>If you have any problems with these, you can open the skill manually with <em>Alexa, open Navisonic</em>. Similarly this can be done when a track is playing, for example
|
||||||
|
if you want to get information on the track that is playing you will need to invoke the skill and call the intent by saying the following while the track is playing:</p>
|
||||||
<ul class="simple">
|
<ul class="simple">
|
||||||
<li><p>Alexa, open Navisonic</p></li>
|
<li><p>Alexa, open Navisonic</p></li>
|
||||||
<li><p>What is playing?</p></li>
|
<li><p>What is playing?</p></li>
|
||||||
</ul>
|
</ul>
|
||||||
<p>You will then be given information about the current track and it will automatically resume. This is also required for the <em>star</em> and <em>unstar</em> intents.</p>
|
|
||||||
</li>
|
|
||||||
</ol>
|
|
||||||
</section>
|
</section>
|
||||||
<section id="installation-and-setup">
|
<section id="installation-and-setup">
|
||||||
<h2>Installation and Setup<a class="headerlink" href="#installation-and-setup" title="Permalink to this heading">¶</a></h2>
|
<h2>Installation and Setup<a class="headerlink" href="#installation-and-setup" title="Permalink to this heading">¶</a></h2>
|
||||||
@@ -2817,11 +2821,197 @@ is working</p>
|
|||||||
</li>
|
</li>
|
||||||
<li><a class="reference internal" href="#troubleshooting">Troubleshooting</a></li>
|
<li><a class="reference internal" href="#troubleshooting">Troubleshooting</a></li>
|
||||||
<li><a class="reference internal" href="#code-documentation">Code Documentation</a><ul>
|
<li><a class="reference internal" href="#code-documentation">Code Documentation</a><ul>
|
||||||
<li><a class="reference internal" href="#module-app">AskNavidrome main</a></li>
|
<li><a class="reference internal" href="#module-app">AskNavidrome main</a><ul>
|
||||||
<li><a class="reference internal" href="#module-asknavidrome.controller">AskNavidrome controller</a></li>
|
<li><a class="reference internal" href="#app.CheckAudioInterfaceHandler"><code class="docutils literal notranslate"><span class="pre">CheckAudioInterfaceHandler</span></code></a><ul>
|
||||||
<li><a class="reference internal" href="#asknavidrome-media-queue">AskNavidrome media queue</a></li>
|
<li><a class="reference internal" href="#app.CheckAudioInterfaceHandler.can_handle"><code class="docutils literal notranslate"><span class="pre">CheckAudioInterfaceHandler.can_handle()</span></code></a></li>
|
||||||
<li><a class="reference internal" href="#asknavidrome-subsonic-api">AskNavidrome subsonic API</a></li>
|
<li><a class="reference internal" href="#app.CheckAudioInterfaceHandler.handle"><code class="docutils literal notranslate"><span class="pre">CheckAudioInterfaceHandler.handle()</span></code></a></li>
|
||||||
<li><a class="reference internal" href="#asknavidrome-track">AskNavidrome track</a></li>
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.GeneralExceptionHandler"><code class="docutils literal notranslate"><span class="pre">GeneralExceptionHandler</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.GeneralExceptionHandler.can_handle"><code class="docutils literal notranslate"><span class="pre">GeneralExceptionHandler.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.GeneralExceptionHandler.handle"><code class="docutils literal notranslate"><span class="pre">GeneralExceptionHandler.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.HelpHandler"><code class="docutils literal notranslate"><span class="pre">HelpHandler</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.HelpHandler.can_handle"><code class="docutils literal notranslate"><span class="pre">HelpHandler.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.HelpHandler.handle"><code class="docutils literal notranslate"><span class="pre">HelpHandler.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.LaunchRequestHandler"><code class="docutils literal notranslate"><span class="pre">LaunchRequestHandler</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.LaunchRequestHandler.can_handle"><code class="docutils literal notranslate"><span class="pre">LaunchRequestHandler.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.LaunchRequestHandler.handle"><code class="docutils literal notranslate"><span class="pre">LaunchRequestHandler.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.LoggingRequestInterceptor"><code class="docutils literal notranslate"><span class="pre">LoggingRequestInterceptor</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.LoggingRequestInterceptor.process"><code class="docutils literal notranslate"><span class="pre">LoggingRequestInterceptor.process()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.LoggingResponseInterceptor"><code class="docutils literal notranslate"><span class="pre">LoggingResponseInterceptor</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.LoggingResponseInterceptor.process"><code class="docutils literal notranslate"><span class="pre">LoggingResponseInterceptor.process()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlayAlbumByArtist"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlayAlbumByArtist</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlayAlbumByArtist.can_handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlayAlbumByArtist.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlayAlbumByArtist.handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlayAlbumByArtist.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlayFavouriteSongs"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlayFavouriteSongs</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlayFavouriteSongs.can_handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlayFavouriteSongs.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlayFavouriteSongs.handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlayFavouriteSongs.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlayMusicByArtist"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlayMusicByArtist</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlayMusicByArtist.can_handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlayMusicByArtist.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlayMusicByArtist.handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlayMusicByArtist.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlayMusicByGenre"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlayMusicByGenre</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlayMusicByGenre.can_handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlayMusicByGenre.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlayMusicByGenre.handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlayMusicByGenre.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlayMusicRandom"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlayMusicRandom</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlayMusicRandom.can_handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlayMusicRandom.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlayMusicRandom.handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlayMusicRandom.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlayPlaylist"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlayPlaylist</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlayPlaylist.can_handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlayPlaylist.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlayPlaylist.handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlayPlaylist.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlaySongByArtist"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlaySongByArtist</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlaySongByArtist.can_handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlaySongByArtist.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicPlaySongByArtist.handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicPlaySongByArtist.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicSongDetails"><code class="docutils literal notranslate"><span class="pre">NaviSonicSongDetails</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicSongDetails.can_handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicSongDetails.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicSongDetails.handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicSongDetails.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicStarSong"><code class="docutils literal notranslate"><span class="pre">NaviSonicStarSong</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicStarSong.can_handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicStarSong.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicStarSong.handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicStarSong.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicUnstarSong"><code class="docutils literal notranslate"><span class="pre">NaviSonicUnstarSong</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicUnstarSong.can_handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicUnstarSong.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.NaviSonicUnstarSong.handle"><code class="docutils literal notranslate"><span class="pre">NaviSonicUnstarSong.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.NextPlaybackHandler"><code class="docutils literal notranslate"><span class="pre">NextPlaybackHandler</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.NextPlaybackHandler.can_handle"><code class="docutils literal notranslate"><span class="pre">NextPlaybackHandler.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.NextPlaybackHandler.handle"><code class="docutils literal notranslate"><span class="pre">NextPlaybackHandler.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.PausePlaybackHandler"><code class="docutils literal notranslate"><span class="pre">PausePlaybackHandler</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.PausePlaybackHandler.can_handle"><code class="docutils literal notranslate"><span class="pre">PausePlaybackHandler.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.PausePlaybackHandler.handle"><code class="docutils literal notranslate"><span class="pre">PausePlaybackHandler.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.PlaybackFailedEventHandler"><code class="docutils literal notranslate"><span class="pre">PlaybackFailedEventHandler</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.PlaybackFailedEventHandler.can_handle"><code class="docutils literal notranslate"><span class="pre">PlaybackFailedEventHandler.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.PlaybackFailedEventHandler.handle"><code class="docutils literal notranslate"><span class="pre">PlaybackFailedEventHandler.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.PlaybackFinishedHandler"><code class="docutils literal notranslate"><span class="pre">PlaybackFinishedHandler</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.PlaybackFinishedHandler.can_handle"><code class="docutils literal notranslate"><span class="pre">PlaybackFinishedHandler.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.PlaybackFinishedHandler.handle"><code class="docutils literal notranslate"><span class="pre">PlaybackFinishedHandler.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.PlaybackNearlyFinishedHandler"><code class="docutils literal notranslate"><span class="pre">PlaybackNearlyFinishedHandler</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.PlaybackNearlyFinishedHandler.can_handle"><code class="docutils literal notranslate"><span class="pre">PlaybackNearlyFinishedHandler.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.PlaybackNearlyFinishedHandler.handle"><code class="docutils literal notranslate"><span class="pre">PlaybackNearlyFinishedHandler.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.PlaybackStartedHandler"><code class="docutils literal notranslate"><span class="pre">PlaybackStartedHandler</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.PlaybackStartedHandler.can_handle"><code class="docutils literal notranslate"><span class="pre">PlaybackStartedHandler.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.PlaybackStartedHandler.handle"><code class="docutils literal notranslate"><span class="pre">PlaybackStartedHandler.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.PlaybackStoppedHandler"><code class="docutils literal notranslate"><span class="pre">PlaybackStoppedHandler</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.PlaybackStoppedHandler.can_handle"><code class="docutils literal notranslate"><span class="pre">PlaybackStoppedHandler.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.PlaybackStoppedHandler.handle"><code class="docutils literal notranslate"><span class="pre">PlaybackStoppedHandler.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.PreviousPlaybackHandler"><code class="docutils literal notranslate"><span class="pre">PreviousPlaybackHandler</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.PreviousPlaybackHandler.can_handle"><code class="docutils literal notranslate"><span class="pre">PreviousPlaybackHandler.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.PreviousPlaybackHandler.handle"><code class="docutils literal notranslate"><span class="pre">PreviousPlaybackHandler.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.ResumePlaybackHandler"><code class="docutils literal notranslate"><span class="pre">ResumePlaybackHandler</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.ResumePlaybackHandler.can_handle"><code class="docutils literal notranslate"><span class="pre">ResumePlaybackHandler.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.ResumePlaybackHandler.handle"><code class="docutils literal notranslate"><span class="pre">ResumePlaybackHandler.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.SkillEventHandler"><code class="docutils literal notranslate"><span class="pre">SkillEventHandler</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.SkillEventHandler.can_handle"><code class="docutils literal notranslate"><span class="pre">SkillEventHandler.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.SkillEventHandler.handle"><code class="docutils literal notranslate"><span class="pre">SkillEventHandler.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.SystemExceptionHandler"><code class="docutils literal notranslate"><span class="pre">SystemExceptionHandler</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#app.SystemExceptionHandler.can_handle"><code class="docutils literal notranslate"><span class="pre">SystemExceptionHandler.can_handle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.SystemExceptionHandler.handle"><code class="docutils literal notranslate"><span class="pre">SystemExceptionHandler.handle()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#app.view_buffer"><code class="docutils literal notranslate"><span class="pre">view_buffer()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.view_history"><code class="docutils literal notranslate"><span class="pre">view_history()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#app.view_queue"><code class="docutils literal notranslate"><span class="pre">view_queue()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#module-asknavidrome.controller">AskNavidrome controller</a><ul>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.controller.add_screen_background"><code class="docutils literal notranslate"><span class="pre">add_screen_background()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.controller.enqueue_songs"><code class="docutils literal notranslate"><span class="pre">enqueue_songs()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.controller.start_playback"><code class="docutils literal notranslate"><span class="pre">start_playback()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.controller.stop"><code class="docutils literal notranslate"><span class="pre">stop()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome-media-queue">AskNavidrome media queue</a><ul>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.media_queue.MediaQueue"><code class="docutils literal notranslate"><span class="pre">MediaQueue</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.media_queue.MediaQueue.add_track"><code class="docutils literal notranslate"><span class="pre">MediaQueue.add_track()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.media_queue.MediaQueue.clear"><code class="docutils literal notranslate"><span class="pre">MediaQueue.clear()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.media_queue.MediaQueue.enqueue_next_track"><code class="docutils literal notranslate"><span class="pre">MediaQueue.enqueue_next_track()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.media_queue.MediaQueue.get_history_count"><code class="docutils literal notranslate"><span class="pre">MediaQueue.get_history_count()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.media_queue.MediaQueue.get_next_track"><code class="docutils literal notranslate"><span class="pre">MediaQueue.get_next_track()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.media_queue.MediaQueue.get_prevous_track"><code class="docutils literal notranslate"><span class="pre">MediaQueue.get_prevous_track()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.media_queue.MediaQueue.get_queue_count"><code class="docutils literal notranslate"><span class="pre">MediaQueue.get_queue_count()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.media_queue.MediaQueue.shuffle"><code class="docutils literal notranslate"><span class="pre">MediaQueue.shuffle()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.media_queue.MediaQueue.sync"><code class="docutils literal notranslate"><span class="pre">MediaQueue.sync()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.media_queue.MediaQueue.buffer"><code class="docutils literal notranslate"><span class="pre">MediaQueue.buffer</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.media_queue.MediaQueue.current_track"><code class="docutils literal notranslate"><span class="pre">MediaQueue.current_track</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.media_queue.MediaQueue.history"><code class="docutils literal notranslate"><span class="pre">MediaQueue.history</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.media_queue.MediaQueue.logger"><code class="docutils literal notranslate"><span class="pre">MediaQueue.logger</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.media_queue.MediaQueue.queue"><code class="docutils literal notranslate"><span class="pre">MediaQueue.queue</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome-subsonic-api">AskNavidrome subsonic API</a><ul>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.subsonic_api.SubsonicConnection"><code class="docutils literal notranslate"><span class="pre">SubsonicConnection</span></code></a><ul>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.subsonic_api.SubsonicConnection.albums_by_artist"><code class="docutils literal notranslate"><span class="pre">SubsonicConnection.albums_by_artist()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.subsonic_api.SubsonicConnection.build_random_song_list"><code class="docutils literal notranslate"><span class="pre">SubsonicConnection.build_random_song_list()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.subsonic_api.SubsonicConnection.build_song_list_from_albums"><code class="docutils literal notranslate"><span class="pre">SubsonicConnection.build_song_list_from_albums()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.subsonic_api.SubsonicConnection.build_song_list_from_favourites"><code class="docutils literal notranslate"><span class="pre">SubsonicConnection.build_song_list_from_favourites()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.subsonic_api.SubsonicConnection.build_song_list_from_genre"><code class="docutils literal notranslate"><span class="pre">SubsonicConnection.build_song_list_from_genre()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.subsonic_api.SubsonicConnection.build_song_list_from_playlist"><code class="docutils literal notranslate"><span class="pre">SubsonicConnection.build_song_list_from_playlist()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.subsonic_api.SubsonicConnection.get_song_details"><code class="docutils literal notranslate"><span class="pre">SubsonicConnection.get_song_details()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.subsonic_api.SubsonicConnection.get_song_uri"><code class="docutils literal notranslate"><span class="pre">SubsonicConnection.get_song_uri()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.subsonic_api.SubsonicConnection.ping"><code class="docutils literal notranslate"><span class="pre">SubsonicConnection.ping()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.subsonic_api.SubsonicConnection.search_album"><code class="docutils literal notranslate"><span class="pre">SubsonicConnection.search_album()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.subsonic_api.SubsonicConnection.search_artist"><code class="docutils literal notranslate"><span class="pre">SubsonicConnection.search_artist()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.subsonic_api.SubsonicConnection.search_playlist"><code class="docutils literal notranslate"><span class="pre">SubsonicConnection.search_playlist()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.subsonic_api.SubsonicConnection.search_song"><code class="docutils literal notranslate"><span class="pre">SubsonicConnection.search_song()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.subsonic_api.SubsonicConnection.star_entry"><code class="docutils literal notranslate"><span class="pre">SubsonicConnection.star_entry()</span></code></a></li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.subsonic_api.SubsonicConnection.unstar_entry"><code class="docutils literal notranslate"><span class="pre">SubsonicConnection.unstar_entry()</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome-track">AskNavidrome track</a><ul>
|
||||||
|
<li><a class="reference internal" href="#asknavidrome.track.Track"><code class="docutils literal notranslate"><span class="pre">Track</span></code></a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
</ul>
|
</ul>
|
||||||
</li>
|
</li>
|
||||||
</ul>
|
</ul>
|
||||||
@@ -2865,7 +3055,7 @@ is working</p>
|
|||||||
</div>
|
</div>
|
||||||
<div class="footer" role="contentinfo">
|
<div class="footer" role="contentinfo">
|
||||||
© Copyright 2022, Ross Stewart.
|
© Copyright 2022, Ross Stewart.
|
||||||
Created using <a href="https://www.sphinx-doc.org/">Sphinx</a> 5.1.1.
|
Created using <a href="https://www.sphinx-doc.org/">Sphinx</a> 5.3.0.
|
||||||
</div>
|
</div>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
@@ -15,6 +15,7 @@
|
|||||||
<script src="_static/underscore.js"></script>
|
<script src="_static/underscore.js"></script>
|
||||||
<script src="_static/_sphinx_javascript_frameworks_compat.js"></script>
|
<script src="_static/_sphinx_javascript_frameworks_compat.js"></script>
|
||||||
<script src="_static/doctools.js"></script>
|
<script src="_static/doctools.js"></script>
|
||||||
|
<script src="_static/sphinx_highlight.js"></script>
|
||||||
<link rel="index" title="Index" href="genindex.html" />
|
<link rel="index" title="Index" href="genindex.html" />
|
||||||
<link rel="search" title="Search" href="search.html" />
|
<link rel="search" title="Search" href="search.html" />
|
||||||
|
|
||||||
@@ -105,7 +106,7 @@
|
|||||||
</div>
|
</div>
|
||||||
<div class="footer" role="contentinfo">
|
<div class="footer" role="contentinfo">
|
||||||
© Copyright 2022, Ross Stewart.
|
© Copyright 2022, Ross Stewart.
|
||||||
Created using <a href="https://www.sphinx-doc.org/">Sphinx</a> 5.1.1.
|
Created using <a href="https://www.sphinx-doc.org/">Sphinx</a> 5.3.0.
|
||||||
</div>
|
</div>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
@@ -16,6 +16,7 @@
|
|||||||
<script src="_static/underscore.js"></script>
|
<script src="_static/underscore.js"></script>
|
||||||
<script src="_static/_sphinx_javascript_frameworks_compat.js"></script>
|
<script src="_static/_sphinx_javascript_frameworks_compat.js"></script>
|
||||||
<script src="_static/doctools.js"></script>
|
<script src="_static/doctools.js"></script>
|
||||||
|
<script src="_static/sphinx_highlight.js"></script>
|
||||||
<script src="_static/searchtools.js"></script>
|
<script src="_static/searchtools.js"></script>
|
||||||
<script src="_static/language_data.js"></script>
|
<script src="_static/language_data.js"></script>
|
||||||
<link rel="index" title="Index" href="genindex.html" />
|
<link rel="index" title="Index" href="genindex.html" />
|
||||||
@@ -99,7 +100,7 @@
|
|||||||
</div>
|
</div>
|
||||||
<div class="footer" role="contentinfo">
|
<div class="footer" role="contentinfo">
|
||||||
© Copyright 2022, Ross Stewart.
|
© Copyright 2022, Ross Stewart.
|
||||||
Created using <a href="https://www.sphinx-doc.org/">Sphinx</a> 5.1.1.
|
Created using <a href="https://www.sphinx-doc.org/">Sphinx</a> 5.3.0.
|
||||||
</div>
|
</div>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
File diff suppressed because one or more lines are too long
Reference in New Issue
Block a user