mirror of
https://gitlab.crans.org/nounous/ghostream.git
synced 2024-12-22 15:02:19 +00:00
Style player in seperate CSS file
This commit is contained in:
parent
8de28e4781
commit
064e35935d
84
web/static/css/player.css
Normal file
84
web/static/css/player.css
Normal file
@ -0,0 +1,84 @@
|
|||||||
|
/* Player */
|
||||||
|
.video-responsive {
|
||||||
|
position: relative;
|
||||||
|
padding-top: 56.25%; /* 16/9 */
|
||||||
|
}
|
||||||
|
|
||||||
|
.video-responsive video {
|
||||||
|
position: absolute;
|
||||||
|
top: 0;
|
||||||
|
bottom: 0;
|
||||||
|
left: 0;
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
max-height: 90vh;
|
||||||
|
|
||||||
|
/* Black borders when video is not 16/9 */
|
||||||
|
background-color: #000;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Controls under the player */
|
||||||
|
.controls {
|
||||||
|
background: #0A1A28;
|
||||||
|
padding: 0.2rem 0.5rem;
|
||||||
|
color: rgb(187, 187, 187);
|
||||||
|
user-select: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
.control-quality,
|
||||||
|
.control-srt-link,
|
||||||
|
.control-viewers,
|
||||||
|
.control-indicator,
|
||||||
|
.control-chat {
|
||||||
|
white-space: nowrap;
|
||||||
|
margin-left: 0.5rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Control icons */
|
||||||
|
.control-quality::before,
|
||||||
|
.control-srt-link::before,
|
||||||
|
.control-viewers::before {
|
||||||
|
content: "";
|
||||||
|
display: inline-block;
|
||||||
|
width: 16px;
|
||||||
|
height: 16px;
|
||||||
|
margin-right: 0.2rem;
|
||||||
|
vertical-align: middle;
|
||||||
|
}
|
||||||
|
|
||||||
|
.control-quality::before {
|
||||||
|
background: transparent url("data:image/svg+xml;utf8,<svg fill='rgb(187, 187, 187)' width='16' height='16' viewBox='0 0 16 16' xmlns='http://www.w3.org/2000/svg'><path fill-rule='evenodd' d='M1.5 2A1.5 1.5 0 0 0 0 3.5v9A1.5 1.5 0 0 0 1.5 14h13a1.5 1.5 0 0 0 1.5-1.5v-9A1.5 1.5 0 0 0 14.5 2h-13zm1 2a.5.5 0 0 0-.5.5v3a.5.5 0 0 0 1 0V5h2.5a.5.5 0 0 0 0-1h-3zm11 8a.5.5 0 0 0 .5-.5v-3a.5.5 0 0 0-1 0V11h-2.5a.5.5 0 0 0 0 1h3z'/></svg>") no-repeat;
|
||||||
|
}
|
||||||
|
|
||||||
|
.control-srt-link::before {
|
||||||
|
background: transparent url("data:image/svg+xml;utf8,<svg fill='rgb(187, 187, 187)' width='16' height='16' viewBox='0 0 16 16' xmlns='http://www.w3.org/2000/svg'><path d='M1.5 13A1.5 1.5 0 0 0 3 14.5h8a1.5 1.5 0 0 0 1.5-1.5V9a.5.5 0 0 0-1 0v4a.5.5 0 0 1-.5.5H3a.5.5 0 0 1-.5-.5V5a.5.5 0 0 1 .5-.5h4a.5.5 0 0 0 0-1H3A1.5 1.5 0 0 0 1.5 5v8zm7-11a.5.5 0 0 1 .5-.5h5a.5.5 0 0 1 .5.5v5a.5.5 0 0 1-1 0V2.5H9a.5.5 0 0 1-.5-.5z' /><path d='M14.354 1.646a.5.5 0 0 1 0 .708l-8 8a.5.5 0 0 1-.708-.708l8-8a.5.5 0 0 1 .708 0z'/></svg>") no-repeat;
|
||||||
|
}
|
||||||
|
|
||||||
|
.control-viewers::before {
|
||||||
|
background: transparent url("data:image/svg+xml;utf8,<svg fill='rgb(187, 187, 187)' width='16' height='16' viewBox='0 0 20 20' xmlns='http://www.w3.org/2000/svg'><path d='M10 11c-5.92 0-8 3-8 5v3h16v-3c0-2-2.08-5-8-5z'/><circle cx='10' cy='5.5' r='4.5'/></svg>") no-repeat;
|
||||||
|
}
|
||||||
|
|
||||||
|
.control-indicator {
|
||||||
|
vertical-align: middle;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Custom select */
|
||||||
|
.control-quality select {
|
||||||
|
border: none;
|
||||||
|
color: inherit;
|
||||||
|
appearance: none;
|
||||||
|
|
||||||
|
/* Custom caret */
|
||||||
|
background: transparent url("data:image/svg+xml;utf8,<svg fill='rgb(187, 187, 187)' width='10' height='5' viewBox='0 0 10 5' xmlns='http://www.w3.org/2000/svg'><path d='m0 0 5 5 5-5z'/></svg>") no-repeat right;
|
||||||
|
padding-right: 0.8rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Hide chat toggler on small screen */
|
||||||
|
.control-chat {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
@media(min-width:1000px){
|
||||||
|
.control-chat {
|
||||||
|
display: inline;
|
||||||
|
}
|
||||||
|
}
|
@ -1,3 +1,5 @@
|
|||||||
|
/* Commun style */
|
||||||
|
|
||||||
body, html {
|
body, html {
|
||||||
height: 100%;
|
height: 100%;
|
||||||
margin: 0;
|
margin: 0;
|
||||||
@ -5,13 +7,12 @@ body, html {
|
|||||||
|
|
||||||
body {
|
body {
|
||||||
background-color: #3b4b5b;
|
background-color: #3b4b5b;
|
||||||
font-family: "Segoe UI", Roboto, "Helvetica Neue", Arial, "Noto Sans", sans-serif;
|
font-family: sans-serif;
|
||||||
font-size: 1rem;
|
font-size: 1rem;
|
||||||
font-weight: 400;
|
font-weight: 400;
|
||||||
line-height: 1.5;
|
line-height: 1.5;
|
||||||
color: #bbb;
|
color: #bbb;
|
||||||
text-align: justify;
|
text-align: justify;
|
||||||
user-select: none;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
p {
|
p {
|
||||||
@ -20,14 +21,10 @@ p {
|
|||||||
}
|
}
|
||||||
|
|
||||||
code {
|
code {
|
||||||
font-size: 87.5%;
|
font-family: monospace;
|
||||||
|
font-size: 10pt;
|
||||||
word-break: break-word;
|
word-break: break-word;
|
||||||
user-select: text;
|
user-select: all;
|
||||||
}
|
|
||||||
|
|
||||||
svg {
|
|
||||||
overflow: hidden;
|
|
||||||
vertical-align: middle;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
a {
|
a {
|
||||||
@ -44,19 +41,6 @@ h1, h2, h3, h4 {
|
|||||||
color: #ddd;
|
color: #ddd;
|
||||||
}
|
}
|
||||||
|
|
||||||
select {
|
|
||||||
border: none;
|
|
||||||
color: inherit;
|
|
||||||
appearance: none;
|
|
||||||
|
|
||||||
/* Custom caret */
|
|
||||||
background-color: transparent;
|
|
||||||
background-image: url("data:image/svg+xml;utf8,<svg fill='rgb(187, 187, 187)' height='24' viewBox='0 1 24 24' width='24' xmlns='http://www.w3.org/2000/svg'><path d='M7 10l5 5 5-5z'/></svg>");
|
|
||||||
background-repeat: no-repeat;
|
|
||||||
background-position-x: 100%;
|
|
||||||
padding-right: 1.2rem;
|
|
||||||
}
|
|
||||||
|
|
||||||
.container {
|
.container {
|
||||||
height: 100%;
|
height: 100%;
|
||||||
width: 100%;
|
width: 100%;
|
||||||
@ -76,24 +60,6 @@ select {
|
|||||||
max-width: 1200px;
|
max-width: 1200px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.video-responsive {
|
|
||||||
position: relative;
|
|
||||||
padding-top: 56.25%; /* 16/9 */
|
|
||||||
}
|
|
||||||
|
|
||||||
.video-responsive video {
|
|
||||||
position: absolute;
|
|
||||||
top: 0;
|
|
||||||
bottom: 0;
|
|
||||||
left: 0;
|
|
||||||
width: 100%;
|
|
||||||
height: 100%;
|
|
||||||
max-height: 90vh;
|
|
||||||
|
|
||||||
/* Black borders when video is not 16/9 */
|
|
||||||
background-color: #000;
|
|
||||||
}
|
|
||||||
|
|
||||||
.col-chat {
|
.col-chat {
|
||||||
position: relative;
|
position: relative;
|
||||||
width: 100%;
|
width: 100%;
|
||||||
@ -111,23 +77,10 @@ select {
|
|||||||
border: 0;
|
border: 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
.ml-1 {
|
|
||||||
margin-left: 0.5rem;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Hide chat toggler on small screen */
|
|
||||||
#sideWidgetToggle {
|
|
||||||
display: none;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* On large screen, put chat on left */
|
/* On large screen, put chat on left */
|
||||||
@media(min-width:1000px){
|
@media(min-width:1000px){
|
||||||
.col-chat {
|
.col-chat {
|
||||||
width: 33.33333%;
|
width: 33.33333%;
|
||||||
flex: 0 0 33.33333%;
|
flex: 0 0 33.33333%;
|
||||||
}
|
}
|
||||||
|
|
||||||
#sideWidgetToggle {
|
|
||||||
display: inline;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
@ -6,12 +6,13 @@
|
|||||||
<meta charset="UTF-8">
|
<meta charset="UTF-8">
|
||||||
<title>{{if .Path}}{{if not .Cfg.OneStreamPerDomain}}{{.Path}} - {{end}}{{end}}{{.Cfg.Name}}</title>
|
<title>{{if .Path}}{{if not .Cfg.OneStreamPerDomain}}{{.Path}} - {{end}}{{end}}{{.Cfg.Name}}</title>
|
||||||
<link rel="stylesheet" href="static/css/style.css">
|
<link rel="stylesheet" href="static/css/style.css">
|
||||||
|
<link rel="stylesheet" href="static/css/player.css">
|
||||||
<link rel="shortcut icon" href="{{.Cfg.Favicon}}">
|
<link rel="shortcut icon" href="{{.Cfg.Favicon}}">
|
||||||
</head>
|
</head>
|
||||||
|
|
||||||
<body>
|
<body>
|
||||||
{{if .Path}}
|
{{if .Path}}
|
||||||
{{template "viewer" .}}
|
{{template "player" .}}
|
||||||
{{else}}
|
{{else}}
|
||||||
{{template "index" .}}
|
{{template "index" .}}
|
||||||
{{end}}
|
{{end}}
|
||||||
|
56
web/template/player.html
Normal file
56
web/template/player.html
Normal file
@ -0,0 +1,56 @@
|
|||||||
|
{{define "player"}}
|
||||||
|
<div class="container">
|
||||||
|
<div class="col-video">
|
||||||
|
<!-- Video -->
|
||||||
|
<div class="video-responsive">
|
||||||
|
<video id="viewer" poster="/static/img/no_stream.svg" muted controls autoplay></video>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<!-- Links and settings under video -->
|
||||||
|
<div class="controls">
|
||||||
|
<span class="control-quality">
|
||||||
|
<select id="quality">
|
||||||
|
<option value="">Source</option>
|
||||||
|
<option value="@720p">720p</option>
|
||||||
|
<option value="@480p">480p</option>
|
||||||
|
<option value="@240p">240p</option>
|
||||||
|
</select>
|
||||||
|
</span>
|
||||||
|
<code class="control-srt-link">srt://{{.Cfg.Hostname}}:{{.Cfg.SRTServerPort}}?streamid={{.Path}}</code>
|
||||||
|
<span class="control-viewers" id="connected-people">0</span>
|
||||||
|
<svg class="control-indicator" id="connectionIndicator" fill="#dc3545" width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg">
|
||||||
|
<rect width="4" height="5" x="1" y="10" rx="1"/>
|
||||||
|
<rect width="4" height="9" x="6" y="6" rx="1"/>
|
||||||
|
<rect width="4" height="14" x="11" y="1" rx="1"/>
|
||||||
|
</svg>
|
||||||
|
{{if .WidgetURL}}<a class="control-chat" id="sideWidgetToggle" href="#" title="Cacher/Afficher le chat">»</a>{{end}}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
{{if .WidgetURL}}
|
||||||
|
<!-- Chat -->
|
||||||
|
<div class="col-chat" id="sideWidget">
|
||||||
|
<iframe src="{{.WidgetURL}}"
|
||||||
|
title="Chat" sandbox="allow-scripts allow-forms allow-same-origin"></iframe>
|
||||||
|
</div>
|
||||||
|
{{end}}
|
||||||
|
</div>
|
||||||
|
|
||||||
|
{{if .WidgetURL}}<script src="/static/js/sideWidget.js"></script>{{end}}
|
||||||
|
<script src="/static/js/videoQuality.js"></script>
|
||||||
|
<script src="/static/js/viewer.js"></script>
|
||||||
|
<script src="/static/js/viewersCounter.js"></script>
|
||||||
|
<script>
|
||||||
|
const stunServers = [
|
||||||
|
{{range $id, $value := .Cfg.STUNServers}}
|
||||||
|
'{{$value}}',
|
||||||
|
{{end}}
|
||||||
|
]
|
||||||
|
startPeerConnection()
|
||||||
|
|
||||||
|
// Wait a bit before pulling viewers counter for the first time
|
||||||
|
setTimeout(() => {
|
||||||
|
refreshViewersCounter({{.Cfg.ViewersCounterRefreshPeriod}})
|
||||||
|
}, 1000)
|
||||||
|
</script>
|
||||||
|
{{end}}
|
@ -1,73 +0,0 @@
|
|||||||
{{define "viewer"}}
|
|
||||||
<div class="container">
|
|
||||||
<div class="col-video">
|
|
||||||
<!-- Video -->
|
|
||||||
<div class="video-responsive">
|
|
||||||
<video id="viewer" poster="/static/img/no_stream.svg" muted controls autoplay></video>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<!-- Links and settings under video -->
|
|
||||||
<p>
|
|
||||||
<svg width="1em" height="1em" viewBox="0 0 16 16" class="bi bi-aspect-ratio-fill" fill="currentColor" xmlns="http://www.w3.org/2000/svg">
|
|
||||||
<path fill-rule="evenodd" d="M1.5 2A1.5 1.5 0 0 0 0 3.5v9A1.5 1.5 0 0 0 1.5 14h13a1.5 1.5 0 0 0 1.5-1.5v-9A1.5 1.5 0 0 0 14.5 2h-13zm1 2a.5.5 0 0 0-.5.5v3a.5.5 0 0 0 1 0V5h2.5a.5.5 0 0 0 0-1h-3zm11 8a.5.5 0 0 0 .5-.5v-3a.5.5 0 0 0-1 0V11h-2.5a.5.5 0 0 0 0 1h3z"/>
|
|
||||||
</svg>
|
|
||||||
<select id="quality">
|
|
||||||
<option value="">Source</option>
|
|
||||||
<option value="@720p">720p</option>
|
|
||||||
<option value="@480p">480p</option>
|
|
||||||
<option value="@240p">240p</option>
|
|
||||||
</select>
|
|
||||||
|
|
||||||
<svg class="ml-1" width="1em" height="1em" viewBox="0 0 16 16" class="bi bi-box-arrow-up-right" fill="#d7d7d7" xmlns="http://www.w3.org/2000/svg">
|
|
||||||
<path fill-rule="evenodd"
|
|
||||||
d="M1.5 13A1.5 1.5 0 0 0 3 14.5h8a1.5 1.5 0 0 0 1.5-1.5V9a.5.5 0 0 0-1 0v4a.5.5 0 0 1-.5.5H3a.5.5 0 0 1-.5-.5V5a.5.5 0 0 1 .5-.5h4a.5.5 0 0 0 0-1H3A1.5 1.5 0 0 0 1.5 5v8zm7-11a.5.5 0 0 1 .5-.5h5a.5.5 0 0 1 .5.5v5a.5.5 0 0 1-1 0V2.5H9a.5.5 0 0 1-.5-.5z" />
|
|
||||||
<path fill-rule="evenodd"
|
|
||||||
d="M14.354 1.646a.5.5 0 0 1 0 .708l-8 8a.5.5 0 0 1-.708-.708l8-8a.5.5 0 0 1 .708 0z" />
|
|
||||||
</svg>
|
|
||||||
<code>srt://{{.Cfg.Hostname}}:{{.Cfg.SRTServerPort}}?streamid={{.Path}}</code>
|
|
||||||
|
|
||||||
<svg class="ml-1" width="1em" height="1em" viewBox="0 0 20 20" fill="#d7d7d7" xmlns="http://www.w3.org/2000/svg">
|
|
||||||
<path d="M10 11c-5.92 0-8 3-8 5v3h16v-3c0-2-2.08-5-8-5z"/>
|
|
||||||
<circle cx="10" cy="5.5" r="4.5"/>
|
|
||||||
</svg>
|
|
||||||
<span id="connected-people">0</span>
|
|
||||||
|
|
||||||
<svg id="connectionIndicator" class="ml-1" width="1em" height="1em" viewBox="0 0 16 16" fill="#dc3545" xmlns="http://www.w3.org/2000/svg">
|
|
||||||
<rect width="4" height="5" x="1" y="10" rx="1"/>
|
|
||||||
<rect width="4" height="9" x="6" y="6" rx="1"/>
|
|
||||||
<rect width="4" height="14" x="11" y="1" rx="1"/>
|
|
||||||
</svg>
|
|
||||||
|
|
||||||
{{if .WidgetURL}}
|
|
||||||
<a href="#" id="sideWidgetToggle" class="ml-1" title="Cacher/Afficher le chat">»</a>
|
|
||||||
{{end}}
|
|
||||||
</p>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
{{if .WidgetURL}}
|
|
||||||
<!-- Chat -->
|
|
||||||
<div class="col-chat" id="sideWidget">
|
|
||||||
<iframe src="{{.WidgetURL}}"
|
|
||||||
title="Chat" sandbox="allow-scripts allow-forms allow-same-origin"></iframe>
|
|
||||||
</div>
|
|
||||||
{{end}}
|
|
||||||
</div>
|
|
||||||
|
|
||||||
{{if .WidgetURL}}<script src="/static/js/sideWidget.js"></script>{{end}}
|
|
||||||
<script src="/static/js/videoQuality.js"></script>
|
|
||||||
<script src="/static/js/viewer.js"></script>
|
|
||||||
<script src="/static/js/viewersCounter.js"></script>
|
|
||||||
<script>
|
|
||||||
const stunServers = [
|
|
||||||
{{range $id, $value := .Cfg.STUNServers}}
|
|
||||||
'{{$value}}',
|
|
||||||
{{end}}
|
|
||||||
]
|
|
||||||
startPeerConnection()
|
|
||||||
|
|
||||||
// Wait a bit before pulling viewers counter for the first time
|
|
||||||
setTimeout(() => {
|
|
||||||
refreshViewersCounter({{.Cfg.ViewersCounterRefreshPeriod}})
|
|
||||||
}, 1000)
|
|
||||||
</script>
|
|
||||||
{{end}}
|
|
Loading…
Reference in New Issue
Block a user