Upgrade web assets (#219)
* Update assets * Upgrade linting and other improvments * Correct linting * Correction and type check improvements * Correct type check lib * Fix lint pathing for VSCode * Remove duplicate babel config * Remove editorconfig root attribute from web subdir * Use double quotes around message * Simplify ESLint config * Update web assets * Allow AMD loader in WebPack * Bump web dependencies * Only include FA icons in-use
This commit is contained in:
parent
c79d4cf977
commit
ff5b1cb1ee
@ -28,7 +28,7 @@ certificate =
|
|||||||
|
|
||||||
[bot]
|
[bot]
|
||||||
username = botamusique
|
username = botamusique
|
||||||
comment = Hi, I'm here to play radio, local music or youtube/soundcloud music. Have fun!
|
comment = "Hi, I'm here to play radio, local music or youtube/soundcloud music. Have fun!"
|
||||||
# default volume from 0 to 1.
|
# default volume from 0 to 1.
|
||||||
volume = 0.1
|
volume = 0.1
|
||||||
stereo = True
|
stereo = True
|
||||||
@ -126,10 +126,10 @@ jazz = http://jazz-wr04.ice.infomaniak.ch/jazz-wr04-128.mp3 "Jazz Yeah !"
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
# ========================================================
|
# =========================================================
|
||||||
# WARNING: WE DO NOT SUGGEST YOU MODIFY THE FOLLOWING
|
# WARNING: WE DO NOT SUGGEST YOU MODIFY THE FOLLOWING
|
||||||
# PARTS, EXCEPT YOU KNOW WHAT YOU ARE DOING.
|
# PARTS, EXCEPT IF YOU KNOW WHAT YOU ARE DOING.
|
||||||
# ========================================================
|
# =========================================================
|
||||||
[commands]
|
[commands]
|
||||||
# This is a list of characters the bot recognizes as command prefix.
|
# This is a list of characters the bot recognizes as command prefix.
|
||||||
command_symbol = !:!
|
command_symbol = !:!
|
||||||
|
@ -22,7 +22,7 @@ port = 64738
|
|||||||
# 'username' is the user name of the bot.
|
# 'username' is the user name of the bot.
|
||||||
# 'comment' is the comment displayed by the bot.
|
# 'comment' is the comment displayed by the bot.
|
||||||
#username = botamusique
|
#username = botamusique
|
||||||
#comment = Hi, I'm here to play radio, local music or youtube/soundcloud music. Have fun!
|
#comment = "Hi, I'm here to play radio, local music or youtube/soundcloud music. Have fun!"
|
||||||
|
|
||||||
# 'language': Available languages can be found inside lang/ folder.
|
# 'language': Available languages can be found inside lang/ folder.
|
||||||
#language=en_US
|
#language=en_US
|
||||||
|
@ -1,5 +1,3 @@
|
|||||||
root = true
|
|
||||||
|
|
||||||
[*]
|
[*]
|
||||||
charset = utf-8
|
charset = utf-8
|
||||||
insert_final_newline = true
|
insert_final_newline = true
|
||||||
|
@ -1,38 +1,40 @@
|
|||||||
{
|
{
|
||||||
|
"parser": "@babel/eslint-parser",
|
||||||
"env": {
|
"env": {
|
||||||
"browser": true,
|
"browser": true,
|
||||||
"es6": true,
|
"es6": true,
|
||||||
"es2017": true,
|
"es2017": true,
|
||||||
"es2020": true,
|
"es2020": true,
|
||||||
|
"es2021": true,
|
||||||
"jquery": true
|
"jquery": true
|
||||||
},
|
},
|
||||||
"plugins": [
|
"plugins": [
|
||||||
"node",
|
"@babel",
|
||||||
"import",
|
"import",
|
||||||
"jsdoc"
|
"jsdoc",
|
||||||
|
"jquery"
|
||||||
],
|
],
|
||||||
"extends": [
|
"extends": [
|
||||||
"eslint:recommended",
|
"eslint:recommended",
|
||||||
"google",
|
|
||||||
"plugin:node/recommended-module",
|
|
||||||
"plugin:import/errors",
|
"plugin:import/errors",
|
||||||
"plugin:import/warnings",
|
"plugin:import/warnings",
|
||||||
"plugin:jsdoc/recommended"
|
"plugin:jsdoc/recommended",
|
||||||
|
"plugin:jquery/deprecated"
|
||||||
],
|
],
|
||||||
"globals": {
|
|
||||||
"Atomics": "readonly",
|
|
||||||
"SharedArrayBuffer": "readonly"
|
|
||||||
},
|
|
||||||
"parser": "babel-eslint",
|
|
||||||
"rules": {
|
"rules": {
|
||||||
"require-jsdoc": "off",
|
|
||||||
"valid-jsdoc": "off",
|
|
||||||
"jsdoc/require-jsdoc": "off",
|
|
||||||
"max-len": ["warn", {
|
"max-len": ["warn", {
|
||||||
"code": 120
|
"code": 120
|
||||||
}],
|
}],
|
||||||
|
"linebreak-style": "off",
|
||||||
|
"jsdoc/require-jsdoc": "off",
|
||||||
|
"import/unambiguous": "error",
|
||||||
"import/no-commonjs": "error",
|
"import/no-commonjs": "error",
|
||||||
"import/no-amd": "error",
|
"import/no-amd": "error",
|
||||||
"linebreak-style": "off"
|
"import/no-nodejs-modules": "error",
|
||||||
|
"import/no-deprecated": "error",
|
||||||
|
"import/extensions": ["error", "always"],
|
||||||
|
"import/no-unresolved": ["error", {
|
||||||
|
"commonjs": true
|
||||||
|
}]
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
1
web/.gitattributes
vendored
Normal file
1
web/.gitattributes
vendored
Normal file
@ -0,0 +1 @@
|
|||||||
|
package-lock.json text eol=lf
|
3
web/.gitignore
vendored
3
web/.gitignore
vendored
@ -1 +1,2 @@
|
|||||||
node_modules/
|
!*
|
||||||
|
node_modules/
|
||||||
|
5
web/babel.config.json
Normal file
5
web/babel.config.json
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
{
|
||||||
|
"plugins": [
|
||||||
|
"@babel/plugin-proposal-class-properties"
|
||||||
|
]
|
||||||
|
}
|
@ -1,13 +1,23 @@
|
|||||||
import {library, dom} from '@fortawesome/fontawesome-svg-core/index.es';
|
import {library, dom} from '@fortawesome/fontawesome-svg-core/index.es.js';
|
||||||
import {fas} from '@fortawesome/free-solid-svg-icons/index.es';
|
import {
|
||||||
import {far} from '@fortawesome/free-regular-svg-icons/index.es';
|
faTimesCircle, faPlus, faCheck, faUpload, faTimes, faTrash, faPlay, faPause, faFastForward, faPlayCircle, faLightbulb,
|
||||||
library.add(fas, far);
|
faTrashAlt, faDownload, faSyncAlt, faEdit, faVolumeUp, faVolumeDown, faRobot, faRedo, faRandom, faTasks
|
||||||
|
} from '@fortawesome/free-solid-svg-icons/index.es.js';
|
||||||
|
import {faFileAlt} from '@fortawesome/free-regular-svg-icons/index.es.js';
|
||||||
|
|
||||||
|
library.add(
|
||||||
|
// Solid
|
||||||
|
faTimesCircle, faPlus, faCheck, faUpload, faTimes, faTrash, faPlay, faPause, faFastForward, faPlayCircle, faLightbulb,
|
||||||
|
faTrashAlt, faDownload, faSyncAlt, faEdit, faVolumeUp, faVolumeDown, faRobot, faRedo, faRandom, faTasks,
|
||||||
|
// Regular
|
||||||
|
faFileAlt
|
||||||
|
);
|
||||||
|
|
||||||
// Old application code
|
// Old application code
|
||||||
import './main.mjs';
|
import './main.mjs';
|
||||||
|
|
||||||
// New application code
|
// New application code
|
||||||
import Theme from './theme.mjs';
|
import Theme from './lib/theme.mjs';
|
||||||
|
|
||||||
document.addEventListener('DOMContentLoaded', () => {
|
document.addEventListener('DOMContentLoaded', () => {
|
||||||
Theme.init();
|
Theme.init();
|
||||||
|
42
web/js/lib/text.mjs
Normal file
42
web/js/lib/text.mjs
Normal file
@ -0,0 +1,42 @@
|
|||||||
|
import {validateString, validateNumber} from './type.mjs';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Truncate string length by characters.
|
||||||
|
*
|
||||||
|
* @param {string} text String to format.
|
||||||
|
* @param {number} limit Maximum number of characters in resulting string.
|
||||||
|
* @param {string} ending Ending to use if string is trucated.
|
||||||
|
*
|
||||||
|
* @returns {string} Formatted string.
|
||||||
|
*/
|
||||||
|
export function limitChars(text, limit = 50, ending = '...') {
|
||||||
|
validateString(text);
|
||||||
|
validateNumber(limit);
|
||||||
|
validateString(ending);
|
||||||
|
|
||||||
|
// Check if string is already below limit
|
||||||
|
if (text.length <= limit) {
|
||||||
|
return text;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Limit string length by characters
|
||||||
|
return text.substring(0, limit - ending.length) + ending;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Truncate string length by words.
|
||||||
|
*
|
||||||
|
* @param {string} text String to format.
|
||||||
|
* @param {number} limit Maximum number of words in resulting string.
|
||||||
|
* @param {string} ending Ending to use if string is trucated.
|
||||||
|
*
|
||||||
|
* @returns {string} Formatted string.
|
||||||
|
*/
|
||||||
|
export function limitWords(text, limit = 10, ending = '...') {
|
||||||
|
validateString(text);
|
||||||
|
validateNumber(limit);
|
||||||
|
validateString(ending);
|
||||||
|
|
||||||
|
// Limit string length by words
|
||||||
|
return text.split(' ').splice(0, limit).join(' ') + ending;
|
||||||
|
}
|
@ -1,6 +1,6 @@
|
|||||||
export default class {
|
export default class {
|
||||||
/**
|
/**
|
||||||
* @property {boolean} #dark Interal state for dark theme activation.
|
* @property {boolean} dark Interal state for dark theme activation.
|
||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
static #dark = false;
|
static #dark = false;
|
65
web/js/lib/type.mjs
Normal file
65
web/js/lib/type.mjs
Normal file
@ -0,0 +1,65 @@
|
|||||||
|
/**
|
||||||
|
* Checks if `value` is the type `Object` excluding `Function` and `null`
|
||||||
|
*
|
||||||
|
* @param {*} value The value to check.
|
||||||
|
* @returns {boolean} Returns `true` if `value` is an object, otherwise `false`.
|
||||||
|
*/
|
||||||
|
export function isObject(value) {
|
||||||
|
return (Object.prototype.toString.call(value) === '[object Object]');
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Checks if `value` is the type `string`
|
||||||
|
*
|
||||||
|
* @param {*} value The value to check.
|
||||||
|
* @returns {boolean} Returns `true` if `value` is a string, otherwise `false`.
|
||||||
|
*/
|
||||||
|
export function isString(value) {
|
||||||
|
return (typeof value === 'string');
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Checks if `value` is the type `number`
|
||||||
|
*
|
||||||
|
* @param {*} value The value to check.
|
||||||
|
* @returns {boolean} Returns `true` if `value` is a number, otherwise `false`.
|
||||||
|
*/
|
||||||
|
export function isNumber(value) {
|
||||||
|
return (typeof value === 'number');
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Validate parameter is of type object.
|
||||||
|
*
|
||||||
|
* @param {string} value Variable to validate.
|
||||||
|
* @throws Error if not an object.
|
||||||
|
*/
|
||||||
|
export function validateObject(value) {
|
||||||
|
if (!isObject(value)) {
|
||||||
|
throw new TypeError('Parameter "value" must be of type object.');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Validate parameter is of type string.
|
||||||
|
*
|
||||||
|
* @param {string} value Variable to validate.
|
||||||
|
* @throws Error if not an string.
|
||||||
|
*/
|
||||||
|
export function validateString(value) {
|
||||||
|
if (!isString(value)) {
|
||||||
|
throw new TypeError('Parameter "value" must be of type string.');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Validate parameter is of type number.
|
||||||
|
*
|
||||||
|
* @param {number} value Variable to validate.
|
||||||
|
* @throws Error if not an number.
|
||||||
|
*/
|
||||||
|
export function validateNumber(value) {
|
||||||
|
if (!isNumber(value)) {
|
||||||
|
throw new TypeError('Parameter "value" must be of type number.');
|
||||||
|
}
|
||||||
|
}
|
@ -3,13 +3,13 @@ export function isOverflown(element) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export function hash(string) {
|
export function hash(string) {
|
||||||
if (typeof string != "string") return 0;
|
if (typeof string != 'string') return 0;
|
||||||
let hash = 0;
|
let hash = 0;
|
||||||
if (string.length === 0) {
|
if (string.length === 0) {
|
||||||
return hash;
|
return hash;
|
||||||
}
|
}
|
||||||
for (let i = 0; i < string.length; i++) {
|
for (let i = 0; i < string.length; i++) {
|
||||||
let char = string.charCodeAt(i);
|
const char = string.charCodeAt(i);
|
||||||
hash = ((hash<<5)-hash)+char;
|
hash = ((hash<<5)-hash)+char;
|
||||||
hash = hash & hash; // Convert to 32bit integer
|
hash = hash & hash; // Convert to 32bit integer
|
||||||
}
|
}
|
||||||
@ -17,24 +17,25 @@ export function hash(string) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export function getColor(string) {
|
export function getColor(string) {
|
||||||
let num = hash(string) % 8;
|
const num = hash(string) % 8;
|
||||||
switch(num) {
|
|
||||||
|
switch (num) {
|
||||||
case 0:
|
case 0:
|
||||||
return "primary";
|
return 'primary';
|
||||||
case 1:
|
case 1:
|
||||||
return "secondary";
|
return 'secondary';
|
||||||
case 2:
|
case 2:
|
||||||
return "success";
|
return 'success';
|
||||||
case 3:
|
case 3:
|
||||||
return "danger";
|
return 'danger';
|
||||||
case 4:
|
case 4:
|
||||||
return "warning";
|
return 'warning';
|
||||||
case 5:
|
case 5:
|
||||||
return "info";
|
return 'info';
|
||||||
case 6:
|
case 6:
|
||||||
return "light";
|
return 'light';
|
||||||
case 7:
|
case 7:
|
||||||
return "dark";
|
return 'dark';
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -52,20 +53,3 @@ export function secondsToStr(seconds) {
|
|||||||
const secs = seconds % 60;
|
const secs = seconds % 60;
|
||||||
return ('00' + mins).slice(-2) + ':' + ('00' + secs).slice(-2);
|
return ('00' + mins).slice(-2) + ':' + ('00' + secs).slice(-2);
|
||||||
}
|
}
|
||||||
|
|
||||||
export function coverArtString(title) {
|
|
||||||
|
|
||||||
let nameOfSong = "";
|
|
||||||
// The maximum length before we start truncating
|
|
||||||
const maxLength = 50;
|
|
||||||
|
|
||||||
if (title.length > maxLength) {
|
|
||||||
// Name = longTitleTooLongToBeAGoodAltTex...
|
|
||||||
nameOfSong = title.substr(0, maxLength) + "\u2026";
|
|
||||||
} else {
|
|
||||||
// Name = shortTitle
|
|
||||||
nameOfSong = title;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 'Cover art for ' + nameOfSong;
|
|
||||||
}
|
|
292
web/js/main.mjs
292
web/js/main.mjs
@ -1,20 +1,20 @@
|
|||||||
import 'jquery/src/jquery';
|
import 'jquery/src/jquery.js';
|
||||||
import 'jquery-migrate/src/migrate';
|
import 'jquery-migrate/src/migrate.js';
|
||||||
import Popper from 'popper.js/dist/esm/popper';
|
import Popper from 'popper.js/dist/esm/popper.js';
|
||||||
import {
|
import {
|
||||||
Modal,
|
Modal,
|
||||||
Toast,
|
Toast,
|
||||||
Tooltip,
|
Tooltip,
|
||||||
} from 'bootstrap/js/src/index';
|
} from 'bootstrap/js/src/index.js';
|
||||||
import {
|
import {
|
||||||
getColor,
|
getColor,
|
||||||
isOverflown,
|
isOverflown,
|
||||||
setProgressBar,
|
setProgressBar,
|
||||||
secondsToStr,
|
secondsToStr,
|
||||||
coverArtString,
|
} from './lib/util.mjs';
|
||||||
} from './util';
|
import {limitChars} from './lib/text.mjs';
|
||||||
|
|
||||||
$('#uploadSelectFile').on('change', function () {
|
$('#uploadSelectFile').on('change', function() {
|
||||||
// get the file name
|
// get the file name
|
||||||
const fileName = $(this).val().replace('C:\\fakepath\\', ' ');
|
const fileName = $(this).val().replace('C:\\fakepath\\', ' ');
|
||||||
// replace the "Choose a file" label
|
// replace the "Choose a file" label
|
||||||
@ -85,7 +85,7 @@ fastForwardBtn.on('click', () => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
document.getElementById('clear-playlist-btn').addEventListener('click', () => {
|
document.getElementById('clear-playlist-btn').addEventListener('click', () => {
|
||||||
request('post', { action: 'clear' });
|
request('post', {action: 'clear'});
|
||||||
});
|
});
|
||||||
|
|
||||||
// eslint-disable-next-line guard-for-in
|
// eslint-disable-next-line guard-for-in
|
||||||
@ -102,14 +102,14 @@ function request(_url, _data, refresh = false) {
|
|||||||
url: _url,
|
url: _url,
|
||||||
data: _data,
|
data: _data,
|
||||||
statusCode: {
|
statusCode: {
|
||||||
200: function (data) {
|
200: function(data) {
|
||||||
if (data.ver !== playlist_ver) {
|
if (data.ver !== playlist_ver) {
|
||||||
checkForPlaylistUpdate();
|
checkForPlaylistUpdate();
|
||||||
}
|
}
|
||||||
updateControls(data.empty, data.play, data.mode, data.volume);
|
updateControls(data.empty, data.play, data.mode, data.volume);
|
||||||
updatePlayerPlayhead(data.playhead);
|
updatePlayerPlayhead(data.playhead);
|
||||||
},
|
},
|
||||||
403: function () {
|
403: function() {
|
||||||
location.reload(true);
|
location.reload(true);
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
@ -125,7 +125,7 @@ function addPlaylistItem(item) {
|
|||||||
pl_title_element.html(item.title);
|
pl_title_element.html(item.title);
|
||||||
pl_artist_element.html(item.artist);
|
pl_artist_element.html(item.artist);
|
||||||
pl_thumb_element.attr('src', item.thumbnail);
|
pl_thumb_element.attr('src', item.thumbnail);
|
||||||
pl_thumb_element.attr('alt', coverArtString(item.title));
|
pl_thumb_element.attr('alt', limitChars(item.title));
|
||||||
pl_type_element.html(item.type);
|
pl_type_element.html(item.type);
|
||||||
pl_path_element.html(item.path);
|
pl_path_element.html(item.path);
|
||||||
|
|
||||||
@ -137,13 +137,13 @@ function addPlaylistItem(item) {
|
|||||||
tags.empty();
|
tags.empty();
|
||||||
|
|
||||||
const tag_edit_copy = pl_tag_edit_element.clone();
|
const tag_edit_copy = pl_tag_edit_element.clone();
|
||||||
tag_edit_copy.click(function () {
|
tag_edit_copy.click(function() {
|
||||||
addTagModalShow(item.id, item.title, item.tags);
|
addTagModalShow(item.id, item.title, item.tags);
|
||||||
});
|
});
|
||||||
tag_edit_copy.appendTo(tags);
|
tag_edit_copy.appendTo(tags);
|
||||||
|
|
||||||
if (item.tags.length > 0) {
|
if (item.tags.length > 0) {
|
||||||
item.tags.forEach(function (tag_tuple) {
|
item.tags.forEach(function(tag_tuple) {
|
||||||
const tag_copy = tag_element.clone();
|
const tag_copy = tag_element.clone();
|
||||||
tag_copy.html(tag_tuple[0]);
|
tag_copy.html(tag_tuple[0]);
|
||||||
tag_copy.addClass('badge-' + tag_tuple[1]);
|
tag_copy.addClass('badge-' + tag_tuple[1]);
|
||||||
@ -160,14 +160,14 @@ function addPlaylistItem(item) {
|
|||||||
function displayPlaylist(data) {
|
function displayPlaylist(data) {
|
||||||
playlist_table.animate({
|
playlist_table.animate({
|
||||||
opacity: 0,
|
opacity: 0,
|
||||||
}, 200, function () {
|
}, 200, function() {
|
||||||
playlist_loading.hide();
|
playlist_loading.hide();
|
||||||
$('.playlist-item').remove();
|
$('.playlist-item').remove();
|
||||||
const items = data.items;
|
const items = data.items;
|
||||||
const length = data.length;
|
const length = data.length;
|
||||||
if (items.length === 0){
|
if (items.length === 0) {
|
||||||
playlist_empty.removeClass('d-none');
|
playlist_empty.removeClass('d-none');
|
||||||
playlist_table.animate({ opacity: 1 }, 200);
|
playlist_table.animate({opacity: 1}, 200);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
playlist_items = {};
|
playlist_items = {};
|
||||||
@ -188,9 +188,9 @@ function displayPlaylist(data) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
items.forEach(
|
items.forEach(
|
||||||
function (item) {
|
function(item) {
|
||||||
addPlaylistItem(item);
|
addPlaylistItem(item);
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|
||||||
if (items.length < length && start_from + items.length < length) {
|
if (items.length < length && start_from + items.length < length) {
|
||||||
@ -205,7 +205,7 @@ function displayPlaylist(data) {
|
|||||||
displayActiveItem(data.current_index);
|
displayActiveItem(data.current_index);
|
||||||
updatePlayerInfo(playlist_items[data.current_index]);
|
updatePlayerInfo(playlist_items[data.current_index]);
|
||||||
bindPlaylistEvent();
|
bindPlaylistEvent();
|
||||||
playlist_table.animate({ opacity: 1 }, 200);
|
playlist_table.animate({opacity: 1}, 200);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -227,7 +227,7 @@ function insertExpandPrompt(real_from, real_to, display_from, display_to, total_
|
|||||||
|
|
||||||
expand_copy.addClass('playlist-item');
|
expand_copy.addClass('playlist-item');
|
||||||
expand_copy.appendTo(playlist_table);
|
expand_copy.appendTo(playlist_table);
|
||||||
expand_copy.click(function () {
|
expand_copy.click(function() {
|
||||||
playlist_range_from = real_from;
|
playlist_range_from = real_from;
|
||||||
playlist_range_to = real_to;
|
playlist_range_to = real_to;
|
||||||
updatePlaylist();
|
updatePlaylist();
|
||||||
@ -237,7 +237,7 @@ function insertExpandPrompt(real_from, real_to, display_from, display_to, total_
|
|||||||
function updatePlaylist() {
|
function updatePlaylist() {
|
||||||
playlist_table.animate({
|
playlist_table.animate({
|
||||||
opacity: 0,
|
opacity: 0,
|
||||||
}, 200, function () {
|
}, 200, function() {
|
||||||
playlist_empty.addClass('d-none');
|
playlist_empty.addClass('d-none');
|
||||||
playlist_loading.show();
|
playlist_loading.show();
|
||||||
playlist_table.find('.playlist-item').css('opacity', 0);
|
playlist_table.find('.playlist-item').css('opacity', 0);
|
||||||
@ -267,7 +267,7 @@ function checkForPlaylistUpdate() {
|
|||||||
type: 'POST',
|
type: 'POST',
|
||||||
url: 'post',
|
url: 'post',
|
||||||
statusCode: {
|
statusCode: {
|
||||||
200: function (data) {
|
200: function(data) {
|
||||||
if (data.ver !== playlist_ver) {
|
if (data.ver !== playlist_ver) {
|
||||||
playlist_ver = data.ver;
|
playlist_ver = data.ver;
|
||||||
playlist_range_from = 0;
|
playlist_range_from = 0;
|
||||||
@ -298,18 +298,18 @@ function checkForPlaylistUpdate() {
|
|||||||
|
|
||||||
function bindPlaylistEvent() {
|
function bindPlaylistEvent() {
|
||||||
$('.playlist-item-play').unbind().click(
|
$('.playlist-item-play').unbind().click(
|
||||||
function (e) {
|
function(e) {
|
||||||
request('post', {
|
request('post', {
|
||||||
'play_music': ($(e.currentTarget).parent().parent().parent().find('.playlist-item-index').html() - 1),
|
'play_music': ($(e.currentTarget).parent().parent().parent().find('.playlist-item-index').html() - 1),
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
$('.playlist-item-trash').unbind().click(
|
$('.playlist-item-trash').unbind().click(
|
||||||
function (e) {
|
function(e) {
|
||||||
request('post', {
|
request('post', {
|
||||||
'delete_music': ($(e.currentTarget).parent().parent().parent().find('.playlist-item-index').html() - 1),
|
'delete_music': ($(e.currentTarget).parent().parent().parent().find('.playlist-item-index').html() - 1),
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -416,10 +416,10 @@ function setFilterType(event, type) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
filter_dir.change(function () {
|
filter_dir.change(function() {
|
||||||
updateResults();
|
updateResults();
|
||||||
});
|
});
|
||||||
filter_keywords.change(function () {
|
filter_keywords.change(function() {
|
||||||
updateResults();
|
updateResults();
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -427,69 +427,69 @@ const item_template = $('#library-item');
|
|||||||
|
|
||||||
function bindLibraryResultEvent() {
|
function bindLibraryResultEvent() {
|
||||||
$('.library-thumb-col').unbind().hover(
|
$('.library-thumb-col').unbind().hover(
|
||||||
function (e) {
|
function(e) {
|
||||||
$(e.currentTarget).find('.library-thumb-grp').addClass('library-thumb-grp-hover');
|
$(e.currentTarget).find('.library-thumb-grp').addClass('library-thumb-grp-hover');
|
||||||
},
|
},
|
||||||
function (e) {
|
function(e) {
|
||||||
$(e.currentTarget).find('.library-thumb-grp').removeClass('library-thumb-grp-hover');
|
$(e.currentTarget).find('.library-thumb-grp').removeClass('library-thumb-grp-hover');
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|
||||||
$('.library-info-title').unbind().hover(
|
$('.library-info-title').unbind().hover(
|
||||||
function (e) {
|
function(e) {
|
||||||
$(e.currentTarget).parent().find('.library-thumb-grp').addClass('library-thumb-grp-hover');
|
$(e.currentTarget).parent().find('.library-thumb-grp').addClass('library-thumb-grp-hover');
|
||||||
},
|
},
|
||||||
function (e) {
|
function(e) {
|
||||||
$(e.currentTarget).parent().find('.library-thumb-grp').removeClass('library-thumb-grp-hover');
|
$(e.currentTarget).parent().find('.library-thumb-grp').removeClass('library-thumb-grp-hover');
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|
||||||
$('.library-item-play').unbind().click(
|
$('.library-item-play').unbind().click(
|
||||||
function (e) {
|
function(e) {
|
||||||
request('post', {
|
request('post', {
|
||||||
'add_item_at_once': $(e.currentTarget).parent().parent().parent().find('.library-item-id').val(),
|
'add_item_at_once': $(e.currentTarget).parent().parent().parent().find('.library-item-id').val(),
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|
||||||
$('.library-item-trash').unbind().click(
|
$('.library-item-trash').unbind().click(
|
||||||
function (e) {
|
function(e) {
|
||||||
request('post', {
|
request('post', {
|
||||||
'delete_item_from_library': $(e.currentTarget).parent().parent().find('.library-item-id').val(),
|
'delete_item_from_library': $(e.currentTarget).parent().parent().find('.library-item-id').val(),
|
||||||
});
|
});
|
||||||
updateResults(active_page);
|
updateResults(active_page);
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|
||||||
$('.library-item-download').unbind().click(
|
$('.library-item-download').unbind().click(
|
||||||
function (e) {
|
function(e) {
|
||||||
const id = $(e.currentTarget).parent().parent().find('.library-item-id').val();
|
const id = $(e.currentTarget).parent().parent().find('.library-item-id').val();
|
||||||
// window.open('/download?id=' + id);
|
// window.open('/download?id=' + id);
|
||||||
downloadId(id);
|
downloadId(id);
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|
||||||
$('.library-item-add-next').unbind().click(
|
$('.library-item-add-next').unbind().click(
|
||||||
function (e) {
|
function(e) {
|
||||||
const id = $(e.currentTarget).parent().parent().find('.library-item-id').val();
|
const id = $(e.currentTarget).parent().parent().find('.library-item-id').val();
|
||||||
request('post', {
|
request('post', {
|
||||||
'add_item_next': id,
|
'add_item_next': id,
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|
||||||
$('.library-item-add-bottom').unbind().click(
|
$('.library-item-add-bottom').unbind().click(
|
||||||
function (e) {
|
function(e) {
|
||||||
const id = $(e.currentTarget).parent().parent().find('.library-item-id').val();
|
const id = $(e.currentTarget).parent().parent().find('.library-item-id').val();
|
||||||
request('post', {
|
request('post', {
|
||||||
'add_item_bottom': id,
|
'add_item_bottom': id,
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
const lib_filter_tag_group = $("#filter-tags");
|
const lib_filter_tag_group = $('#filter-tags');
|
||||||
const lib_filter_tag_element = $(".filter-tag");
|
const lib_filter_tag_element = $('.filter-tag');
|
||||||
|
|
||||||
const lib_group = $('#library-group');
|
const lib_group = $('#library-group');
|
||||||
const id_element = $('.library-item-id');
|
const id_element = $('.library-item-id');
|
||||||
@ -503,62 +503,62 @@ const tag_edit_element = $('.library-item-edit');
|
|||||||
// var notag_element = $(".library-item-notag");
|
// var notag_element = $(".library-item-notag");
|
||||||
// var tag_element = $(".library-item-tag");
|
// var tag_element = $(".library-item-tag");
|
||||||
|
|
||||||
let library_tags = [];
|
const library_tags = [];
|
||||||
|
|
||||||
function updateLibraryControls(){
|
function updateLibraryControls() {
|
||||||
$.ajax({
|
$.ajax({
|
||||||
type: 'GET',
|
type: 'GET',
|
||||||
url: 'library/info',
|
url: 'library/info',
|
||||||
statusCode: {
|
statusCode: {
|
||||||
200: displayLibraryControls,
|
200: displayLibraryControls,
|
||||||
403: function () {
|
403: function() {
|
||||||
location.reload(true);
|
location.reload(true);
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
function displayLibraryControls(data){
|
function displayLibraryControls(data) {
|
||||||
$("#maxUploadFileSize").val(data.max_upload_file_size);
|
$('#maxUploadFileSize').val(data.max_upload_file_size);
|
||||||
if (data.upload_enabled) {
|
if (data.upload_enabled) {
|
||||||
$("#uploadDisabled").val("false");
|
$('#uploadDisabled').val('false');
|
||||||
$("#upload").show();
|
$('#upload').show();
|
||||||
} else {
|
} else {
|
||||||
$("#uploadDisabled").val("true");
|
$('#uploadDisabled').val('true');
|
||||||
$("#upload").hide();
|
$('#upload').hide();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (data.delete_allowed) {
|
if (data.delete_allowed) {
|
||||||
$("#deleteAllowed").val("true");
|
$('#deleteAllowed').val('true');
|
||||||
$(".library-delete").show();
|
$('.library-delete').show();
|
||||||
} else {
|
} else {
|
||||||
$("#uploadDisabled").val("false");
|
$('#uploadDisabled').val('false');
|
||||||
$(".library-delete").hide();
|
$('.library-delete').hide();
|
||||||
}
|
}
|
||||||
|
|
||||||
let select = $("#filter-dir");
|
const select = $('#filter-dir');
|
||||||
let dataList = $("#upload-target-dirs");
|
const dataList = $('#upload-target-dirs');
|
||||||
select.find("option").remove();
|
select.find('option').remove();
|
||||||
dataList.find("option").remove();
|
dataList.find('option').remove();
|
||||||
if (data.dirs.length > 0) {
|
if (data.dirs.length > 0) {
|
||||||
console.log(data.dirs);
|
console.log(data.dirs);
|
||||||
data.dirs.forEach(function (dir) {
|
data.dirs.forEach(function(dir) {
|
||||||
$("<option value=\"" + dir + "\">" + dir + "</option>").appendTo(select);
|
$('<option value="' + dir + '">' + dir + '</option>').appendTo(select);
|
||||||
$("<option value=\"" + dir + "\">").appendTo(dataList);
|
$('<option value="' + dir + '">').appendTo(dataList);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
// ----- Tag filters -----
|
// ----- Tag filters -----
|
||||||
let tags = [];
|
const tags = [];
|
||||||
let tags_dict = {};
|
const tags_dict = {};
|
||||||
$(".filter-tag").each(function(i, tag_element){
|
$('.filter-tag').each(function(i, tag_element) {
|
||||||
tags_dict[tag_element.innerHTML] = tag_element;
|
tags_dict[tag_element.innerHTML] = tag_element;
|
||||||
tags.push(tag_element.innerHTML);
|
tags.push(tag_element.innerHTML);
|
||||||
});
|
});
|
||||||
if (data.tags.length > 0) {
|
if (data.tags.length > 0) {
|
||||||
for (const tag of data.tags){
|
for (const tag of data.tags) {
|
||||||
if (tags.includes(tag)){
|
if (tags.includes(tag)) {
|
||||||
let index = tags.indexOf(tag);
|
const index = tags.indexOf(tag);
|
||||||
tags.splice(index, 1);
|
tags.splice(index, 1);
|
||||||
} else {
|
} else {
|
||||||
const tag_copy = lib_filter_tag_element.clone();
|
const tag_copy = lib_filter_tag_element.clone();
|
||||||
@ -566,7 +566,7 @@ function displayLibraryControls(data){
|
|||||||
tag_copy.addClass('badge-' + getColor(tag));
|
tag_copy.addClass('badge-' + getColor(tag));
|
||||||
tag_copy.appendTo(lib_filter_tag_group);
|
tag_copy.appendTo(lib_filter_tag_group);
|
||||||
// Bind Event
|
// Bind Event
|
||||||
tag_copy.click(function (e) {
|
tag_copy.click(function(e) {
|
||||||
const tag = $(e.currentTarget);
|
const tag = $(e.currentTarget);
|
||||||
if (!tag.hasClass('tag-clicked')) {
|
if (!tag.hasClass('tag-clicked')) {
|
||||||
tag.addClass('tag-clicked');
|
tag.addClass('tag-clicked');
|
||||||
@ -583,7 +583,7 @@ function displayLibraryControls(data){
|
|||||||
tags_dict[tag].remove();
|
tags_dict[tag].remove();
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
$(".filter-tag").remove();
|
$('.filter-tag').remove();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -592,7 +592,7 @@ function addResultItem(item) {
|
|||||||
title_element.html(item.title);
|
title_element.html(item.title);
|
||||||
artist_element.html(item.artist ? ('- ' + item.artist) : '');
|
artist_element.html(item.artist ? ('- ' + item.artist) : '');
|
||||||
thumb_element.attr('src', item.thumb);
|
thumb_element.attr('src', item.thumb);
|
||||||
thumb_element.attr('alt', coverArtString(item.title));
|
thumb_element.attr('alt', limitChars(item.title));
|
||||||
type_element.html('[' + item.type + ']');
|
type_element.html('[' + item.type + ']');
|
||||||
path_element.html(item.path);
|
path_element.html(item.path);
|
||||||
|
|
||||||
@ -603,13 +603,13 @@ function addResultItem(item) {
|
|||||||
tags.empty();
|
tags.empty();
|
||||||
|
|
||||||
const tag_edit_copy = tag_edit_element.clone();
|
const tag_edit_copy = tag_edit_element.clone();
|
||||||
tag_edit_copy.click(function () {
|
tag_edit_copy.click(function() {
|
||||||
addTagModalShow(item.id, item.title, item.tags);
|
addTagModalShow(item.id, item.title, item.tags);
|
||||||
});
|
});
|
||||||
tag_edit_copy.appendTo(tags);
|
tag_edit_copy.appendTo(tags);
|
||||||
|
|
||||||
if (item.tags.length > 0) {
|
if (item.tags.length > 0) {
|
||||||
item.tags.forEach(function (tag_tuple) {
|
item.tags.forEach(function(tag_tuple) {
|
||||||
const tag_copy = tag_element.clone();
|
const tag_copy = tag_element.clone();
|
||||||
tag_copy.html(tag_tuple[0]);
|
tag_copy.html(tag_tuple[0]);
|
||||||
tag_copy.addClass('badge-' + tag_tuple[1]);
|
tag_copy.addClass('badge-' + tag_tuple[1]);
|
||||||
@ -627,7 +627,7 @@ function addResultItem(item) {
|
|||||||
function getFilters(dest_page = 1) {
|
function getFilters(dest_page = 1) {
|
||||||
const tags = $('.tag-clicked');
|
const tags = $('.tag-clicked');
|
||||||
const tags_list = [];
|
const tags_list = [];
|
||||||
tags.each(function (index, tag) {
|
tags.each(function(index, tag) {
|
||||||
tags_list.push(tag.innerHTML);
|
tags_list.push(tag.innerHTML);
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -658,14 +658,14 @@ function updateResults(dest_page = 1) {
|
|||||||
|
|
||||||
lib_group.animate({
|
lib_group.animate({
|
||||||
opacity: 0,
|
opacity: 0,
|
||||||
}, 200, function () {
|
}, 200, function() {
|
||||||
$.ajax({
|
$.ajax({
|
||||||
type: 'POST',
|
type: 'POST',
|
||||||
url: 'library',
|
url: 'library',
|
||||||
data: data,
|
data: data,
|
||||||
statusCode: {
|
statusCode: {
|
||||||
200: processResults,
|
200: processResults,
|
||||||
403: function () {
|
403: function() {
|
||||||
location.reload(true);
|
location.reload(true);
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
@ -731,7 +731,7 @@ document.getElementById('library-download-btn').addEventListener('click', () =>
|
|||||||
});
|
});
|
||||||
|
|
||||||
document.getElementById('library-rescan-btn').addEventListener('click', () => {
|
document.getElementById('library-rescan-btn').addEventListener('click', () => {
|
||||||
request('post', { action: 'rescan' });
|
request('post', {action: 'rescan'});
|
||||||
updateResults();
|
updateResults();
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -751,7 +751,7 @@ const page_no = $('.library-page-no');
|
|||||||
function processResults(data) {
|
function processResults(data) {
|
||||||
lib_group.animate({
|
lib_group.animate({
|
||||||
opacity: 0,
|
opacity: 0,
|
||||||
}, 200, function () {
|
}, 200, function() {
|
||||||
lib_loading.hide();
|
lib_loading.hide();
|
||||||
const total_pages = data.total_pages;
|
const total_pages = data.total_pages;
|
||||||
const active_page = data.active_page;
|
const active_page = data.active_page;
|
||||||
@ -760,14 +760,14 @@ function processResults(data) {
|
|||||||
lib_loading.hide();
|
lib_loading.hide();
|
||||||
lib_empty.show();
|
lib_empty.show();
|
||||||
page_ul.empty();
|
page_ul.empty();
|
||||||
lib_group.animate({ opacity: 1 }, 200);
|
lib_group.animate({opacity: 1}, 200);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
items.forEach(
|
items.forEach(
|
||||||
function (item) {
|
function(item) {
|
||||||
addResultItem(item);
|
addResultItem(item);
|
||||||
bindLibraryResultEvent();
|
bindLibraryResultEvent();
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|
||||||
page_ul.empty();
|
page_ul.empty();
|
||||||
@ -785,7 +785,7 @@ function processResults(data) {
|
|||||||
page_no_copy = page_no.clone();
|
page_no_copy = page_no.clone();
|
||||||
page_no_copy.html('«');
|
page_no_copy.html('«');
|
||||||
|
|
||||||
page_no_copy.click(function (e) {
|
page_no_copy.click(function(e) {
|
||||||
updateResults(1);
|
updateResults(1);
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -801,7 +801,7 @@ function processResults(data) {
|
|||||||
if (active_page === i) {
|
if (active_page === i) {
|
||||||
page_li_copy.addClass('active');
|
page_li_copy.addClass('active');
|
||||||
} else {
|
} else {
|
||||||
page_no_copy.click(function (e) {
|
page_no_copy.click(function(e) {
|
||||||
const _page_no = $(e.currentTarget).html();
|
const _page_no = $(e.currentTarget).html();
|
||||||
updateResults(_page_no);
|
updateResults(_page_no);
|
||||||
});
|
});
|
||||||
@ -815,14 +815,14 @@ function processResults(data) {
|
|||||||
page_no_copy = page_no.clone();
|
page_no_copy = page_no.clone();
|
||||||
page_no_copy.html('»');
|
page_no_copy.html('»');
|
||||||
|
|
||||||
page_no_copy.click(function (e) {
|
page_no_copy.click(function(e) {
|
||||||
updateResults(total_pages);
|
updateResults(total_pages);
|
||||||
});
|
});
|
||||||
|
|
||||||
page_no_copy.appendTo(page_li_copy);
|
page_no_copy.appendTo(page_li_copy);
|
||||||
page_li_copy.appendTo(page_ul);
|
page_li_copy.appendTo(page_ul);
|
||||||
}
|
}
|
||||||
lib_group.animate({ opacity: 1 }, 200);
|
lib_group.animate({opacity: 1}, 200);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -841,11 +841,11 @@ function addTagModalShow(_id, _title, _tag_tuples) {
|
|||||||
add_tag_modal_title.html(_title);
|
add_tag_modal_title.html(_title);
|
||||||
add_tag_modal_item_id.val(_id);
|
add_tag_modal_item_id.val(_id);
|
||||||
add_tag_modal_tags.empty();
|
add_tag_modal_tags.empty();
|
||||||
_tag_tuples.forEach(function (tag_tuple) {
|
_tag_tuples.forEach(function(tag_tuple) {
|
||||||
modal_tag_text.html(tag_tuple[0]);
|
modal_tag_text.html(tag_tuple[0]);
|
||||||
const tag_copy = modal_tag.clone();
|
const tag_copy = modal_tag.clone();
|
||||||
const modal_tag_remove = tag_copy.find('.modal-tag-remove');
|
const modal_tag_remove = tag_copy.find('.modal-tag-remove');
|
||||||
modal_tag_remove.click(function (e) {
|
modal_tag_remove.click(function(e) {
|
||||||
$(e.currentTarget).parent().remove();
|
$(e.currentTarget).parent().remove();
|
||||||
});
|
});
|
||||||
tag_copy.show();
|
tag_copy.show();
|
||||||
@ -856,14 +856,14 @@ function addTagModalShow(_id, _title, _tag_tuples) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
document.getElementById('addTagModalAddBtn').addEventListener('click', () => {
|
document.getElementById('addTagModalAddBtn').addEventListener('click', () => {
|
||||||
const new_tags = add_tag_modal_input.val().split(',').map(function (str) {
|
const new_tags = add_tag_modal_input.val().split(',').map(function(str) {
|
||||||
return str.trim();
|
return str.trim();
|
||||||
});
|
});
|
||||||
new_tags.forEach(function (tag) {
|
new_tags.forEach(function(tag) {
|
||||||
modal_tag_text.html(tag);
|
modal_tag_text.html(tag);
|
||||||
const tag_copy = modal_tag.clone();
|
const tag_copy = modal_tag.clone();
|
||||||
const modal_tag_remove = tag_copy.find('.modal-tag-remove');
|
const modal_tag_remove = tag_copy.find('.modal-tag-remove');
|
||||||
modal_tag_remove.click(function (e) {
|
modal_tag_remove.click(function(e) {
|
||||||
$(e.currentTarget).parent().remove();
|
$(e.currentTarget).parent().remove();
|
||||||
});
|
});
|
||||||
tag_copy.show();
|
tag_copy.show();
|
||||||
@ -876,7 +876,7 @@ document.getElementById('addTagModalAddBtn').addEventListener('click', () => {
|
|||||||
document.getElementById('addTagModalSubmit').addEventListener('click', () => {
|
document.getElementById('addTagModalSubmit').addEventListener('click', () => {
|
||||||
const all_tags = $('.modal-tag-text');
|
const all_tags = $('.modal-tag-text');
|
||||||
const tags = [];
|
const tags = [];
|
||||||
all_tags.each(function (i, element) {
|
all_tags.each(function(i, element) {
|
||||||
if (element.innerHTML) {
|
if (element.innerHTML) {
|
||||||
tags.push(element.innerHTML);
|
tags.push(element.innerHTML);
|
||||||
}
|
}
|
||||||
@ -890,7 +890,9 @@ document.getElementById('addTagModalSubmit').addEventListener('click', () => {
|
|||||||
id: add_tag_modal_item_id.val(),
|
id: add_tag_modal_item_id.val(),
|
||||||
tags: tags.join(','),
|
tags: tags.join(','),
|
||||||
},
|
},
|
||||||
complete: function () { updateResults(active_page); },
|
complete: function() {
|
||||||
|
updateResults(active_page);
|
||||||
|
},
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -904,7 +906,7 @@ let volume_popover_instance = null;
|
|||||||
let volume_popover_show = false;
|
let volume_popover_show = false;
|
||||||
let volume_update_timer;
|
let volume_update_timer;
|
||||||
|
|
||||||
volumePopoverBtn.addEventListener('click', function (e) {
|
volumePopoverBtn.addEventListener('click', function(e) {
|
||||||
e.stopPropagation();
|
e.stopPropagation();
|
||||||
|
|
||||||
if (!volume_popover_show) {
|
if (!volume_popover_show) {
|
||||||
@ -926,7 +928,7 @@ volumePopoverBtn.addEventListener('click', function (e) {
|
|||||||
}
|
}
|
||||||
volume_popover_show = !volume_popover_show;
|
volume_popover_show = !volume_popover_show;
|
||||||
|
|
||||||
document.addEventListener('click', function () {
|
document.addEventListener('click', function() {
|
||||||
volumePopoverDiv.removeAttribute('data-show');
|
volumePopoverDiv.removeAttribute('data-show');
|
||||||
if (volume_popover_instance) {
|
if (volume_popover_instance) {
|
||||||
volume_popover_instance.destroy();
|
volume_popover_instance.destroy();
|
||||||
@ -938,7 +940,7 @@ volumePopoverBtn.addEventListener('click', function (e) {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
volumePopoverBtn.addEventListener('click', function (e) {
|
volumePopoverBtn.addEventListener('click', function(e) {
|
||||||
e.stopPropagation();
|
e.stopPropagation();
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -954,11 +956,11 @@ volumeSlider.addEventListener('change', (e) => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
document.getElementById('volume-down-btn').addEventListener('click', () => {
|
document.getElementById('volume-down-btn').addEventListener('click', () => {
|
||||||
request('post', { action: 'volume_down' });
|
request('post', {action: 'volume_down'});
|
||||||
});
|
});
|
||||||
|
|
||||||
document.getElementById('volume-up-btn').addEventListener('click', () => {
|
document.getElementById('volume-up-btn').addEventListener('click', () => {
|
||||||
request('post', { action: 'volume_up' });
|
request('post', {action: 'volume_up'});
|
||||||
});
|
});
|
||||||
|
|
||||||
// ---------------------
|
// ---------------------
|
||||||
@ -1054,7 +1056,7 @@ function uploadNextFile() {
|
|||||||
const file = filesToProceed.shift();
|
const file = filesToProceed.shift();
|
||||||
const file_progress_item = filesProgressItem[file.name];
|
const file_progress_item = filesProgressItem[file.name];
|
||||||
|
|
||||||
req.addEventListener('load', function () {
|
req.addEventListener('load', function() {
|
||||||
if (this.status === 200) {
|
if (this.status === 200) {
|
||||||
setProgressBar(file_progress_item.progress, 1);
|
setProgressBar(file_progress_item.progress, 1);
|
||||||
file_progress_item.progress.classList.add('bg-success');
|
file_progress_item.progress.classList.add('bg-success');
|
||||||
@ -1087,7 +1089,7 @@ function uploadNextFile() {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
req.upload.addEventListener('progress', function (e) {
|
req.upload.addEventListener('progress', function(e) {
|
||||||
if (e.lengthComputable) {
|
if (e.lengthComputable) {
|
||||||
const percent = e.loaded / e.total;
|
const percent = e.loaded / e.total;
|
||||||
setProgressBar(file_progress_item.progress, percent, Math.floor(percent * 100) + '%');
|
setProgressBar(file_progress_item.progress, percent, Math.floor(percent * 100) + '%');
|
||||||
@ -1134,12 +1136,12 @@ const musicUrlInput = document.getElementById('music-url-input');
|
|||||||
const radioUrlInput = document.getElementById('radio-url-input');
|
const radioUrlInput = document.getElementById('radio-url-input');
|
||||||
|
|
||||||
document.getElementById('add-music-url').querySelector('button').addEventListener('click', () => {
|
document.getElementById('add-music-url').querySelector('button').addEventListener('click', () => {
|
||||||
request('post', { add_url: musicUrlInput.value });
|
request('post', {add_url: musicUrlInput.value});
|
||||||
musicUrlInput.value = '';
|
musicUrlInput.value = '';
|
||||||
});
|
});
|
||||||
|
|
||||||
document.getElementById('add-radio-url').querySelector('button').addEventListener('click', () => {
|
document.getElementById('add-radio-url').querySelector('button').addEventListener('click', () => {
|
||||||
request('post', { add_radio: radioUrlInput.value });
|
request('post', {add_radio: radioUrlInput.value});
|
||||||
radioUrlInput.value = '';
|
radioUrlInput.value = '';
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -1161,15 +1163,15 @@ const playerSkipBtn = document.getElementById('playerSkipBtn');
|
|||||||
let currentPlayingItem = null;
|
let currentPlayingItem = null;
|
||||||
|
|
||||||
playerPlayBtn.addEventListener('click', () => {
|
playerPlayBtn.addEventListener('click', () => {
|
||||||
request('post', { action: 'resume' });
|
request('post', {action: 'resume'});
|
||||||
});
|
});
|
||||||
|
|
||||||
playerPauseBtn.addEventListener('click', () => {
|
playerPauseBtn.addEventListener('click', () => {
|
||||||
request('post', { action: 'pause' });
|
request('post', {action: 'pause'});
|
||||||
});
|
});
|
||||||
|
|
||||||
playerSkipBtn.addEventListener('click', () => {
|
playerSkipBtn.addEventListener('click', () => {
|
||||||
request('post', { action: 'next' });
|
request('post', {action: 'next'});
|
||||||
});
|
});
|
||||||
|
|
||||||
document.getElementById('player-toast').addEventListener('click', () => {
|
document.getElementById('player-toast').addEventListener('click', () => {
|
||||||
@ -1196,7 +1198,7 @@ function updatePlayerInfo(item) {
|
|||||||
playerTitle.textContent = item.title;
|
playerTitle.textContent = item.title;
|
||||||
playerArtist.textContent = item.artist;
|
playerArtist.textContent = item.artist;
|
||||||
playerArtwork.setAttribute('src', item.thumbnail);
|
playerArtwork.setAttribute('src', item.thumbnail);
|
||||||
playerArtwork.setAttribute('alt', coverArtString(item.title));
|
playerArtwork.setAttribute('alt', limitChars(item.title));
|
||||||
|
|
||||||
if (isOverflown(playerTitle)) {
|
if (isOverflown(playerTitle)) {
|
||||||
playerTitle.classList.add('scrolling');
|
playerTitle.classList.add('scrolling');
|
||||||
@ -1245,7 +1247,7 @@ function updatePlayerPlayhead(playhead) {
|
|||||||
player_playhead_position = playhead;
|
player_playhead_position = playhead;
|
||||||
setProgressBar(playerBar, player_playhead_position / currentPlayingItem.duration, secondsToStr(player_playhead_position));
|
setProgressBar(playerBar, player_playhead_position / currentPlayingItem.duration, secondsToStr(player_playhead_position));
|
||||||
if (playing) {
|
if (playing) {
|
||||||
playhead_timer = setInterval(function () {
|
playhead_timer = setInterval(function() {
|
||||||
player_playhead_position += 0.3;
|
player_playhead_position += 0.3;
|
||||||
setProgressBar(playerBar, player_playhead_position / currentPlayingItem.duration, secondsToStr(player_playhead_position));
|
setProgressBar(playerBar, player_playhead_position / currentPlayingItem.duration, secondsToStr(player_playhead_position));
|
||||||
}, 300); // delay in milliseconds
|
}, 300); // delay in milliseconds
|
||||||
@ -1260,7 +1262,7 @@ function updatePlayerPlayhead(playhead) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
playerBarBox.addEventListener('mousedown', function () {
|
playerBarBox.addEventListener('mousedown', function() {
|
||||||
if (currentPlayingItem && currentPlayingItem.duration > 0) {
|
if (currentPlayingItem && currentPlayingItem.duration > 0) {
|
||||||
playerBarBox.addEventListener('mousemove', playheadDragged);
|
playerBarBox.addEventListener('mousemove', playheadDragged);
|
||||||
clearInterval(playhead_timer);
|
clearInterval(playhead_timer);
|
||||||
@ -1268,7 +1270,7 @@ playerBarBox.addEventListener('mousedown', function () {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
playerBarBox.addEventListener('mouseup', function (event) {
|
playerBarBox.addEventListener('mouseup', function(event) {
|
||||||
playerBarBox.removeEventListener('mousemove', playheadDragged);
|
playerBarBox.removeEventListener('mousemove', playheadDragged);
|
||||||
const percent = (event.clientX - playerBarBox.getBoundingClientRect().x) / playerBarBox.clientWidth;
|
const percent = (event.clientX - playerBarBox.getBoundingClientRect().x) / playerBarBox.clientWidth;
|
||||||
request('post', {
|
request('post', {
|
||||||
|
13655
web/package-lock.json
generated
13655
web/package-lock.json
generated
File diff suppressed because it is too large
Load Diff
@ -4,7 +4,6 @@
|
|||||||
"type": "module",
|
"type": "module",
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"lint": "eslint --config .eslintrc.json js/ --ext .mjs",
|
"lint": "eslint --config .eslintrc.json js/ --ext .mjs",
|
||||||
"lint:fix": "npm run lint -- --fix",
|
|
||||||
"build": "webpack --config webpack.config.cjs --progress",
|
"build": "webpack --config webpack.config.cjs --progress",
|
||||||
"test": "echo \"Error: no test specified\" && exit 1"
|
"test": "echo \"Error: no test specified\" && exit 1"
|
||||||
},
|
},
|
||||||
@ -19,38 +18,36 @@
|
|||||||
},
|
},
|
||||||
"homepage": "https://github.com/azlux/botamusique#readme",
|
"homepage": "https://github.com/azlux/botamusique#readme",
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@babel/core": "^7.11.1",
|
"@babel/core": "^7.12.9",
|
||||||
"@babel/plugin-proposal-class-properties": "^7.10.4",
|
"@babel/eslint-parser": "^7.12.1",
|
||||||
"@babel/preset-env": "^7.11.0",
|
"@babel/eslint-plugin": "^7.12.1",
|
||||||
"autoprefixer": "^9.8.6",
|
"@babel/plugin-proposal-class-properties": "^7.12.1",
|
||||||
"babel-eslint": "^10.1.0",
|
"@babel/preset-env": "^7.12.7",
|
||||||
"babel-loader": "^8.1.0",
|
"autoprefixer": "^10.0.2",
|
||||||
"core-js": "^3.6.5",
|
"babel-loader": "^8.2.1",
|
||||||
"css-loader": "^4.2.1",
|
"core-js": "^3.7.0",
|
||||||
"eslint": "^7.7.0",
|
"css-loader": "^5.0.1",
|
||||||
"eslint-config-google": "^0.14.0",
|
"eslint": "^7.14.0",
|
||||||
"eslint-plugin-import": "^2.22.0",
|
"eslint-plugin-import": "^2.22.1",
|
||||||
"eslint-plugin-jsdoc": "^30.2.2",
|
"eslint-plugin-jquery": "^1.5.1",
|
||||||
"eslint-plugin-node": "^11.1.0",
|
"eslint-plugin-jsdoc": "^30.7.8",
|
||||||
"html-webpack-plugin": "^4.3.0",
|
"html-webpack-plugin": "^4.5.0",
|
||||||
"mini-css-extract-plugin": "^0.10.0",
|
"mini-css-extract-plugin": "^1.3.1",
|
||||||
"postcss-loader": "^3.0.0",
|
"postcss-loader": "^4.1.0",
|
||||||
"regenerator-runtime": "^0.13.7",
|
"regenerator-runtime": "^0.13.7",
|
||||||
"sass": "^1.26.10",
|
"sass": "^1.29.0",
|
||||||
"sass-loader": "^9.0.3",
|
"sass-loader": "^10.1.0",
|
||||||
"webpack": "^4.44.1",
|
"webpack": "^5.6.0",
|
||||||
"webpack-cli": "^3.3.12"
|
"webpack-cli": "^4.2.0"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@fortawesome/fontawesome-svg-core": "^1.2.30",
|
"@fortawesome/fontawesome-svg-core": "^1.2.32",
|
||||||
"@fortawesome/free-brands-svg-icons": "^5.14.0",
|
"@fortawesome/free-regular-svg-icons": "^5.15.1",
|
||||||
"@fortawesome/free-regular-svg-icons": "^5.14.0",
|
"@fortawesome/free-solid-svg-icons": "^5.15.1",
|
||||||
"@fortawesome/free-solid-svg-icons": "^5.14.0",
|
"bootstrap": "^4.5.3",
|
||||||
"bootstrap": "^4.5.2",
|
"bootswatch": "^4.5.3",
|
||||||
"bootswatch": "^4.5.2",
|
|
||||||
"jquery": "^3.5.1",
|
"jquery": "^3.5.1",
|
||||||
"jquery-migrate": "^3.3.1",
|
"jquery-migrate": "^3.3.2",
|
||||||
"popper.js": "^1.16.1"
|
"popper.js": "^1.16.1"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
7
web/vscode.eslintrc.json
Normal file
7
web/vscode.eslintrc.json
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
{
|
||||||
|
"parserOptions": {
|
||||||
|
"babelOptions": {
|
||||||
|
"configFile": "./web/babel.config.json"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -4,6 +4,7 @@ const HtmlWebpackPlugin = require('html-webpack-plugin');
|
|||||||
|
|
||||||
module.exports = {
|
module.exports = {
|
||||||
mode: 'production',
|
mode: 'production',
|
||||||
|
devtool: 'source-map',
|
||||||
entry: {
|
entry: {
|
||||||
main: [
|
main: [
|
||||||
'./js/app.mjs',
|
'./js/app.mjs',
|
||||||
@ -13,16 +14,9 @@ module.exports = {
|
|||||||
'./sass/app-dark.scss',
|
'./sass/app-dark.scss',
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
devtool: 'source-map',
|
|
||||||
/*optimization: {
|
|
||||||
splitChunks: {
|
|
||||||
chunks: 'all',
|
|
||||||
},
|
|
||||||
},*/
|
|
||||||
output: {
|
output: {
|
||||||
filename: 'static/js/[name].js',
|
filename: 'static/js/[name].js',
|
||||||
path: path.resolve(__dirname, '../'),
|
path: path.resolve(__dirname, '../'),
|
||||||
// ecmaVersion: 5,
|
|
||||||
},
|
},
|
||||||
plugins: [
|
plugins: [
|
||||||
new MiniCssExtractPlugin({
|
new MiniCssExtractPlugin({
|
||||||
@ -48,10 +42,15 @@ module.exports = {
|
|||||||
{
|
{
|
||||||
loader: 'postcss-loader',
|
loader: 'postcss-loader',
|
||||||
options: {
|
options: {
|
||||||
plugins: function() {
|
postcssOptions: {
|
||||||
return [
|
plugins: [
|
||||||
require('autoprefixer'),
|
[
|
||||||
];
|
'autoprefixer',
|
||||||
|
{
|
||||||
|
// Options
|
||||||
|
},
|
||||||
|
],
|
||||||
|
],
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
@ -61,6 +60,9 @@ module.exports = {
|
|||||||
{
|
{
|
||||||
test: /\.m?js$/,
|
test: /\.m?js$/,
|
||||||
exclude: /(node_modules|bower_components)/,
|
exclude: /(node_modules|bower_components)/,
|
||||||
|
resolve: {
|
||||||
|
fullySpecified: false,
|
||||||
|
},
|
||||||
use: {
|
use: {
|
||||||
loader: 'babel-loader',
|
loader: 'babel-loader',
|
||||||
options: {
|
options: {
|
||||||
@ -73,15 +75,9 @@ module.exports = {
|
|||||||
},
|
},
|
||||||
],
|
],
|
||||||
],
|
],
|
||||||
plugins: [
|
|
||||||
'@babel/plugin-proposal-class-properties',
|
|
||||||
],
|
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
/* experiments: {
|
|
||||||
mjs: true,
|
|
||||||
},*/
|
|
||||||
};
|
};
|
||||||
|
Loading…
x
Reference in New Issue
Block a user