Merge branch 'ciderapp:upcoming' into upcoming
This commit is contained in:
commit
32db847a5a
10 changed files with 713 additions and 25 deletions
130
CODE_OF_CONDUCT.md
Normal file
130
CODE_OF_CONDUCT.md
Normal file
|
@ -0,0 +1,130 @@
|
||||||
|
# Contributor Covenant Code of Conduct
|
||||||
|
|
||||||
|
## Our Pledge
|
||||||
|
|
||||||
|
We as members, contributors, and leaders pledge to make participation in our
|
||||||
|
community a harassment-free experience for everyone, regardless of age, body
|
||||||
|
size, visible or invisible disability, ethnicity, sex characteristics, gender
|
||||||
|
identity and expression, level of experience, education, socio-economic status,
|
||||||
|
nationality, personal appearance, race, religion, or sexual identity
|
||||||
|
and orientation.
|
||||||
|
|
||||||
|
We pledge to act and interact in ways that contribute to an open, welcoming,
|
||||||
|
diverse, inclusive, and healthy community.
|
||||||
|
|
||||||
|
## Our Standards
|
||||||
|
|
||||||
|
Examples of behavior that contributes to a positive environment for our
|
||||||
|
community include:
|
||||||
|
|
||||||
|
* Demonstrating empathy and kindness toward other people
|
||||||
|
* Being respectful of differing opinions, viewpoints, and experiences
|
||||||
|
* Giving and gracefully accepting constructive feedback
|
||||||
|
* Accepting responsibility and apologizing to those affected by our mistakes,
|
||||||
|
and learning from the experience
|
||||||
|
* Focusing on what is best not just for us as individuals, but for the
|
||||||
|
overall community
|
||||||
|
|
||||||
|
Examples of unacceptable behavior include:
|
||||||
|
|
||||||
|
* The use of sexualized language or imagery, and sexual attention or
|
||||||
|
advances of any kind
|
||||||
|
* Trolling, insulting or derogatory comments, and personal or political attacks
|
||||||
|
* Public or private harassment
|
||||||
|
* Publishing others' private information, such as a physical or email
|
||||||
|
address, without their explicit permission
|
||||||
|
* Other conduct which could reasonably be considered inappropriate in a
|
||||||
|
professional setting
|
||||||
|
|
||||||
|
> Threats made to someone's wellbeing, especially towards self-harm or sucide, will be automatically be dealt with as a maximum level offense, no matter the reasoning.
|
||||||
|
|
||||||
|
## Enforcement Responsibilities
|
||||||
|
|
||||||
|
Community leaders are responsible for clarifying and enforcing our standards of
|
||||||
|
acceptable behavior and will take appropriate and fair corrective action in
|
||||||
|
response to any behavior that they deem inappropriate, threatening, offensive,
|
||||||
|
or harmful.
|
||||||
|
|
||||||
|
Community leaders have the right and responsibility to remove, edit, or reject
|
||||||
|
comments, commits, code, wiki edits, issues, and other contributions that are
|
||||||
|
not aligned to this Code of Conduct, and will communicate reasons for moderation
|
||||||
|
decisions when appropriate.
|
||||||
|
|
||||||
|
## Scope
|
||||||
|
|
||||||
|
This Code of Conduct applies within all community spaces, and also applies when
|
||||||
|
an individual is officially representing the community in public spaces.
|
||||||
|
Examples of representing our community include using an official e-mail address,
|
||||||
|
posting via an official social media account, or acting as an appointed
|
||||||
|
representative at an online or offline event.
|
||||||
|
|
||||||
|
## Enforcement
|
||||||
|
|
||||||
|
Instances of abusive, harassing, or otherwise unacceptable behavior may be
|
||||||
|
reported to the community leaders responsible for enforcement at
|
||||||
|
cryptofyre@cider.sh.
|
||||||
|
All complaints will be reviewed and investigated promptly and fairly.
|
||||||
|
|
||||||
|
All community leaders are obligated to respect the privacy and security of the
|
||||||
|
reporter of any incident.
|
||||||
|
|
||||||
|
## Enforcement Guidelines
|
||||||
|
|
||||||
|
Community leaders will follow these Community Impact Guidelines in determining
|
||||||
|
the consequences for any action they deem in violation of this Code of Conduct:
|
||||||
|
|
||||||
|
### 1. Correction
|
||||||
|
|
||||||
|
**Community Impact**: Use of inappropriate language or other behavior deemed
|
||||||
|
unprofessional or unwelcome in the community.
|
||||||
|
|
||||||
|
**Consequence**: A private, written warning from community leaders, providing
|
||||||
|
clarity around the nature of the violation and an explanation of why the
|
||||||
|
behavior was inappropriate. A public apology may be requested.
|
||||||
|
|
||||||
|
### 2. Warning
|
||||||
|
|
||||||
|
**Community Impact**: A violation through a single incident or series
|
||||||
|
of actions.
|
||||||
|
|
||||||
|
**Consequence**: A warning with consequences for continued behavior. No
|
||||||
|
interaction with the people involved, including unsolicited interaction with
|
||||||
|
those enforcing the Code of Conduct, for a specified period of time. This
|
||||||
|
includes avoiding interactions in community spaces as well as external channels
|
||||||
|
like social media. Violating these terms may lead to a temporary or
|
||||||
|
permanent ban.
|
||||||
|
|
||||||
|
### 3. Temporary Ban
|
||||||
|
|
||||||
|
**Community Impact**: A serious violation of community standards, including
|
||||||
|
sustained inappropriate behavior.
|
||||||
|
|
||||||
|
**Consequence**: A temporary ban from any sort of interaction or public
|
||||||
|
communication with the community for a specified period of time. No public or
|
||||||
|
private interaction with the people involved, including unsolicited interaction
|
||||||
|
with those enforcing the Code of Conduct, is allowed during this period.
|
||||||
|
Violating these terms may lead to a permanent ban.
|
||||||
|
|
||||||
|
### 4. Permanent Ban
|
||||||
|
|
||||||
|
**Community Impact**: Demonstrating a pattern of violation of community
|
||||||
|
standards, including sustained inappropriate behavior, harassment of an
|
||||||
|
individual, or aggression toward or disparagement of classes of individuals.
|
||||||
|
|
||||||
|
**Consequence**: A permanent ban from any sort of public interaction within
|
||||||
|
the community.
|
||||||
|
|
||||||
|
## Attribution
|
||||||
|
|
||||||
|
This Code of Conduct is adapted from the [Contributor Covenant][homepage],
|
||||||
|
version 2.0, available at
|
||||||
|
https://www.contributor-covenant.org/version/2/0/code_of_conduct.html.
|
||||||
|
|
||||||
|
Community Impact Guidelines were inspired by [Mozilla's code of conduct
|
||||||
|
enforcement ladder](https://github.com/mozilla/diversity).
|
||||||
|
|
||||||
|
[homepage]: https://www.contributor-covenant.org
|
||||||
|
|
||||||
|
For answers to common questions about this code of conduct, see the FAQ at
|
||||||
|
https://www.contributor-covenant.org/faq. Translations are available at
|
||||||
|
https://www.contributor-covenant.org/translations.
|
|
@ -1,6 +1,5 @@
|
||||||
import * as electron from 'electron';
|
import * as electron from 'electron';
|
||||||
import * as path from 'path';
|
import * as path from 'path';
|
||||||
|
|
||||||
export class AppEvents {
|
export class AppEvents {
|
||||||
private static protocols: any = [
|
private static protocols: any = [
|
||||||
"ame",
|
"ame",
|
||||||
|
@ -125,45 +124,28 @@ export class AppEvents {
|
||||||
}
|
}
|
||||||
// Play
|
// Play
|
||||||
else if (arg.includes('/play/')) { //Steer away from protocol:// specific conditionals
|
else if (arg.includes('/play/')) { //Steer away from protocol:// specific conditionals
|
||||||
|
|
||||||
const playParam = arg.split('/play/')[1]
|
const playParam = arg.split('/play/')[1]
|
||||||
if (playParam.includes('s/')) { // song
|
if (playParam.includes('s/')) { // song
|
||||||
console.log(playParam)
|
console.log(playParam)
|
||||||
let song = playParam.split('s/')[1]
|
let song = playParam.split('s/')[1]
|
||||||
console.warn(`[LinkHandler] Attempting to load song by id: ${song}`);
|
console.warn(`[LinkHandler] Attempting to load song by id: ${song}`);
|
||||||
// AppEvents.window.webContents.executeJavaScript(`
|
electron.ipcRenderer.send('play', 'song', song)
|
||||||
// MusicKit.getInstance().setQueue({ song: '${song}'}).then(function(queue) {
|
|
||||||
// MusicKit.getInstance().play();
|
|
||||||
// });
|
|
||||||
// `)
|
|
||||||
} else if (playParam.includes('a/')) { // album
|
} else if (playParam.includes('a/')) { // album
|
||||||
console.log(playParam)
|
console.log(playParam)
|
||||||
let album = playParam.split('a/')[1]
|
let album = playParam.split('a/')[1]
|
||||||
console.warn(`[LinkHandler] Attempting to load album by id: ${album}`);
|
console.warn(`[LinkHandler] Attempting to load album by id: ${album}`);
|
||||||
// AppEvents.window.webContents.executeJavaScript(`
|
electron.ipcRenderer.send('play', 'album', album)
|
||||||
// MusicKit.getInstance().setQueue({ album: '${album}'}).then(function(queue) {
|
|
||||||
// MusicKit.getInstance().play();
|
|
||||||
// });
|
|
||||||
// `)
|
|
||||||
} else if (playParam.includes('p/')) { // playlist
|
} else if (playParam.includes('p/')) { // playlist
|
||||||
console.log(playParam)
|
console.log(playParam)
|
||||||
let playlist = playParam.split('p/')[1]
|
let playlist = playParam.split('p/')[1]
|
||||||
console.warn(`[LinkHandler] Attempting to load playlist by id: ${playlist}`);
|
console.warn(`[LinkHandler] Attempting to load playlist by id: ${playlist}`);
|
||||||
// AppEvents.window.webContents.executeJavaScript(`
|
electron.ipcRenderer.send('play', 'playlist', playlist)
|
||||||
// MusicKit.getInstance().setQueue({ playlist: '${playlist}'}).then(function(queue) {
|
|
||||||
// MusicKit.getInstance().play();
|
|
||||||
// });
|
|
||||||
// `)
|
|
||||||
}
|
}
|
||||||
} else if (arg.includes('music.apple.com')) { // URL (used with itms/itmss/music/musics uris)
|
} else if (arg.includes('music.apple.com')) { // URL (used with itms/itmss/music/musics uris)
|
||||||
console.log(arg)
|
console.log(arg)
|
||||||
let url = arg.split('//')[1]
|
let url = arg.split('//')[1]
|
||||||
console.warn(`[LinkHandler] Attempting to load url: ${url}`);
|
console.warn(`[LinkHandler] Attempting to load url: ${url}`);
|
||||||
// AppEvents.window.webContents.executeJavaScript(`
|
electron.ipcRenderer.send('play', 'url', url)
|
||||||
// MusicKit.getInstance().setQueue({ url: 'https://${url}'}).then(function(queue) {
|
|
||||||
// MusicKit.getInstance().play();
|
|
||||||
// });
|
|
||||||
// `)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -406,11 +406,26 @@ export class Win {
|
||||||
this.win.webContents.setZoomFactor(parseFloat(scale));
|
this.win.webContents.setZoomFactor(parseFloat(scale));
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// Set scale
|
||||||
|
electron.ipcMain.on("windowresize", (event, width, height, lock = false) => {
|
||||||
|
this.win.setMinimumSize(300,300);
|
||||||
|
this.win.setContentSize(width, height);
|
||||||
|
this.win.setResizable(!lock);
|
||||||
|
});
|
||||||
|
|
||||||
//Fullscreen
|
//Fullscreen
|
||||||
electron.ipcMain.on('setFullScreen', (event, flag) => {
|
electron.ipcMain.on('setFullScreen', (event, flag) => {
|
||||||
this.win.setFullScreen(flag)
|
this.win.setFullScreen(flag)
|
||||||
})
|
})
|
||||||
|
|
||||||
|
electron.ipcMain.on('play', (event, type, id) => {
|
||||||
|
this.win.webContents.executeJavaScript(`
|
||||||
|
MusicKit.getInstance().setQueue({ ${type}: '${id}'}).then(function(queue) {
|
||||||
|
MusicKit.getInstance().play();
|
||||||
|
});
|
||||||
|
`)
|
||||||
|
})
|
||||||
|
|
||||||
function getIp() {
|
function getIp() {
|
||||||
let ip = false;
|
let ip = false;
|
||||||
let alias = 0;
|
let alias = 0;
|
||||||
|
@ -488,7 +503,6 @@ export class Win {
|
||||||
return { action: "deny" };
|
return { action: "deny" };
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
private async broadcastRemote() {
|
private async broadcastRemote() {
|
||||||
function getIp() {
|
function getIp() {
|
||||||
let ip :any = false;
|
let ip :any = false;
|
||||||
|
|
8
src/renderer/assets/pip.svg
Normal file
8
src/renderer/assets/pip.svg
Normal file
|
@ -0,0 +1,8 @@
|
||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<!-- Generator: Adobe Illustrator 24.1.1, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
|
||||||
|
<svg version="1.1" id="Layer_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
|
||||||
|
fill="white" viewBox="0 0 512 512" style="enable-background:new 0 0 512 512;" xml:space="preserve">
|
||||||
|
<path id="XMLID_11_" d="M418.5,139.4H232.4v139.8h186.1V139.4z M464.8,46.7H46.3C20.5,46.7,0,68.1,0,93.1v325.9
|
||||||
|
c0,25.8,21.4,46.3,46.3,46.3h419.4c25.8,0,46.3-20.5,46.3-46.3V93.1C512,67.2,490.6,46.7,464.8,46.7z M464.8,418.9H46.3V92.2h419.4
|
||||||
|
v326.8H464.8z"/>
|
||||||
|
</svg>
|
After Width: | Height: | Size: 627 B |
|
@ -259,6 +259,8 @@ const app = new Vue({
|
||||||
platform: "web"
|
platform: "web"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
tmpHeight : '',
|
||||||
|
tmpWidth : '',
|
||||||
tmpVar: [],
|
tmpVar: [],
|
||||||
notification: false,
|
notification: false,
|
||||||
chrome: {
|
chrome: {
|
||||||
|
@ -3275,6 +3277,17 @@ const app = new Vue({
|
||||||
app.appMode = 'player';
|
app.appMode = 'player';
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
miniPlayer(flag) {
|
||||||
|
if (flag) {
|
||||||
|
this.tmpWidth = screen.width;
|
||||||
|
this.tmpHeight = screen.height;
|
||||||
|
ipcRenderer.send('windowresize', 350, 350, false)
|
||||||
|
app.appMode = 'mini';
|
||||||
|
} else {
|
||||||
|
ipcRenderer.send('windowresize', this.tmpWidth, this.tmpHeight, false)
|
||||||
|
app.appMode = 'player';
|
||||||
|
}
|
||||||
|
},
|
||||||
formatTimezoneOffset: (e = new Date) => {
|
formatTimezoneOffset: (e = new Date) => {
|
||||||
let leadingZeros = (e, s = 2) => {
|
let leadingZeros = (e, s = 2) => {
|
||||||
let n = "" + e;
|
let n = "" + e;
|
||||||
|
|
|
@ -1511,6 +1511,10 @@ input[type="range"].web-slider.display--small::-webkit-slider-thumb {
|
||||||
background-image: url("./assets/cast_white.svg");
|
background-image: url("./assets/cast_white.svg");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.playback-button--small.miniplayer {
|
||||||
|
background-image: url("./assets/pip.svg");
|
||||||
|
}
|
||||||
|
|
||||||
.playback-button--small.queue {
|
.playback-button--small.queue {
|
||||||
background-image: url("./assets/list.svg");
|
background-image: url("./assets/list.svg");
|
||||||
}
|
}
|
||||||
|
@ -4744,6 +4748,377 @@ input[type="range"].web-slider.display--small::-webkit-slider-thumb {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.mini-view {
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
background: black;
|
||||||
|
display: flex;
|
||||||
|
justify-content: center;
|
||||||
|
align-items: center;
|
||||||
|
|
||||||
|
.fs-row {
|
||||||
|
flex-grow: 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
.playback-button--small.active {
|
||||||
|
background-color: rgba(200, 200, 200, 0.7);
|
||||||
|
}
|
||||||
|
|
||||||
|
.playback-button--small {
|
||||||
|
opacity: 0.7;
|
||||||
|
}
|
||||||
|
|
||||||
|
.right-col {
|
||||||
|
height: 50vh;
|
||||||
|
}
|
||||||
|
|
||||||
|
@media only screen and (max-width: 1023px) {
|
||||||
|
.display--large {
|
||||||
|
display: flex !important;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.display--large {
|
||||||
|
display: flex;
|
||||||
|
|
||||||
|
.slider {
|
||||||
|
width: 100%;
|
||||||
|
z-index: 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
.input-container {
|
||||||
|
display: flex;
|
||||||
|
justify-content: center;
|
||||||
|
align-items: center;
|
||||||
|
width: 100%
|
||||||
|
}
|
||||||
|
|
||||||
|
.volume-button--small {
|
||||||
|
border-radius: 6px;
|
||||||
|
color: inherit;
|
||||||
|
background-size: 16px;
|
||||||
|
background-repeat: no-repeat;
|
||||||
|
background-position: center;
|
||||||
|
background-color: transparent;
|
||||||
|
height: 15px;
|
||||||
|
width: 30px;
|
||||||
|
border: 0px;
|
||||||
|
box-shadow: unset;
|
||||||
|
opacity: 0.70;
|
||||||
|
background-image: url("./assets/feather/volume-2.svg");
|
||||||
|
}
|
||||||
|
|
||||||
|
.volume-button--small:active {
|
||||||
|
transform: scale(0.9);
|
||||||
|
}
|
||||||
|
|
||||||
|
.volume-button--small.active {
|
||||||
|
background-image: url("./assets/feather/volume.svg");
|
||||||
|
}
|
||||||
|
|
||||||
|
input[type=range] {
|
||||||
|
-webkit-appearance: none;
|
||||||
|
height: 4px;
|
||||||
|
background: rgba(255, 255, 255, 0.4);
|
||||||
|
border-radius: 5px;
|
||||||
|
background-size: 70% 100%;
|
||||||
|
background-repeat: no-repeat;
|
||||||
|
|
||||||
|
&::-webkit-slider-thumb {
|
||||||
|
-webkit-appearance: none;
|
||||||
|
height: 14px;
|
||||||
|
width: 14px;
|
||||||
|
border-radius: 50%;
|
||||||
|
background: rgb(50 50 50);
|
||||||
|
cursor: default;
|
||||||
|
box-shadow: inset 0px 0px 0px 1px rgba(255, 255, 255, 0.4);
|
||||||
|
transition: all var(--appleTransition);
|
||||||
|
}
|
||||||
|
|
||||||
|
&::-webkit-slider-thumb:hover {
|
||||||
|
background-image: radial-gradient(var(--keyColor) 2px, transparent 3px, transparent 10px);
|
||||||
|
transform: scale(1.2);
|
||||||
|
}
|
||||||
|
|
||||||
|
&::-webkit-slider-thumb:active {
|
||||||
|
background-image: radial-gradient(var(--keyColor) 3px, transparent 4px, transparent 10px);
|
||||||
|
transform: scale(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
&::-webkit-slider-runnable-track {
|
||||||
|
-webkit-appearance: none;
|
||||||
|
box-shadow: none;
|
||||||
|
border: none;
|
||||||
|
background: transparent;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
.background {
|
||||||
|
position: absolute;
|
||||||
|
background-size: cover;
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
-webkit-user-select: none;
|
||||||
|
-webkit-app-region: drag;
|
||||||
|
|
||||||
|
.bgArtworkMaterial {
|
||||||
|
position: absolute;
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
|
||||||
|
.bg-artwork-container {
|
||||||
|
z-index: unset;
|
||||||
|
}
|
||||||
|
|
||||||
|
.bg-artwork-container .bg-artwork {
|
||||||
|
filter: brightness(85%) saturate(95%) blur(180px) contrast(0.9) opacity(0.9);
|
||||||
|
}
|
||||||
|
|
||||||
|
.no-animation {
|
||||||
|
animation: unset;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
.lyrics-col {
|
||||||
|
|
||||||
|
height: 62vh;
|
||||||
|
display: flex;
|
||||||
|
justify-content: center;
|
||||||
|
align-content: center;
|
||||||
|
width: 80%;
|
||||||
|
|
||||||
|
::-webkit-scrollbar-thumb {
|
||||||
|
box-shadow: unset;
|
||||||
|
}
|
||||||
|
|
||||||
|
&:hover ::-webkit-scrollbar-thumb {
|
||||||
|
box-shadow: inset 0px 0px 10px 10px rgb(200 200 200 / 50%);
|
||||||
|
}
|
||||||
|
|
||||||
|
.no-lyrics {
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
display: flex;
|
||||||
|
justify-content: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.lyric-line {
|
||||||
|
font-size: 35px;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
.queue-col {
|
||||||
|
|
||||||
|
width: 60vh;
|
||||||
|
height: 50vh;
|
||||||
|
|
||||||
|
.queue-title {
|
||||||
|
opacity: 0.6;
|
||||||
|
}
|
||||||
|
|
||||||
|
.queue-panel > * {
|
||||||
|
z-index: 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
::-webkit-scrollbar-thumb {
|
||||||
|
box-shadow: unset;
|
||||||
|
}
|
||||||
|
|
||||||
|
&:hover ::-webkit-scrollbar-thumb {
|
||||||
|
box-shadow: inset 0px 0px 10px 10px rgb(200 200 200 / 50%);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.tab-toggles {
|
||||||
|
display: flex;
|
||||||
|
position: absolute;
|
||||||
|
bottom: 0;
|
||||||
|
right: 0;
|
||||||
|
width: 15vh;
|
||||||
|
height: 5vh;
|
||||||
|
justify-content: space-evenly;
|
||||||
|
|
||||||
|
.volume {
|
||||||
|
background-image: url("./assets/feathers/volume.svg");
|
||||||
|
padding: 0.5vh;
|
||||||
|
width: 2vh;
|
||||||
|
height: 2vh;
|
||||||
|
background-origin: content-box;
|
||||||
|
background-repeat: no-repeat;
|
||||||
|
}
|
||||||
|
|
||||||
|
.queue {
|
||||||
|
background-image: url("./assets/list.svg");
|
||||||
|
padding: 0.5vh;
|
||||||
|
width: 2.5vh;
|
||||||
|
height: 2.5vh;
|
||||||
|
background-origin: content-box;
|
||||||
|
background-repeat: no-repeat;
|
||||||
|
}
|
||||||
|
|
||||||
|
.lyrics {
|
||||||
|
background-image: url("./assets/quote-right.svg");
|
||||||
|
padding: 0.5vh;
|
||||||
|
width: 2.5vh;
|
||||||
|
height: 2.5vh;
|
||||||
|
background-origin: content-box;
|
||||||
|
background-repeat: no-repeat;
|
||||||
|
}
|
||||||
|
|
||||||
|
.active {
|
||||||
|
background-color: rgba(200, 200, 200, 0.7);
|
||||||
|
border-radius: 3px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.artwork-col {
|
||||||
|
justify-content: center;
|
||||||
|
align-items: center;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
|
||||||
|
.artwork {
|
||||||
|
width: 50vh;
|
||||||
|
height: 50vh;
|
||||||
|
-webkit-app-region: no-drag;
|
||||||
|
}
|
||||||
|
|
||||||
|
.controls-parents {
|
||||||
|
width: 50vh;
|
||||||
|
}
|
||||||
|
|
||||||
|
.app-playback-controls {
|
||||||
|
-webkit-app-region: no-drag;
|
||||||
|
|
||||||
|
.song-artist, .song-name {
|
||||||
|
font-weight: 600;
|
||||||
|
text-align: center;
|
||||||
|
font-size: 0.9em;
|
||||||
|
height: 1.2em;
|
||||||
|
line-height: 0.9em;
|
||||||
|
overflow: hidden;
|
||||||
|
text-overflow: ellipsis;
|
||||||
|
max-width: 360px;
|
||||||
|
|
||||||
|
.song-name-normal {
|
||||||
|
height: inherit;
|
||||||
|
}
|
||||||
|
|
||||||
|
&.song-artist-marquee {
|
||||||
|
> marquee {
|
||||||
|
//margin-bottom: -3px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.song-artist {
|
||||||
|
font-size: 0.875em;
|
||||||
|
font-weight: 400;
|
||||||
|
}
|
||||||
|
|
||||||
|
.song-name {
|
||||||
|
width: unset !important;
|
||||||
|
margin-top: 0.15vh;
|
||||||
|
display: -webkit-box;
|
||||||
|
line-height: 1.2;
|
||||||
|
text-overflow: ellipsis;
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.app-playback-controls .playback-info {
|
||||||
|
margin-top: 0.5vh;
|
||||||
|
width: 100%;
|
||||||
|
display: flex;
|
||||||
|
justify-content: center;
|
||||||
|
align-items: center;
|
||||||
|
flex-direction: column;
|
||||||
|
position: relative;
|
||||||
|
|
||||||
|
input[type="range"] {
|
||||||
|
width: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
> div {
|
||||||
|
width: 100%;
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
.app-playback-controls .song-progress {
|
||||||
|
@bgColor: transparent;
|
||||||
|
//height: 16px;
|
||||||
|
position: absolute;
|
||||||
|
bottom: -1.5vh;
|
||||||
|
left: 0px;
|
||||||
|
background: @bgColor;
|
||||||
|
|
||||||
|
.song-duration p {
|
||||||
|
font-weight: 400;
|
||||||
|
font-size: 10px;
|
||||||
|
height: 1.2em;
|
||||||
|
line-height: 1.3em;
|
||||||
|
overflow: hidden;
|
||||||
|
margin: 0 0 0 0.25em;
|
||||||
|
}
|
||||||
|
|
||||||
|
&:hover {
|
||||||
|
> input[type=range] {
|
||||||
|
&::-webkit-slider-thumb {
|
||||||
|
opacity: 1;
|
||||||
|
transform: scale(1);
|
||||||
|
z-index: 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
input[type=range] {
|
||||||
|
appearance: none;
|
||||||
|
width: 100%;
|
||||||
|
height: 4px;
|
||||||
|
background-color: rgb(200 200 200 / 10%);
|
||||||
|
border-radius: 2px;
|
||||||
|
|
||||||
|
&::-webkit-slider-thumb {
|
||||||
|
opacity: 0;
|
||||||
|
transform: scale(0.5);
|
||||||
|
-webkit-appearance: none;
|
||||||
|
appearance: none;
|
||||||
|
width: 12px;
|
||||||
|
height: 12px;
|
||||||
|
border-radius: 100%;
|
||||||
|
background: var(--keyColor);
|
||||||
|
cursor: default;
|
||||||
|
transition: opacity .10s var(--appleEase), transform .10s var(--appleEase);
|
||||||
|
}
|
||||||
|
|
||||||
|
&::-moz-range-thumb {
|
||||||
|
width: 8px;
|
||||||
|
height: 8px;
|
||||||
|
border-radius: 100%;
|
||||||
|
background: var(--keyColor);
|
||||||
|
cursor: default;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.control-buttons {
|
||||||
|
margin-top: 2vh;
|
||||||
|
display: inline-flex;
|
||||||
|
width: 100%;
|
||||||
|
justify-content: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/* Cider */
|
/* Cider */
|
||||||
|
|
||||||
.settings-page {
|
.settings-page {
|
||||||
|
|
|
@ -26,7 +26,7 @@
|
||||||
{{ app.mk.nowPlayingItem["attributes"]["name"] }}
|
{{ app.mk.nowPlayingItem["attributes"]["name"] }}
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
style="display: inline-block; -webkit-box-orient: horizontal; white-space: nowrap; margin-top: 0.25vh;">
|
style="display: inline-block; -webkit-box-orient: horizontal; white-space: nowrap; margin-top: 0.25vh; overflow: hidden;">
|
||||||
<div class="item-navigate song-artist" style="display: inline-block;"
|
<div class="item-navigate song-artist" style="display: inline-block;"
|
||||||
@click="app.getNowPlayingItemDetailed(`artist`)">
|
@click="app.getNowPlayingItemDetailed(`artist`)">
|
||||||
{{ app.mk.nowPlayingItem["attributes"]["artistName"] }}
|
{{ app.mk.nowPlayingItem["attributes"]["artistName"] }}
|
||||||
|
|
152
src/renderer/views/components/miniplayer.ejs
Normal file
152
src/renderer/views/components/miniplayer.ejs
Normal file
|
@ -0,0 +1,152 @@
|
||||||
|
<script type="text/x-template" id="mini-view">
|
||||||
|
<div class="mini-view" tabindex="0">
|
||||||
|
<div class="background">
|
||||||
|
</div>
|
||||||
|
<div class="col artwork-col">
|
||||||
|
<div class="artwork" @click="app.miniPlayer(false)">
|
||||||
|
<mediaitem-artwork
|
||||||
|
:size="600"
|
||||||
|
:url="image ?? ''"
|
||||||
|
></mediaitem-artwork>
|
||||||
|
</div>
|
||||||
|
<div class="controls-parents">
|
||||||
|
<template v-if="app.mkReady()">
|
||||||
|
<div class="app-playback-controls" @mouseover="app.chrome.progresshover = true"
|
||||||
|
@mouseleave="app.chrome.progresshover = false" @contextmenu="app.nowPlayingContextMenu">
|
||||||
|
<div class="playback-info">
|
||||||
|
<div class="song-name">
|
||||||
|
{{ app.mk.nowPlayingItem["attributes"]["name"] }}
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
style="display: inline-block; -webkit-box-orient: horizontal; white-space: nowrap; margin-top: 0.25vh; overflow: hidden;">
|
||||||
|
<div class="item-navigate song-artist" style="display: inline-block;"
|
||||||
|
@click="app.getNowPlayingItemDetailed(`artist`)">
|
||||||
|
{{ app.mk.nowPlayingItem["attributes"]["artistName"] }}
|
||||||
|
</div>
|
||||||
|
<div class="song-artist item-navigate" style="display: inline-block;"
|
||||||
|
@click="app.getNowPlayingItemDetailed('album')">
|
||||||
|
{{ (app.mk.nowPlayingItem["attributes"]["albumName"]) ? (" — " +
|
||||||
|
app.mk.nowPlayingItem["attributes"]["albumName"]) : "" }}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="song-progress">
|
||||||
|
<div class="song-duration" style="justify-content: space-between; height: 1px;"
|
||||||
|
:style="[app.chrome.progresshover ? {'display': 'flex'} : {'display' : 'none'} ]">
|
||||||
|
<p style="width: auto">{{ app.convertToMins(app.getSongProgress()) }}</p>
|
||||||
|
<p style="width: auto">{{ app.convertToMins(app.mk.currentPlaybackDuration) }}</p>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<input type="range" step="0.01" min="0" :style="app.progressBarStyle()"
|
||||||
|
@input="app.playerLCD.desiredDuration = $event.target.value;app.playerLCD.userInteraction = true"
|
||||||
|
@mouseup="app.mk.seekToTime($event.target.value);app.playerLCD.desiredDuration = 0;app.playerLCD.userInteraction = false"
|
||||||
|
:max="app.mk.currentPlaybackDuration" :value="app.getSongProgress()">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="control-buttons">
|
||||||
|
<div class="app-chrome-item">
|
||||||
|
<button class="playback-button--small shuffle" v-if="app.mk.shuffleMode == 0"
|
||||||
|
@click="app.mk.shuffleMode = 1"></button>
|
||||||
|
<button class="playback-button--small shuffle active" v-else
|
||||||
|
@click="app.mk.shuffleMode = 0"></button>
|
||||||
|
</div>
|
||||||
|
<div class="app-chrome-item">
|
||||||
|
<button class="playback-button previous" @click="app.prevButton()"></button>
|
||||||
|
</div>
|
||||||
|
<div class="app-chrome-item">
|
||||||
|
<button class="playback-button pause" @click="app.mk.pause()" v-if="app.mk.isPlaying"></button>
|
||||||
|
<button class="playback-button play" @click="app.mk.play()" v-else></button>
|
||||||
|
</div>
|
||||||
|
<div class="app-chrome-item">
|
||||||
|
<button class="playback-button next" @click="app.mk.skipToNextItem()"></button>
|
||||||
|
</div>
|
||||||
|
<div class="app-chrome-item">
|
||||||
|
<button class="playback-button--small repeat" v-if="app.mk.repeatMode == 0"
|
||||||
|
@click="app.mk.repeatMode = 1"></button>
|
||||||
|
<button class="playback-button--small repeat active" @click="app.mk.repeatMode = 2"
|
||||||
|
v-else-if="app.mk.repeatMode == 1"></button>
|
||||||
|
<button class="playback-button--small repeat repeatOne" @click="app.mk.repeatMode = 0"
|
||||||
|
v-else-if="app.mk.repeatMode == 2"></button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="app-chrome-item volume display--large">
|
||||||
|
<div class="input-container">
|
||||||
|
<button class="volume-button--small volume" @click="app.muteButtonPressed()" :class="{'active': app.cfg.audio.volume == 0}"></button>
|
||||||
|
<input type="range" class="slider" @wheel="app.volumeWheel" step="0.01" min="0" max="1" v-model="app.mk.volume"
|
||||||
|
v-if="typeof app.mk.volume != 'undefined'" @change="app.checkMuteChange()">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<!-- <div class="row fs-row">
|
||||||
|
|
||||||
|
<div class="col right-col" v-if="tabMode != ''">
|
||||||
|
<div class="fs-info">
|
||||||
|
<div>Name</div>
|
||||||
|
<div>Name</div>
|
||||||
|
<div>Name</div>
|
||||||
|
</div>
|
||||||
|
<div class="lyrics-col" v-if="tabMode == 'lyrics'">
|
||||||
|
<lyrics-view :yoffset="120" :time="time" :lyrics="lyrics"
|
||||||
|
:richlyrics="richlyrics"></lyrics-view>
|
||||||
|
</div>
|
||||||
|
<div class="queue-col" v-if="tabMode == 'queue'">
|
||||||
|
<cider-queue v-if="tabMode == 'queue'" ref="queue" ></cider-queue>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div> -->
|
||||||
|
<!-- <div class="tab-toggles">
|
||||||
|
<div class="lyrics" :class="{active: tabMode == 'lyrics'}" @click="tabMode = (tabMode == 'lyrics') ? '' : 'lyrics'"></div>
|
||||||
|
<div class="queue" :class="{active: tabMode == 'queue'}" @click="tabMode = (tabMode == 'queue') ? '' :'queue'"></div>
|
||||||
|
</div> -->
|
||||||
|
</div>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
Vue.component('mini-view', {
|
||||||
|
template: '#mini-view',
|
||||||
|
props: {
|
||||||
|
time: {
|
||||||
|
type: Number,
|
||||||
|
required: false
|
||||||
|
},
|
||||||
|
lyrics: {
|
||||||
|
type: Array,
|
||||||
|
required: false
|
||||||
|
},
|
||||||
|
richlyrics: {
|
||||||
|
type: Array,
|
||||||
|
required: false
|
||||||
|
},
|
||||||
|
image: {
|
||||||
|
type: String,
|
||||||
|
required: false
|
||||||
|
},
|
||||||
|
},
|
||||||
|
data: function () {
|
||||||
|
return {
|
||||||
|
app: this.$root,
|
||||||
|
tabMode: "",
|
||||||
|
}
|
||||||
|
},
|
||||||
|
beforeMount() {
|
||||||
|
window.addEventListener('keyup', this.onEscapeKeyUp);
|
||||||
|
},
|
||||||
|
beforeDestroy() {
|
||||||
|
window.removeEventListener('keyup', this.onEscapeKeyUp)
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
onEscapeKeyUp(event) {
|
||||||
|
if (event.which === 27) {
|
||||||
|
app.miniPlayer(false);
|
||||||
|
console.log('js')
|
||||||
|
}
|
||||||
|
},
|
||||||
|
}
|
||||||
|
});
|
||||||
|
</script>
|
|
@ -150,6 +150,10 @@
|
||||||
<%- include("svg/cast.svg") %>
|
<%- include("svg/cast.svg") %>
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
|
<div class="app-chrome-item generic">
|
||||||
|
<button class="playback-button--small miniplayer"
|
||||||
|
@click="drawer.open = false; miniPlayer(true)"></button>
|
||||||
|
</div>
|
||||||
<div class="app-chrome-item generic">
|
<div class="app-chrome-item generic">
|
||||||
<button class="playback-button--small queue" :class="{'active': drawer.panel == 'queue'}"
|
<button class="playback-button--small queue" :class="{'active': drawer.panel == 'queue'}"
|
||||||
@click="invokeDrawer('queue')"></button>
|
@click="invokeDrawer('queue')"></button>
|
||||||
|
@ -593,6 +597,12 @@
|
||||||
:lyrics="lyrics" :richlyrics="richlyrics"></fullscreen-view>
|
:lyrics="lyrics" :richlyrics="richlyrics"></fullscreen-view>
|
||||||
</div>
|
</div>
|
||||||
</transition>
|
</transition>
|
||||||
|
<transition name="fsModeSwitch">
|
||||||
|
<div class="fullscreen-view-container" v-if="appMode == 'mini'">
|
||||||
|
<mini-view :image="currentArtUrl.replace('50x50', '600x600')" :time="lyriccurrenttime"
|
||||||
|
:lyrics="lyrics" :richlyrics="richlyrics"></mini-view>
|
||||||
|
</div>
|
||||||
|
</transition>
|
||||||
<transition name="wpfade">
|
<transition name="wpfade">
|
||||||
<div class="bg-artwork-container" v-if="cfg.visual.window_background_style == 'artwork'"
|
<div class="bg-artwork-container" v-if="cfg.visual.window_background_style == 'artwork'"
|
||||||
:class="{noanimation: (!cfg.visual.bg_artwork_rotation || !animateBackground)}">
|
:class="{noanimation: (!cfg.visual.bg_artwork_rotation || !animateBackground)}">
|
||||||
|
@ -774,6 +784,10 @@
|
||||||
<%- include('components/fullscreen')
|
<%- include('components/fullscreen')
|
||||||
%>
|
%>
|
||||||
|
|
||||||
|
<!-- Miniplayer View -->
|
||||||
|
<%- include('components/miniplayer')
|
||||||
|
%>
|
||||||
|
|
||||||
<script
|
<script
|
||||||
src="musickit.js?v=1"></script>
|
src="musickit.js?v=1"></script>
|
||||||
<script>
|
<script>
|
||||||
|
|
|
@ -432,7 +432,7 @@
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="md-option-header">
|
<div class="md-option-header">
|
||||||
<span>Conectivity</span>
|
<span>Connectivity</span>
|
||||||
</div>
|
</div>
|
||||||
<div class="settings-option-body">
|
<div class="settings-option-body">
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue