13 changed files with 26865 additions and 47 deletions
@ -0,0 +1,53 @@ |
|||
<?php |
|||
|
|||
use App\Dataclasses\DatabaseFolkTuneDetails; |
|||
use App\Dataclasses\TuneVariant; |
|||
use App\Wrappers\DatabaseInteractions; |
|||
use App\Wrappers\SQLQueryBuilderWrapper; |
|||
|
|||
$tuneDir = __DIR__ . '/../../../LocalStorage/Tunes'; |
|||
$targetTuneVariantID = $_GET['tune-variant-id']; |
|||
|
|||
$db = new DatabaseInteractions(); |
|||
|
|||
$variantDetails = $db->RunOneSelect( |
|||
queryBuilder: SQLQueryBuilderWrapper::SELECT_ONE( |
|||
table: 'TuneVariants', |
|||
id: $targetTuneVariantID |
|||
) |
|||
->cols([ |
|||
'T.ID AS TuneVariantID', |
|||
'T.TuneID AS TuneID', |
|||
"CONCAT('[', GROUP_CONCAT( |
|||
CONCAT( |
|||
'{\"TimeSignature\":', JSON_QUOTE(T_TVP.TimeSignature), ',', |
|||
'\"KeySignature\":', JSON_QUOTE(T_TVP.KeySignature), ',', |
|||
'\"ABCNotation\":', JSON_QUOTE(T_TVP.ABCNotation), '}' |
|||
) |
|||
), ']') AS Parts" |
|||
]) |
|||
->join( |
|||
join: 'INNER', |
|||
spec: 'TuneVariantParts AS T_TVP', |
|||
cond: 'T.ID = T_TVP.TuneVariantID' |
|||
) |
|||
->groupBy(spec: [ |
|||
'T.ID', |
|||
]) |
|||
); |
|||
|
|||
$tuneDetails = $db->RunOneSelect( |
|||
queryBuilder: SQLQueryBuilderWrapper::SELECT_ONE( |
|||
table: 'Tunes', |
|||
id: $variantDetails['TuneID'] |
|||
) |
|||
); |
|||
|
|||
|
|||
$tuneDetails = new DatabaseFolkTuneDetails($tuneDetails); |
|||
$variantDetails = new TuneVariant($tuneDetails, $variantDetails); |
|||
|
|||
|
|||
header(header: "Content-type: text/text"); |
|||
echo $variantDetails->Build(); |
|||
die(); |
@ -0,0 +1,187 @@ |
|||
/* Some basic CSS to make the Audio controls in abcjs presentable. */ |
|||
|
|||
.abcjs-inline-audio { |
|||
height: 26px; |
|||
padding: 0 5px; |
|||
border-radius: 3px; |
|||
background-color: #424242; |
|||
display: flex; |
|||
align-items: center; |
|||
box-sizing: border-box; |
|||
} |
|||
|
|||
.abcjs-inline-audio.abcjs-disabled { |
|||
opacity: 0.5; |
|||
} |
|||
|
|||
.abcjs-inline-audio .abcjs-btn { |
|||
display: block; |
|||
width: 28px; |
|||
height: 34px; |
|||
margin-right: 2px; |
|||
padding: 7px 4px; |
|||
|
|||
background: none !important; |
|||
border: 1px solid transparent; |
|||
box-sizing: border-box; |
|||
line-height: 1; |
|||
} |
|||
|
|||
.abcjs-btn g { |
|||
fill: #f4f4f4; |
|||
stroke: #f4f4f4; |
|||
} |
|||
|
|||
.abcjs-inline-audio .abcjs-btn:hover g { |
|||
fill: #cccccc; |
|||
stroke: #cccccc; |
|||
} |
|||
|
|||
.abcjs-inline-audio .abcjs-midi-selection.abcjs-pushed { |
|||
border: 1px solid #cccccc; |
|||
background-color: #666666; |
|||
box-sizing: border-box; |
|||
} |
|||
|
|||
.abcjs-inline-audio .abcjs-midi-loop.abcjs-pushed { |
|||
border: 1px solid #cccccc; |
|||
background-color: #666666; |
|||
box-sizing: border-box; |
|||
} |
|||
|
|||
.abcjs-inline-audio .abcjs-midi-reset.abcjs-pushed { |
|||
border: 1px solid #cccccc; |
|||
background-color: #666666; |
|||
box-sizing: border-box; |
|||
} |
|||
|
|||
.abcjs-inline-audio .abcjs-midi-start .abcjs-pause-svg { |
|||
display: none; |
|||
} |
|||
|
|||
.abcjs-inline-audio .abcjs-midi-start .abcjs-loading-svg { |
|||
display: none; |
|||
} |
|||
|
|||
.abcjs-inline-audio .abcjs-midi-start.abcjs-pushed .abcjs-play-svg { |
|||
display: none; |
|||
} |
|||
|
|||
.abcjs-inline-audio .abcjs-midi-start.abcjs-loading .abcjs-play-svg { |
|||
display: none; |
|||
} |
|||
|
|||
.abcjs-inline-audio .abcjs-midi-start.abcjs-pushed .abcjs-pause-svg { |
|||
display: block; |
|||
} |
|||
|
|||
.abcjs-inline-audio .abcjs-midi-progress-background { |
|||
background-color: #424242; |
|||
height: 10px; |
|||
border-radius: 5px; |
|||
border: 2px solid #cccccc; |
|||
margin: 0 8px 0 15px; |
|||
position: relative; |
|||
flex: 1; |
|||
padding: 0; |
|||
box-sizing: border-box; |
|||
} |
|||
|
|||
.abcjs-inline-audio .abcjs-midi-progress-indicator { |
|||
width: 20px; |
|||
margin-left: -10px; /* half of the width */ |
|||
height: 14px; |
|||
background-color: #f4f4f4; |
|||
position: absolute; |
|||
display: inline-block; |
|||
border-radius: 6px; |
|||
top: -4px; |
|||
left: 0; |
|||
box-sizing: border-box; |
|||
} |
|||
|
|||
.abcjs-inline-audio .abcjs-midi-clock { |
|||
margin-left: 4px; |
|||
margin-top: 1px; |
|||
margin-right: 2px; |
|||
display: inline-block; |
|||
font-family: sans-serif; |
|||
font-size: 16px; |
|||
box-sizing: border-box; |
|||
color: #f4f4f4; |
|||
} |
|||
|
|||
.abcjs-inline-audio .abcjs-tempo-wrapper { |
|||
font-size: 10px; |
|||
color: #f4f4f4; |
|||
box-sizing: border-box; |
|||
display: flex; |
|||
align-items: center; |
|||
} |
|||
|
|||
.abcjs-inline-audio .abcjs-midi-tempo { |
|||
border-radius: 2px; |
|||
border: none; |
|||
margin: 0 2px 0 4px; |
|||
width: 42px; |
|||
padding-left: 2px; |
|||
box-sizing: border-box; |
|||
} |
|||
|
|||
.abcjs-inline-audio .abcjs-loading .abcjs-loading-svg { |
|||
display: inherit; |
|||
} |
|||
|
|||
.abcjs-inline-audio .abcjs-loading { |
|||
outline: none; |
|||
animation-name: abcjs-spin; |
|||
animation-duration: 1s; |
|||
animation-iteration-count: infinite; |
|||
animation-timing-function: linear; |
|||
|
|||
} |
|||
.abcjs-inline-audio .abcjs-loading-svg circle { |
|||
stroke: #f4f4f4; |
|||
} |
|||
|
|||
@keyframes abcjs-spin { |
|||
from {transform:rotate(0deg);} |
|||
to {transform:rotate(360deg);} |
|||
} |
|||
|
|||
/* Adding the class "abcjs-large" will make the control easier on a touch device. */ |
|||
.abcjs-large .abcjs-inline-audio { |
|||
height: 52px; |
|||
} |
|||
.abcjs-large .abcjs-btn { |
|||
width: 56px; |
|||
height: 52px; |
|||
font-size: 28px; |
|||
padding: 6px 8px; |
|||
} |
|||
.abcjs-large .abcjs-midi-progress-background { |
|||
height: 20px; |
|||
border: 4px solid #cccccc; |
|||
} |
|||
.abcjs-large .abcjs-midi-progress-indicator { |
|||
height: 28px; |
|||
top: -8px; |
|||
width: 40px; |
|||
} |
|||
.abcjs-large .abcjs-midi-clock { |
|||
font-size: 32px; |
|||
margin-right: 10px; |
|||
margin-left: 10px; |
|||
margin-top: -1px; |
|||
} |
|||
.abcjs-large .abcjs-midi-tempo { |
|||
font-size: 20px; |
|||
width: 50px; |
|||
} |
|||
.abcjs-large .abcjs-tempo-wrapper { |
|||
font-size: 20px; |
|||
} |
|||
|
|||
.abcjs-css-warning { |
|||
display: none; |
|||
} |
@ -1,31 +0,0 @@ |
|||
|
|||
function RenderABC(containerID, targetTuneID) |
|||
{ |
|||
|
|||
API_GET("/V1/GetABCFile.php?tune-variant-id=" + targetTuneID).then(payload => { |
|||
|
|||
const tunes = ABCJS.renderAbc( |
|||
containerID, |
|||
payload, |
|||
{ |
|||
add_classes: true, |
|||
format: { |
|||
gchordfont: "Atkinson Hyperlegible", |
|||
annotationfont: "Atkinson Hyperlegible", |
|||
headerfont: "Atkinson Hyperlegible", |
|||
infofont: "Atkinson Hyperlegible", |
|||
repeatfont: "Atkinson Hyperlegible", |
|||
tempofont: "Atkinson Hyperlegible", |
|||
titlefont: "Atkinson Hyperlegible", |
|||
voicefont: "Atkinson Hyperlegible", |
|||
wordsfont: "Atkinson Hyperlegible", |
|||
}, |
|||
} |
|||
); |
|||
document.getElementById('RawABCReadout').innerHTML = payload; |
|||
|
|||
}) |
|||
.catch(error => { |
|||
console.log(error) |
|||
}); |
|||
} |
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
Loading…
Reference in new issue