Configured and ran Prettier on client files

This commit is contained in:
Andrew Carr 2021-05-23 03:15:19 +00:00
parent 9d1a3ccfb2
commit b35e705066
9 changed files with 1673 additions and 1010 deletions

13
.prettierignore Normal file
View File

@ -0,0 +1,13 @@
# Used by Prettier to ignore certain files and folders completely.
# See https://prettier.io/docs/en/ignore.html for details.
# Ignore build and system artifacts
build/
cmake/
contrib/
# Ignore all 3rd party libraries
**/bootstrap*
**/jquery*
**/modernizr*
**/sammy*

20
.prettierrc.json Normal file
View File

@ -0,0 +1,20 @@
{
"trailingComma": "es5",
"tabWidth": 4,
"semi": true,
"singleQuote": true,
"overrides": [
{
"files": ["*.html"],
"options": {
"tabWidth": 2
}
},
{
"files": ["*.css"],
"options": {
"tabWidth": 2
}
}
]
}

View File

@ -3,16 +3,15 @@ language: c
sudo: required sudo: required
dist: trusty dist: trusty
compiler: compiler:
- gcc - gcc
- clang - clang
before_install: before_install:
- sudo apt-get -qq update - sudo apt-get -qq update
- sudo apt-get install -y libmpdclient-dev cmake - sudo apt-get install -y libmpdclient-dev cmake
- mkdir build - mkdir build
- cd build - cd build
- cmake -D CMAKE_BUILD_TYPE=DEBUG .. - cmake -D CMAKE_BUILD_TYPE=DEBUG ..
script: make script: make

13
DEVELOPMENT.md Normal file
View File

@ -0,0 +1,13 @@
# Development Notes
## Code Formatting
The project has been formatted with [prettier.io](https://prettier.io/) for the HTML, JavaScript, CSS, and Markdown files. See the configuration file [.prettierrc.json](./.prettierrc.json) and the ignore file [.prettierignore](./.prettierignore) for details. If `prettier` is installed globally, there's no need to provide the various `npm`-type dependencies in the project. Various editors may provide plugins that can use this configuration without having to install `npm` and `prettier` manually.
Manual Usage:
```bash
> npx prettier --write .
```
The C source and header files have been formatted with `clang-format`.

View File

@ -4,28 +4,26 @@ ympd
Standalone MPD Web GUI written in C, utilizing Websockets and Bootstrap/JS Standalone MPD Web GUI written in C, utilizing Websockets and Bootstrap/JS
http://www.ympd.org http://www.ympd.org
![ScreenShot](http://www.ympd.org/assets/ympd_github.png) ![ScreenShot](http://www.ympd.org/assets/ympd_github.png)
Dependencies ## Dependencies
------------
- libmpdclient 2: http://www.musicpd.org/libs/libmpdclient/
- cmake 2.6: http://cmake.org/
- OpenSSL: https://www.openssl.org/
Unix Build Instructions - libmpdclient 2: http://www.musicpd.org/libs/libmpdclient/
----------------------- - cmake 2.6: http://cmake.org/
- OpenSSL: https://www.openssl.org/
## Unix Build Instructions
1. install dependencies. cmake, libmpdclient (dev), and OpenSSL (dev) are available from all major distributions. 1. install dependencies. cmake, libmpdclient (dev), and OpenSSL (dev) are available from all major distributions.
2. create build directory ```cd /path/to/src; mkdir build; cd build``` 2. create build directory `cd /path/to/src; mkdir build; cd build`
3. create makefile ```cmake .. -DCMAKE_INSTALL_PREFIX:PATH=/usr``` 3. create makefile `cmake .. -DCMAKE_INSTALL_PREFIX:PATH=/usr`
4. build ```make``` 4. build `make`
5. install ```sudo make install``` or just run with ```./ympd``` 5. install `sudo make install` or just run with `./ympd`
## Run flags
Run flags
---------
``` ```
Usage: ./ympd [OPTION]... Usage: ./ympd [OPTION]...
@ -39,21 +37,23 @@ Usage: ./ympd [OPTION]...
--help this help --help this help
``` ```
SSL Support ## SSL Support
-----------
To run ympd with SSL support: To run ympd with SSL support:
- create a certificate (key and cert in the same file), example: - create a certificate (key and cert in the same file), example:
``` ```
# openssl req -x509 -newkey rsa:2048 -keyout key.pem -out cert.pem -days 1000 -nodes # openssl req -x509 -newkey rsa:2048 -keyout key.pem -out cert.pem -days 1000 -nodes
# cat key.pem cert.pem > ssl.pem # cat key.pem cert.pem > ssl.pem
``` ```
- tell ympd to use a webport using SSL and where to find the certificate:
- tell ympd to use a webport using SSL and where to find the certificate:
``` ```
# ./ympd -w "ssl://8081:/path/to/ssl.pem" # ./ympd -w "ssl://8081:/path/to/ssl.pem"
``` ```
Copyright ## Copyright
---------
2013-2014 <andy@ndyk.de> 2013-2014 <andy@ndyk.de>

View File

@ -15,12 +15,10 @@ body {
margin-bottom: 0; margin-bottom: 0;
} }
button { button {
overflow: hidden; overflow: hidden;
} }
#volume-icon { #volume-icon {
float: left; float: left;
margin-right: 10px; margin-right: 10px;
@ -34,7 +32,7 @@ button {
white-space: nowrap; white-space: nowrap;
} }
#breadcrump > li > a{ #breadcrump > li > a {
cursor: pointer; cursor: pointer;
} }
@ -58,17 +56,17 @@ button {
background-image: none; background-image: none;
outline: 0; outline: 0;
-webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125); -webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);
box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125); box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);
color: #428bca; color: #428bca;
background-color: #fdfdfd; background-color: #fdfdfd;
border-color: #adadad; border-color: #adadad;
} }
@media (max-width: 1199px) { @media (max-width: 1199px) {
#btn-responsive-block > .btn { #btn-responsive-block > .btn {
padding: 6px 12px; padding: 6px 12px;
font-size: 14px; font-size: 14px;
border-radius: 4px; border-radius: 4px;
} }
} }
@ -80,14 +78,16 @@ h1 {
white-space: nowrap; white-space: nowrap;
} }
td:nth-child(4), th:nth-child(4) { td:nth-child(4),
th:nth-child(4) {
/* This *has* to be placed before /* This *has* to be placed before
any t[dh]:nth-last-child(2) for any t[dh]:nth-last-child(2) for
the override to work. */ the override to work. */
min-width: 50%; min-width: 50%;
} }
td:nth-last-child(2), th:nth-last-child(2) { td:nth-last-child(2),
th:nth-last-child(2) {
text-align: right; text-align: right;
width: 4em; width: 4em;
} }
@ -98,7 +98,8 @@ td:nth-last-child(2), th:nth-last-child(2) {
display: block; display: block;
} }
td:nth-child(2), td:nth-child(3) { td:nth-child(2),
td:nth-child(3) {
min-width: 25%; min-width: 25%;
max-width: 10em; max-width: 10em;
@ -108,21 +109,24 @@ td:nth-child(2), td:nth-child(3) {
} }
@media only screen and (max-width: 600px) { @media only screen and (max-width: 600px) {
td:nth-child(2), td:nth-child(3) { td:nth-child(2),
min-width: 0; td:nth-child(3) {
max-width: 0; min-width: 0;
} max-width: 0;
td:nth-child(4), th:nth-child(4) { }
min-width: 10%; td:nth-child(4),
white-space: normal; th:nth-child(4) {
} min-width: 10%;
white-space: normal;
}
} }
tbody { tbody {
cursor: pointer; cursor: pointer;
} }
td:last-child, td:first-child { td:last-child,
td:first-child {
width: 30px; width: 30px;
} }
@ -149,9 +153,9 @@ button {
} }
#trashmode span:last-child { #trashmode span:last-child {
display:inline-block; display: inline-block;
text-align:left; text-align: left;
width:2.8em; width: 2.8em;
} }
#filter > a.active { #filter > a.active {

View File

@ -1,65 +1,110 @@
<!DOCTYPE html> <!DOCTYPE html>
<html lang="en"> <html lang="en">
<head> <head>
<meta charset="utf-8"> <meta charset="utf-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge"> <meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta name="viewport" content="width=device-width, initial-scale=1.0" />
<meta name="description" content="ympd - fast and lightweight MPD webclient"> <meta
<meta name="author" content="andy@ndyk.de"> name="description"
content="ympd - fast and lightweight MPD webclient"
/>
<meta name="author" content="andy@ndyk.de" />
<title>ympd</title> <title>ympd</title>
<!-- Bootstrap core CSS --> <!-- Bootstrap core CSS -->
<link href="css/bootstrap.css" rel="stylesheet"> <link href="css/bootstrap.css" rel="stylesheet" />
<link href="css/bootstrap-theme.css" rel="stylesheet"> <link href="css/bootstrap-theme.css" rel="stylesheet" />
<!-- Custom styles for this template --> <!-- Custom styles for this template -->
<link href="css/mpd.css" rel="stylesheet"> <link href="css/mpd.css" rel="stylesheet" />
<link href="assets/favicon.ico" rel="shortcut icon" type="image/vnd.microsoft.icon"> <link
<script src="js/modernizr-custom.js"></script> href="assets/favicon.ico"
</head> rel="shortcut icon"
<body> type="image/vnd.microsoft.icon"
/>
<script src="js/modernizr-custom.js"></script>
</head>
<body>
<div class="navbar navbar-inverse navbar-fixed-top" role="navigation">
<div class="container">
<div class="navbar-header">
<button
type="button"
class="navbar-toggle"
data-toggle="collapse"
data-target=".navbar-collapse"
>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
</button>
<a class="navbar-brand" href="/"
><span class="glyphicon glyphicon-play-circle"></span> ympd</a
>
</div>
<div class="collapse navbar-collapse">
<ul id="nav_links" class="nav navbar-nav">
<li id="queue"><a href="#/">Queue</a></li>
<li id="browse"><a href="#/browse/0/">Browse</a></li>
<li>
<a href="#" data-toggle="modal" data-target="#addstream"
>Add Stream</a
>
</li>
<li>
<a
href="#"
data-toggle="modal"
data-target="#settings"
onclick="getHost();"
>Settings</a
>
</li>
</ul>
<div class="navbar navbar-inverse navbar-fixed-top" role="navigation"> <div class="btn-toolbar navbar-btn navbar-right" role="toolbar">
<div class="container"> <div class="btn-group">
<div class="navbar-header"> <button
<button type="button" class="navbar-toggle" data-toggle="collapse" data-target=".navbar-collapse"> type="button"
<span class="icon-bar"></span> class="btn btn-default"
<span class="icon-bar"></span> onclick="socket.send('MPD_API_SET_PREV');"
<span class="icon-bar"></span> >
</button> <span class="glyphicon glyphicon-backward"></span>
<a class="navbar-brand" href="/"><span class="glyphicon glyphicon-play-circle"></span> ympd</a> </button>
</div> <button
<div class="collapse navbar-collapse"> type="button"
class="btn btn-default"
<ul id="nav_links" class="nav navbar-nav"> onclick="socket.send('MPD_API_SET_STOP');"
<li id="queue"><a href="#/">Queue</a></li> >
<li id="browse"><a href="#/browse/0/">Browse</a></li> <span id="stop-icon" class="glyphicon glyphicon-stop"></span>
<li><a href="#" data-toggle="modal" data-target="#addstream">Add Stream</a></li> </button>
<li><a href="#" data-toggle="modal" data-target="#settings" onclick="getHost();">Settings</a></li> <button
</ul> type="button"
class="btn btn-default"
<div class="btn-toolbar navbar-btn navbar-right" role="toolbar"> onclick="clickPlay();"
<div class="btn-group"> >
<button type="button" class="btn btn-default" onclick="socket.send('MPD_API_SET_PREV');"> <span id="play-icon" class="glyphicon glyphicon-pause"></span>
<span class="glyphicon glyphicon-backward"></span> </button>
</button> <button
<button type="button" class="btn btn-default" onclick="socket.send('MPD_API_SET_STOP');"> type="button"
<span id="stop-icon" class="glyphicon glyphicon-stop"></span> class="btn btn-default"
</button> onclick="socket.send('MPD_API_SET_NEXT');"
<button type="button" class="btn btn-default" onclick="clickPlay();"> >
<span id="play-icon" class="glyphicon glyphicon-pause"></span> <span class="glyphicon glyphicon-forward"></span>
</button> </button>
<button type="button" class="btn btn-default" onclick="socket.send('MPD_API_SET_NEXT');"> </div>
<span class="glyphicon glyphicon-forward"></span> <div class="btn-group">
</button> <button
</div> id="btnlove"
<div class="btn-group"> type="button"
<button id="btnlove" type="button" class="btn btn-default" onclick="clickLove();"> class="btn btn-default"
<span class="glyphicon glyphicon-heart"></span> onclick="clickLove();"
</button> >
</div> <span class="glyphicon glyphicon-heart"></span>
<!-- </button>
</div>
<!--
<div class="btn-group"> <div class="btn-group">
<div class="btn btn-toolbar btn-default"> <div class="btn btn-toolbar btn-default">
<span id="volume-icon" class="glyphicon glyphicon-volume-up"></span> <span id="volume-icon" class="glyphicon glyphicon-volume-up"></span>
@ -67,293 +112,493 @@
</div> </div>
</div> </div>
--> -->
<div class="btn-group" role="group"> <div class="btn-group" role="group">
<audio id="player" preload="none"></audio> <audio id="player" preload="none"></audio>
<button type="button" class="btn btn-default" onclick="clickLocalPlay()"> <button
<span id="localplay-icon" class="glyphicon glyphicon-play"></span> type="button"
</button> class="btn btn-default"
<button type="button" class="btn btn-default" onclick="window.open('/player.html');"> onclick="clickLocalPlay()"
<span id="localplay-icon" class="glyphicon glyphicon-new-window"></span> >
</button> <span
id="localplay-icon"
class="glyphicon glyphicon-play"
></span>
</button>
<button
type="button"
class="btn btn-default"
onclick="window.open('/player.html');"
>
<span
id="localplay-icon"
class="glyphicon glyphicon-new-window"
></span>
</button>
</div>
</div> </div>
</div>
<form id="search" class="navbar-form navbar-right" role="search">
<form id="search" class="navbar-form navbar-right" role="search"> <div class="form-group">
<div class="form-group"> <input type="text" class="form-control" placeholder="Search" />
<input type="text" class="form-control" placeholder="Search"> </div>
</div> </form>
</form> </div>
</div><!--/.nav-collapse --> <!--/.nav-collapse -->
</div>
</div> </div>
</div>
<div class="container starter-template"> <div class="container starter-template">
<div class="row"> <div class="row">
<div class="col-md-10 col-xs-12">
<div class="notifications top-right"></div>
<div class="col-md-10 col-xs-12"> <div class="panel panel-primary">
<div class="notifications top-right"></div> <!-- Default panel contents -->
<div class="panel-heading">
<b id="panel-heading">Queue</b>
<b id="panel-heading-info" class="text pull-right"></b>
</div>
<div class="panel-body">
<h1>
<span
id="track-icon"
onclick="clickPlay();"
class="glyphicon glyphicon-play"
></span>
<span id="currenttrack"></span>
</h1>
<h4>
<span id="artist" class="text"></span>
<span id="album" class="text pull-right"></span>
</h4>
<p id="counter" class="text pull-right">&nbsp;&nbsp;</p>
<div class="panel panel-primary"> <div id="progressbar"></div>
<!-- Default panel contents --> </div>
<div class="panel-heading"><b id="panel-heading">Queue</b> <!-- /.panel-body -->
<b id="panel-heading-info" class="text pull-right"></b></div>
<div class="panel-body"> <ol id="breadcrump" class="breadcrumb"></ol>
<h1>
<span id="track-icon" onclick="clickPlay();" class="glyphicon glyphicon-play"></span> <div class="col-md-12" id="filter"></div>
<span id="currenttrack"></span>
</h1> <!-- Table -->
<table id="salamisandwich" class="table table-hover">
<thead>
<tr>
<th>#</th>
<th>Artist</th>
<th>Album</th>
<th>Title</th>
<th>Length</th>
<th></th>
</tr>
</thead>
<tbody></tbody>
</table>
</div>
<!-- /.panel -->
<ul class="pager">
<li id="prev" class="page-btn hide"><a href="">Previous</a></li>
<li id="next" class="page-btn"><a href="">Next</a></li>
</ul>
</div>
<!-- /.col-md-10 -->
<div class="col-md-2 col-xs-12">
<div class="btn-toolbar">
<div
class="btn-group-vertical btn-block btn-group-lg"
data-toggle="buttons"
>
<button id="btnrandom" type="button" class="btn btn-default">
<span class="glyphicon glyphicon-random"></span> Random
</button>
<button id="btnconsume" type="button" class="btn btn-default">
<span class="glyphicon glyphicon-fire"></span> Consume
</button>
<button id="btnsingle" type="button" class="btn btn-default">
<span class="glyphicon glyphicon-star"></span> Single
</button>
<button id="btncrossfade" type="button" class="btn btn-default">
<span class="glyphicon glyphicon-link"></span> Crossfade
</button>
<button id="btnrepeat" type="button" class="btn btn-default">
<span class="glyphicon glyphicon-repeat"></span> Repeat
</button>
</div>
<div
id="btn-outputs-block"
class="btn-group-vertical btn-block btn-group-lg"
></div>
<div
id="trashmode"
class="btn-group-vertical btn-block btn-group-lg"
data-toggle="radio"
>
<button id="btntrashmodeup" type="button" class="btn btn-default">
<span class="glyphicon glyphicon-chevron-up"></span>
<span class="glyphicon glyphicon-trash"></span> <span>Up</span>
</button>
<button
id="btntrashmodesingle"
type="button"
class="btn btn-default active"
>
<span class="glyphicon glyphicon-star-empty"></span>
<span class="glyphicon glyphicon-trash"></span>
<span>Single</span>
</button>
<button
id="btntrashmodedown"
type="button"
class="btn btn-default"
>
<span class="glyphicon glyphicon-chevron-down"></span>
<span class="glyphicon glyphicon-trash"></span>
<span>Down</span>
</button>
</div>
<div
id="btn-responsive-block"
class="btn-group-vertical btn-block btn-group-lg"
>
<button
type="button"
class="btn btn-default"
onclick="socket.send('MPD_API_RM_ALL');"
>
<span class="glyphicon glyphicon-trash"></span> Clear Queue
</button>
<a
href="#"
data-toggle="modal"
data-target="#savequeue"
class="btn btn-default"
>
<span class="glyphicon glyphicon-save"></span> Save Queue
</a>
</div>
</div>
</div>
<!-- /.col-md-2 -->
</div>
<!-- /.row -->
</div>
<!-- /.container -->
<!-- Modal -->
<div
class="modal fade"
id="settings"
tabindex="-1"
role="dialog"
aria-labelledby="settingsLabel"
aria-hidden="true"
>
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<button
type="button"
class="close"
data-dismiss="modal"
aria-hidden="true"
>
&times;
</button>
<h2 class="modal-title" id="settingsLabel">
<span class="glyphicon glyphicon-wrench"></span> Settings
</h2>
</div>
<div class="modal-body">
<h4> <h4>
<span id="artist" class="text"></span> <a href="http://www.ympd.org"
<span id="album" class="text pull-right"></span> ><span class="glyphicon glyphicon-play-circle"></span> ympd</a
>&nbsp;&nbsp;&nbsp;<small
>MPD Web GUI - written in C, utilizing Websockets and
Bootstrap/JS</small
>
</h4> </h4>
<p id="counter" class="text pull-right">&nbsp;&nbsp;</p> <p>
ympd is a lightweight MPD (Music Player Daemon) web client that
<div id="progressbar"></div> runs without a dedicated webserver or interpreters like PHP,
NodeJS or Ruby. It's tuned for minimal resource usage and requires
only very litte dependencies.
</div><!-- /.panel-body --> </p>
<h5>ympd uses following excellent software:</h5>
<ol id="breadcrump" class="breadcrumb"> <h6>
</ol> <a href="http://cesanta.com/docs.html">Mongoose</a>
<small>GPLv2</small>
<div class="col-md-12" id="filter"> </h6>
</div> <h6>
<a href="http://www.musicpd.org/libs/libmpdclient/"
>libMPDClient</a
<!-- Table --> >
<table id="salamisandwich" class="table table-hover"> <small>BSD License</small>
<thead> </h6>
<tr> <hr />
<th>#</th>
<th>Artist</th>
<th>Album</th>
<th>Title</th>
<th>Length</th>
<th></th>
</tr>
</thead>
<tbody>
</tbody>
</table>
</div><!-- /.panel -->
<ul class="pager">
<li id="prev" class="page-btn hide"><a href="">Previous</a></li>
<li id="next" class="page-btn"><a href="">Next</a></li>
</ul>
</div><!-- /.col-md-10 -->
<div class="col-md-2 col-xs-12">
<div class="btn-toolbar">
<div class="btn-group-vertical btn-block btn-group-lg" data-toggle="buttons">
<button id="btnrandom" type="button" class="btn btn-default">
<span class="glyphicon glyphicon-random"></span> Random
</button>
<button id="btnconsume" type="button" class="btn btn-default">
<span class="glyphicon glyphicon-fire"></span> Consume
</button>
<button id="btnsingle" type="button" class="btn btn-default">
<span class="glyphicon glyphicon-star"></span> Single
</button>
<button id="btncrossfade" type="button" class="btn btn-default">
<span class="glyphicon glyphicon-link"></span> Crossfade
</button>
<button id="btnrepeat" type="button" class="btn btn-default">
<span class="glyphicon glyphicon-repeat"></span> Repeat
</button>
</div>
<div id="btn-outputs-block" class="btn-group-vertical btn-block btn-group-lg">
</div>
<div id="trashmode" class="btn-group-vertical btn-block btn-group-lg" data-toggle="radio">
<button id="btntrashmodeup" type="button" class="btn btn-default">
<span class="glyphicon glyphicon-chevron-up"></span>
<span class="glyphicon glyphicon-trash"></span> <span>Up</span>
</button>
<button id="btntrashmodesingle" type="button" class="btn btn-default active">
<span class="glyphicon glyphicon-star-empty"></span>
<span class="glyphicon glyphicon-trash"></span> <span>Single</span>
</button>
<button id="btntrashmodedown" type="button" class="btn btn-default">
<span class="glyphicon glyphicon-chevron-down"></span>
<span class="glyphicon glyphicon-trash"></span> <span>Down</span>
</button>
</div>
<div id="btn-responsive-block" class="btn-group-vertical btn-block btn-group-lg">
<button type="button" class="btn btn-default" onclick="socket.send('MPD_API_RM_ALL');">
<span class="glyphicon glyphicon-trash"></span> Clear Queue
</button>
<a href="#" data-toggle="modal" data-target="#savequeue" class="btn btn-default">
<span class="glyphicon glyphicon-save"></span> Save Queue
</a>
</div>
</div>
</div><!-- /.col-md-2 -->
</div><!-- /.row -->
</div><!-- /.container -->
<!-- Modal -->
<div class="modal fade" id="settings" tabindex="-1" role="dialog" aria-labelledby="settingsLabel" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
<h2 class="modal-title" id="settingsLabel"><span class="glyphicon glyphicon-wrench"></span> Settings</h2>
</div>
<div class="modal-body">
<h4><a href="http://www.ympd.org"><span class="glyphicon glyphicon-play-circle"></span> ympd</a>&nbsp;&nbsp;&nbsp;<small>MPD Web GUI - written in C, utilizing Websockets and Bootstrap/JS</small></h4>
<p>
ympd is a lightweight MPD (Music Player Daemon) web client that runs without a dedicated webserver or interpreters like PHP, NodeJS or Ruby. It's tuned for minimal resource usage and requires only very litte dependencies.</p>
<h5>ympd uses following excellent software:</h5>
<h6><a href="http://cesanta.com/docs.html">Mongoose</a> <small>GPLv2</small></h6>
<h6><a href="http://www.musicpd.org/libs/libmpdclient/">libMPDClient</a> <small>BSD License</small></h6>
<hr />
<div class="row">
<div class="form-group col-md-6">
<button type="button" class="btn btn-default btn-block" onclick="updateDB();">
<span class="glyphicon glyphicon-refresh"></span> Update Database
</button>
</div>
<div class="form-group col-md-6" data-toggle="buttons">
<button type="button" class="btn btn-default btn-block" id="btnnotify">
<span class="glyphicon glyphicon-comment"></span> Enable Notifications
</button>
</div>
</div>
<hr />
<form role="form">
<div class="row">
<div class="form-group col-md-9">
<label class="control-label" for="mpdhost">MPD Host/IP</label>
<input type="text" class="form-control" id="mpdhost" />
</div>
<div class="form-group col-md-3">
<label class="control-label" for="mpdport">MPD Port</label>
<input type="text" class="form-control" id="mpdport" />
</div>
</div>
<div class="row"> <div class="row">
<div class="form-group col-md-6"> <div class="form-group col-md-6">
<label class="control-label" for="mpd_pw">MPD Password</label> <button
<input type="password" class="form-control" id="mpd_pw" placeholder="Password"/> type="button"
class="btn btn-default btn-block"
onclick="updateDB();"
>
<span class="glyphicon glyphicon-refresh"></span> Update
Database
</button>
</div> </div>
<div class="form-group col-md-6"> <div class="form-group col-md-6" data-toggle="buttons">
<label class="control-label" for="mpd_pw_con">MPD Password (Confirmation)</label> <button
<input type="password" class="form-control" id="mpd_pw_con" placeholder="Confirmation" type="button"
data-placement="right" data-toggle="popover" data-content="Password does not match!" class="btn btn-default btn-block"
data-trigger="manual" /> id="btnnotify"
>
<span class="glyphicon glyphicon-comment"></span> Enable
Notifications
</button>
</div> </div>
<div class="form-group col-md-12"> </div>
<div id="mpd_password_set" class="hide alert alert-info"> <hr />
<button type="button" class="close" aria-hidden="true">&times;</button> <form role="form">
MPD Password is set <div class="row">
<div class="form-group col-md-9">
<label class="control-label" for="mpdhost">MPD Host/IP</label>
<input type="text" class="form-control" id="mpdhost" />
</div>
<div class="form-group col-md-3">
<label class="control-label" for="mpdport">MPD Port</label>
<input type="text" class="form-control" id="mpdport" />
</div> </div>
</div> </div>
</div> <div class="row">
<div class="row"> <div class="form-group col-md-6">
<div class="form-group col-md-12"> <label class="control-label" for="mpd_pw">MPD Password</label>
<label class="control-label" for="mpdstream">MPD Stream URL</label> <input
<input type="text" class="form-control" id="mpdstream" /> type="password"
class="form-control"
id="mpd_pw"
placeholder="Password"
/>
</div>
<div class="form-group col-md-6">
<label class="control-label" for="mpd_pw_con"
>MPD Password (Confirmation)</label
>
<input
type="password"
class="form-control"
id="mpd_pw_con"
placeholder="Confirmation"
data-placement="right"
data-toggle="popover"
data-content="Password does not match!"
data-trigger="manual"
/>
</div>
<div class="form-group col-md-12">
<div id="mpd_password_set" class="hide alert alert-info">
<button type="button" class="close" aria-hidden="true">
&times;
</button>
MPD Password is set
</div>
</div>
</div>
<div class="row">
<div class="form-group col-md-12">
<label class="control-label" for="mpdstream"
>MPD Stream URL</label
>
<input type="text" class="form-control" id="mpdstream" />
</div>
</div>
</form>
<div class="row">
<div class="form-group col-md-12" data-toggle="buttons">
<button
type="button"
class="btn btn-default btn-block"
id="btnautoplay"
>
<span class="glyphicon glyphicon-play"></span> Autoplay stream
in this browser when mpd is playing
</button>
</div> </div>
</div>
</form>
<div class="row">
<div class="form-group col-md-12" data-toggle="buttons">
<button type="button" class="btn btn-default btn-block" id="btnautoplay">
<span class="glyphicon glyphicon-play"></span> Autoplay stream in this browser when mpd is playing
</button>
</div> </div>
</div> </div>
<div class="modal-footer">
<button type="button" class="btn btn-default" data-dismiss="modal">
Cancel
</button>
<button
type="button"
class="btn btn-default"
onclick="confirmSettings();"
>
Save
</button>
</div>
</div> </div>
<div class="modal-footer"> <!-- /.modal-content -->
<button type="button" class="btn btn-default" data-dismiss="modal">Cancel</button> </div>
<button type="button" class="btn btn-default" onclick="confirmSettings();">Save</button> <!-- /.modal-dialog -->
</div> </div>
</div><!-- /.modal-content --> <!-- /.modal -->
</div><!-- /.modal-dialog -->
</div><!-- /.modal -->
<!-- Modal --> <!-- Modal -->
<div class="modal fade" id="addstream" tabindex="-1" role="dialog" aria-labelledby="addstreamLabel" aria-hidden="true"> <div
<div class="modal-dialog"> class="modal fade"
<div class="modal-content"> id="addstream"
<div class="modal-header"> tabindex="-1"
<button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button> role="dialog"
<h2 class="modal-title" id="addstreamLabel"><span class="glyphicon glyphicon-wrench"></span> Add Stream</h2> aria-labelledby="addstreamLabel"
</div> aria-hidden="true"
<div class="modal-body"> >
<form role="form"> <div class="modal-dialog">
<div class="row"> <div class="modal-content">
<div class="form-group col-md-12"> <div class="modal-header">
<label class="control-label" for="streamurl">Stream URL</label> <button
<input type="text" class="form-control" id="streamurl" /> type="button"
class="close"
data-dismiss="modal"
aria-hidden="true"
>
&times;
</button>
<h2 class="modal-title" id="addstreamLabel">
<span class="glyphicon glyphicon-wrench"></span> Add Stream
</h2>
</div>
<div class="modal-body">
<form role="form">
<div class="row">
<div class="form-group col-md-12">
<label class="control-label" for="streamurl"
>Stream URL</label
>
<input type="text" class="form-control" id="streamurl" />
</div>
</div> </div>
</div> </form>
</form> </div>
<div class="modal-footer">
<button type="button" class="btn btn-default" data-dismiss="modal">
Cancel
</button>
<button
type="button"
class="btn btn-default"
onclick="addStream();"
>
Add Stream
</button>
</div>
</div> </div>
<div class="modal-footer"> <!-- /.modal-content -->
<button type="button" class="btn btn-default" data-dismiss="modal">Cancel</button> </div>
<button type="button" class="btn btn-default" onclick="addStream();">Add Stream</button> <!-- /.modal-dialog -->
</div> </div>
</div><!-- /.modal-content --> <!-- /.modal -->
</div><!-- /.modal-dialog -->
</div><!-- /.modal -->
<div class="modal fade" id="savequeue" tabindex="-1" role="dialog" aria-labelledby="savequeueLabel" aria-hidden="true"> <div
<div class="modal-dialog"> class="modal fade"
<div class="modal-content"> id="savequeue"
<div class="modal-header"> tabindex="-1"
<button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button> role="dialog"
<h2 class="modal-title" id="savequeueLabel"><span class="glyphicon glyphicon-wrench"></span> Save Queue</h2> aria-labelledby="savequeueLabel"
</div> aria-hidden="true"
<div class="modal-body"> >
<form role="form"> <div class="modal-dialog">
<div class="row"> <div class="modal-content">
<div class="form-group col-md-9"> <div class="modal-header">
<label class="control-label" for="playlistname">Playlist Name</label> <button
<input type="text" class="form-control" id="playlistname" /> type="button"
class="close"
data-dismiss="modal"
aria-hidden="true"
>
&times;
</button>
<h2 class="modal-title" id="savequeueLabel">
<span class="glyphicon glyphicon-wrench"></span> Save Queue
</h2>
</div>
<div class="modal-body">
<form role="form">
<div class="row">
<div class="form-group col-md-9">
<label class="control-label" for="playlistname"
>Playlist Name</label
>
<input type="text" class="form-control" id="playlistname" />
</div>
</div> </div>
</div> </form>
</form> </div>
<div class="modal-footer">
<button type="button" class="btn btn-default" data-dismiss="modal">
Cancel
</button>
<button
type="button"
class="btn btn-default"
onclick="saveQueue();"
>
Save Queue
</button>
</div>
</div> </div>
<div class="modal-footer"> <!-- /.modal-content -->
<button type="button" class="btn btn-default" data-dismiss="modal">Cancel</button> </div>
<button type="button" class="btn btn-default" onclick="saveQueue();">Save Queue</button> <!-- /.modal-dialog -->
</div> </div>
</div><!-- /.modal-content --> <!-- /.modal -->
</div><!-- /.modal-dialog -->
</div><!-- /.modal -->
<div class="modal fade bs-example-modal-sm" id="wait" tabindex="-1" role="dialog" data-backdrop="static" data-keyboard="false" aria-hidden="true"> <div
<div class="modal-dialog"> class="modal fade bs-example-modal-sm"
<div class="modal-content"> id="wait"
<div class="modal-header"> tabindex="-1"
<h1>Searching...</h1> role="dialog"
</div> data-backdrop="static"
<div class="modal-body"> data-keyboard="false"
<div class="progress progress-striped active"> aria-hidden="true"
<div class="progress-bar" role="progressbar" aria-valuenow="45" aria-valuemin="0" aria-valuemax="100" style="width: 100%"> >
<span class="sr-only">Please Wait</span> <div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<h1>Searching...</h1>
</div>
<div class="modal-body">
<div class="progress progress-striped active">
<div
class="progress-bar"
role="progressbar"
aria-valuenow="45"
aria-valuemin="0"
aria-valuemax="100"
style="width: 100%"
>
<span class="sr-only">Please Wait</span>
</div>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
</div>
<!-- Bootstrap core JavaScript
<!-- Bootstrap core JavaScript
================================================== --> ================================================== -->
<!-- Placed at the end of the document so the pages load faster --> <!-- Placed at the end of the document so the pages load faster -->
<script src="js/jquery-1.10.2.min.js"></script> <script src="js/jquery-1.10.2.min.js"></script>
<script src="js/jquery.cookie.js"></script> <script src="js/jquery.cookie.js"></script>
<script src="js/bootstrap.min.js"></script> <script src="js/bootstrap.min.js"></script>
<script src="js/bootstrap-notify.js"></script> <script src="js/bootstrap-notify.js"></script>
<script src="js/bootstrap-slider.js"></script> <script src="js/bootstrap-slider.js"></script>
<script src="js/sammy.js"></script> <script src="js/sammy.js"></script>
<script src="js/jquery-ui-sortable.min.js"></script> <script src="js/jquery-ui-sortable.min.js"></script>
<script src="js/mpd.js"></script> <script src="js/mpd.js"></script>
</body> </body>
</html> </html>

File diff suppressed because it is too large Load Diff

View File

@ -1,126 +1,168 @@
<!DOCTYPE html> <!DOCTYPE html>
<html lang="en"> <html lang="en">
<head> <head>
<meta charset="utf-8"> <meta charset="utf-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge"> <meta http-equiv="X-UA-Compatible" content="IE=edge" />
<!-- <meta name="viewport" content="width=device-width, initial-scale=1.0">--> <!-- <meta name="viewport" content="width=device-width, initial-scale=1.0">-->
<meta name="viewport" content="width=320"> <meta name="viewport" content="width=320" />
<meta name="description" content="ympd - fast and lightweight MPD webclient"> <meta
<meta name="author" content="andy@ndyk.de"> name="description"
content="ympd - fast and lightweight MPD webclient"
/>
<meta name="author" content="andy@ndyk.de" />
<title>ympd player</title> <title>ympd player</title>
<!-- Bootstrap core CSS --> <!-- Bootstrap core CSS -->
<link href="css/bootstrap.css" rel="stylesheet"> <link href="css/bootstrap.css" rel="stylesheet" />
<link href="css/bootstrap-theme.css" rel="stylesheet"> <link href="css/bootstrap-theme.css" rel="stylesheet" />
<!-- Custom styles for this template --> <!-- Custom styles for this template -->
<link href="css/mpd.css" rel="stylesheet"> <link href="css/mpd.css" rel="stylesheet" />
<link href="assets/favicon.ico" rel="shortcut icon" type="image/vnd.microsoft.icon"> <link
<script src="js/jquery-1.10.2.min.js"></script> href="assets/favicon.ico"
<script src="js/jquery.cookie.js"></script> rel="shortcut icon"
<script src="js/bootstrap.min.js"></script> type="image/vnd.microsoft.icon"
<script src="js/bootstrap-notify.js"></script> />
<script type="text/javascript"> <script src="js/jquery-1.10.2.min.js"></script>
function clickLocalPlay() { <script src="js/jquery.cookie.js"></script>
var player = document.getElementById('player'); <script src="js/bootstrap.min.js"></script>
$("#localplay-icon").removeClass("glyphicon-play").removeClass("glyphicon-pause"); <script src="js/bootstrap-notify.js"></script>
<script type="text/javascript">
function clickLocalPlay() {
var player = document.getElementById('player');
$('#localplay-icon')
.removeClass('glyphicon-play')
.removeClass('glyphicon-pause');
if (player.paused) {
var mpdstream = $.cookie('mpdstream');
player.src = mpdstream;
console.log('playing mpd stream: ' + player.src);
player.load();
player.play();
$('#localplay-icon').addClass('glyphicon-pause');
} else {
player.pause();
player.src = '';
player.removeAttribute('src');
$('#localplay-icon').addClass('glyphicon-play');
}
}
if ( player.paused ) { $(document).ready(function () {
var mpdstream = $.cookie("mpdstream"); document
player.src = mpdstream; .getElementById('player')
console.log("playing mpd stream: " + player.src); .addEventListener('stalled', function () {
player.load(); if (!document.getElementById('player').paused) {
player.play(); this.pause();
$("#localplay-icon").addClass("glyphicon-pause"); clickLocalPlay();
} else { $('.top-right')
player.pause(); .notify({
player.src=''; message: {
player.removeAttribute("src"); text: 'music stream stalled - trying to recover...',
$("#localplay-icon").addClass("glyphicon-play"); },
} type: 'danger',
} fadeOut: { enabled: true, delay: 1000 },
})
.show();
}
});
$(document).ready(function(){ document
document.getElementById('player').addEventListener('stalled', function() { .getElementById('player')
if ( !document.getElementById('player').paused ) { .addEventListener('pause', function () {
this.pause(); this.src = '';
clickLocalPlay(); this.removeAttribute('src');
$('.top-right').notify({ $('#localplay-icon')
message:{text:"music stream stalled - trying to recover..."}, .removeClass('glyphicon-pause')
type: "danger", .addClass('glyphicon-play');
fadeOut: { enabled: true, delay: 1000 }, });
}).show();
}
});
document.getElementById('player').addEventListener('pause', function() { document.getElementById('player').addEventListener(
this.src=''; 'error',
this.removeAttribute("src"); function failed(e) {
$("#localplay-icon").removeClass("glyphicon-pause").addClass("glyphicon-play"); this.pause();
}); switch (e.target.error.code) {
case e.target.error.MEDIA_ERR_ABORTED:
document.getElementById('player').addEventListener('error', function failed(e) { $('.top-right')
this.pause(); .notify({
switch (e.target.error.code) { message: { text: 'Audio playback aborted by user.' },
case e.target.error.MEDIA_ERR_ABORTED: type: 'info',
$('.top-right').notify({ fadeOut: { enabled: true, delay: 1000 },
message:{text:"Audio playback aborted by user."}, })
type: "info", .show();
fadeOut: { enabled: true, delay: 1000 }, break;
}).show(); case e.target.error.MEDIA_ERR_NETWORK:
break; $('.top-right')
case e.target.error.MEDIA_ERR_NETWORK: .notify({
$('.top-right').notify({ message: { text: 'Network error while playing audio.' },
message:{text:"Network error while playing audio."}, type: 'danger',
type: "danger", fadeOut: { enabled: true, delay: 1000 },
fadeOut: { enabled: true, delay: 1000 }, })
}).show(); .show();
break; break;
case e.target.error.MEDIA_ERR_DECODE: case e.target.error.MEDIA_ERR_DECODE:
$('.top-right').notify({ $('.top-right')
message:{text:"Audio playback aborted. Did you unplug your headphones?"}, .notify({
type: "danger", message: {
fadeOut: { enabled: true, delay: 1000 }, text: 'Audio playback aborted. Did you unplug your headphones?',
}).show(); },
break; type: 'danger',
case e.target.error.MEDIA_ERR_SRC_NOT_SUPPORTED: fadeOut: { enabled: true, delay: 1000 },
$('.top-right').notify({ })
message:{text:"Error while loading audio (server, network or format error)."}, .show();
type: "danger", break;
fadeOut: { enabled: true, delay: 1000 }, case e.target.error.MEDIA_ERR_SRC_NOT_SUPPORTED:
}).show(); $('.top-right')
break; .notify({
default: message: {
$('.top-right').notify({ text: 'Error while loading audio (server, network or format error).',
message:{text:"Unknown error while playing audio."}, },
type: "danger", type: 'danger',
fadeOut: { enabled: true, delay: 1000 }, fadeOut: { enabled: true, delay: 1000 },
}).show(); })
break; .show();
} break;
}, true); default:
}); $('.top-right')
</script> .notify({
</head> message: { text: 'Unknown error while playing audio.' },
<body> type: 'danger',
<div class="navbar navbar-inverse navbar-fixed-top" role="navigation"> fadeOut: { enabled: true, delay: 1000 },
<div class="container"> })
<a class="navbar-brand" href="/" target="_blank"><span class="glyphicon glyphicon-play-circle"></span> ympd</a> .show();
</div> break;
</div> }
},
<div class="container starter-template"> true
<div class="row"> );
<div class="col-md-10 col-xs-12"> });
<audio id="player" preload="none"></audio> </script>
<button type="button" class="btn btn-default btn-lg center-block" onclick="clickLocalPlay()"> </head>
<span id="localplay-icon" class="glyphicon glyphicon-play"></span> <body>
</button> <div class="navbar navbar-inverse navbar-fixed-top" role="navigation">
<div class="notifications top-right"></div> <div class="container">
<a class="navbar-brand" href="/" target="_blank"
><span class="glyphicon glyphicon-play-circle"></span> ympd</a
>
</div> </div>
</div> </div>
</div>
</body> <div class="container starter-template">
<div class="row">
<div class="col-md-10 col-xs-12">
<audio id="player" preload="none"></audio>
<button
type="button"
class="btn btn-default btn-lg center-block"
onclick="clickLocalPlay()"
>
<span id="localplay-icon" class="glyphicon glyphicon-play"></span>
</button>
<div class="notifications top-right"></div>
</div>
</div>
</div>
</body>
</html> </html>