Files
YoutubeDL-Material/src/app/main/main.component.html
Isaac Grynsztein b3c8f9e57a Fixed bug that caused downloads to fail when archiving was enabled
Removed error message on URL input on the home page

Fixed bug that prevented file deletion in multi user mode with archiving enabled
2020-05-30 16:20:03 -04:00

281 lines
19 KiB
HTML

<br/>
<div class="big demo-basic">
<mat-card id="card" style="margin-right: 20px; margin-left: 20px;" [ngClass]="(allowAdvancedDownload) ? 'no-border-radius-bottom' : null">
<mat-card-title>
<ng-container i18n="Youtube downloader home page label">Youtube Downloader</ng-container>
</mat-card-title>
<mat-card-content>
<div style="position: relative;">
<form class="example-form">
<div class="container-fluid">
<div class="row">
<div [ngClass]="allowQualitySelect ? 'col-sm-9' : null" class="col-12">
<mat-form-field color="accent" class="example-full-width">
<input style="padding-right: 25px;" matInput (keyup.enter)="downloadClicked()" (ngModelChange)="inputChanged($event)" [(ngModel)]="url" [placeholder]="'URL' + (youtubeSearchEnabled ? ' or search' : '')" type="url" name="url" #urlinput>
</mat-form-field>
<button type="button" class="input-clear-button" mat-icon-button (click)="clearInput()"><mat-icon>clear</mat-icon></button>
</div>
<div *ngIf="allowQualitySelect" class="col-7 col-sm-3">
<mat-form-field color="accent" style="display: inline-block; width: inherit; min-width: 120px;">
<mat-label>
<ng-container i18n="Quality select label">
Quality
</ng-container>
</mat-label>
<mat-select [ngModelOptions]="{standalone: true}" [(ngModel)]="selectedQuality">
<ng-container *ngFor="let option of qualityOptions[(audioOnly) ? 'audio' : 'video']">
<mat-option *ngIf="option.value === '' || url && cachedAvailableFormats[url] && cachedAvailableFormats[url]['formats'] && cachedAvailableFormats[url]['formats'][(audioOnly) ? 'audio' : 'video'][option.value]" [value]="option.value">
{{option.label}}
</mat-option>
</ng-container>
</mat-select>
<div class="spinner-div" *ngIf="url !== '' && cachedAvailableFormats[url] && cachedAvailableFormats[url]['formats_loading']">
<mat-spinner [diameter]="25"></mat-spinner>
</div>
</mat-form-field>
</div>
</div>
</div>
<div class="results-div" *ngIf="results_showing">
<span *ngFor="let result of results; let i = index">
<mat-card class="result-card mat-elevation-z7" [ngClass]="[(i === 0 && results.length > 1) ? 'first-result-card' : '', ((i === results.length-1) && results.length > 1) ? 'last-result-card' : '', (results.length === 1) ? 'only-result-card' : '']">
<div class="search-card-title">
{{result.title}}
</div>
<div style="font-size: 12px; margin-bottom: 10px;">
{{result.uploaded}}
</div>
<button mat-flat-button color="primary" style="float: left;" (click)="useURL(result.videoUrl)">
<ng-container i18n="YT search Use URL button for searched video">Use URL</ng-container>
</button>
<button mat-stroked-button color="primary" (click)="visitURL(result.videoUrl)" style="float: right">
<ng-container i18n="YT search View button for searched video">
View
</ng-container>
</button>
</mat-card>
</span>
</div>
</form>
<br/>
<mat-checkbox [disabled]="current_download" (change)="videoModeChanged($event)" [(ngModel)]="audioOnly" style="float: left; margin-top: -12px">
<ng-container i18n="Only Audio checkbox">
Only Audio
</ng-container>
</mat-checkbox>
<mat-checkbox *ngIf="allowMultiDownloadMode" [disabled]="current_download" (change)="multiDownloadModeChanged($event)" [(ngModel)]="multiDownloadMode" style="float: right; margin-top: -12px">
<ng-container i18n="Multi-download Mode checkbox">
Multi-download Mode
</ng-container>
</mat-checkbox>
</div>
</mat-card-content>
<mat-card-actions>
<button style="margin-left: 8px; margin-bottom: 8px" (click)="downloadClicked()" [disabled]="downloadingfile" type="submit" mat-stroked-button color="accent">
<ng-container i18n="Main download button">
Download
</ng-container>
</button>
<button (click)="cancelDownload()" style="float: right" *ngIf="!!current_download" mat-stroked-button color="warn">
<ng-container i18n="Cancel download button">
Cancel
</ng-container>
</button>
</mat-card-actions>
</mat-card>
</div>
<div *ngIf="allowAdvancedDownload" class="big demo-basic">
<form style="margin-left: 20px; margin-right: 20px;">
<mat-expansion-panel class="big no-border-radius-top">
<mat-expansion-panel-header>
<mat-panel-title>
<ng-container i18n="Advanced download mode panel">
Advanced
</ng-container>
</mat-panel-title>
</mat-expansion-panel-header>
<p *ngIf="this.simulatedOutput">
<ng-container i18n="Simulated command label">
Simulated command:
</ng-container>
&nbsp;<i>{{this.simulatedOutput}}</i></p>
<div class="container" style="padding-bottom: 20px;">
<div class="row">
<div class="col-12 col-sm-6">
<mat-checkbox color="accent" [disabled]="current_download" (change)="customArgsEnabledChanged($event)" [(ngModel)]="customArgsEnabled" style="z-index: 999" [ngModelOptions]="{standalone: true}">
<ng-container i18n="Use custom args checkbox">
Use custom args
</ng-container>
</mat-checkbox>
<button class="edit-button" (click)="openArgsModifierDialog()" mat-icon-button><mat-icon>edit</mat-icon></button>
<mat-form-field color="accent" style="margin-bottom: 42px;" class="advanced-input">
<input [(ngModel)]="customArgs" [ngModelOptions]="{standalone: true}" [disabled]="!customArgsEnabled" matInput placeholder="Custom args" i18n-placeholder="Custom args placeholder">
<mat-hint>
<ng-container i18n="Custom Args input hint">
No need to include URL, just everything after. Args are delimited using two commas like so: ,,
</ng-container>
</mat-hint>
</mat-form-field>
</div>
<div class="col-12 col-sm-6">
<mat-checkbox color="accent" [disabled]="current_download" (change)="customOutputEnabledChanged($event)" [(ngModel)]="customOutputEnabled" style="z-index: 999" [ngModelOptions]="{standalone: true}">
<ng-container i18n="Use custom output checkbox">
Use custom output
</ng-container>
</mat-checkbox>
<mat-form-field style="margin-bottom: 42px;" color="accent" class="advanced-input">
<input [(ngModel)]="customOutput" [ngModelOptions]="{standalone: true}" [disabled]="!customOutputEnabled" matInput placeholder="Custom output" i18n-placeholder="Custom output placeholder">
<mat-hint><a target="_blank" href="https://github.com/ytdl-org/youtube-dl/blob/master/README.md#output-template">
<ng-container i18n="Youtube-dl output template documentation link">Documentation</ng-container></a>.
<ng-container i18n="Custom Output input hint">Path is relative to the config download path. Don't include extension.</ng-container>
</mat-hint>
</mat-form-field>
</div>
<div *ngIf="!youtubeAuthDisabledOverride" class="col-12 col-sm-6 mt-2">
<mat-checkbox color="accent" [disabled]="current_download" (change)="youtubeAuthEnabledChanged($event)" [(ngModel)]="youtubeAuthEnabled" style="z-index: 999" [ngModelOptions]="{standalone: true}">
<ng-container i18n="Use authentication checkbox">
Use authentication
</ng-container>
</mat-checkbox>
<mat-form-field color="accent" class="advanced-input">
<input [(ngModel)]="youtubeUsername" [ngModelOptions]="{standalone: true}" [disabled]="!youtubeAuthEnabled" matInput placeholder="Username" i18n-placeholder="YT Username placeholder">
</mat-form-field>
</div>
<div *ngIf="!youtubeAuthDisabledOverride" class="col-12 col-sm-6 mt-2">
<mat-form-field style="margin-top: 31px;" color="accent" class="advanced-input">
<input [(ngModel)]="youtubePassword" type="password" [ngModelOptions]="{standalone: true}" [disabled]="!youtubeAuthEnabled" matInput placeholder="Password" i18n-placeholder="YT Password placeholder">
</mat-form-field>
</div>
</div>
</div>
</mat-expansion-panel>
</form>
</div>
<div *ngIf="multiDownloadMode && downloads.length > 0 && !current_download" style="margin-top: 15px;" class="big demo-basic">
<mat-card id="card" style="margin-right: 20px; margin-left: 20px;">
<div class="container">
<div *ngFor="let download of downloads; let i = index;" class="row">
<ng-container *ngIf="current_download !== download && download['downloading']">
<app-download-item style="width: 100%" [download]="download" [queueNumber]="i+1" (cancelDownload)="cancelDownload($event)"></app-download-item>
<mat-divider style="position: relative" *ngIf="i !== downloads.length - 1"></mat-divider>
</ng-container>
</div>
</div>
</mat-card>
</div>
<br/>
<div class="centered big" id="bar_div" *ngIf="current_download && current_download.downloading; else nofile">
<div class="margined">
<div [ngClass]="(+percentDownloaded > 99)?'make-room-for-spinner':'equal-sizes'" style="display: inline-block; width: 100%; padding-left: 20px" *ngIf="current_download.percent_complete && current_download.percent_complete > 15;else indeterminateprogress">
<mat-progress-bar style="border-radius: 5px;" mode="determinate" value="{{percentDownloaded}}"></mat-progress-bar>
<br/>
</div>
<div *ngIf="+percentDownloaded > 99" class="spinner">
<mat-spinner [diameter]="25"></mat-spinner>
</div>
<ng-template #indeterminateprogress>
<mat-progress-bar style="border-radius: 5px;" mode="indeterminate"></mat-progress-bar>
</ng-template>
</div>
<br/>
</div>
<ng-template #nofile>
</ng-template>
<div style="margin: 20px" *ngIf="fileManagerEnabled && (!postsService.isLoggedIn || postsService.permissions.includes('filemanager'))">
<mat-accordion>
<mat-expansion-panel (opened)="accordionOpened('audio')" (closed)="accordionClosed('audio')" (mouseleave)="accordionLeft('audio')" (mouseenter)="accordionEntered('audio')" class="big">
<mat-expansion-panel-header>
<mat-panel-title>
<ng-container i18n="Audio files title">
Audio
</ng-container>
</mat-panel-title>
<mat-panel-description>
<ng-container i18n="Audio files description">
Your audio files are here
</ng-container>
</mat-panel-description>
</mat-expansion-panel-header>
<div *ngIf="mp3s.length > 0;else nomp3s">
<mat-grid-list style="margin-bottom: 15px;" (window:resize)="onResize($event)" [cols]="files_cols" rowHeight="150px">
<mat-grid-tile *ngFor="let file of mp3s; index as i;">
<app-file-card #audiofilecard (removeFile)="removeFromMp3($event)" [file]="file" [title]="file.title" [name]="file.id" [uid]="file.uid" [thumbnailURL]="file.thumbnailURL"
[length]="file.duration" [isAudio]="true" [use_youtubedl_archive]="use_youtubedl_archive"></app-file-card>
<mat-progress-bar *ngIf="downloading_content['audio'][file.id]" class="download-progress-bar" mode="indeterminate"></mat-progress-bar>
</mat-grid-tile>
</mat-grid-list>
<mat-divider></mat-divider>
<div style="width: 100%; text-align: center; margin-top: 10px;">
<h6 i18n="Playlists title">Playlists</h6>
</div>
<mat-grid-list *ngIf="playlists.audio.length > 0" (window:resize)="onResize($event)" [cols]="files_cols" rowHeight="150px">
<mat-grid-tile *ngFor="let playlist of playlists.audio; let i = index;">
<app-file-card #audiofilecard (removeFile)="removePlaylistMp3(playlist.id, i)" [title]="playlist.name" [name]="playlist.id" [thumbnailURL]="playlist_thumbnails[playlist.id]"
[length]="null" [isAudio]="true" [isPlaylist]="true" [count]="playlist.fileNames.length" [use_youtubedl_archive]="use_youtubedl_archive"></app-file-card>
<mat-progress-bar *ngIf="downloading_content['audio'][playlist.id]" class="download-progress-bar" mode="indeterminate"></mat-progress-bar>
</mat-grid-tile>
</mat-grid-list>
<div class="add-playlist-button"><button (click)="openCreatePlaylistDialog('audio')" mat-fab><mat-icon>add</mat-icon></button></div>
<div *ngIf="playlists.audio.length === 0">
<ng-container i18n="No video playlists available text">
No playlists available. Create one from your downloading audio files by clicking the blue plus button.
</ng-container>
</div>
</div>
</mat-expansion-panel>
<mat-expansion-panel (opened)="accordionOpened('video')" (closed)="accordionClosed('video')" (mouseleave)="accordionLeft('video')" (mouseenter)="accordionEntered('video')" class="big">
<mat-expansion-panel-header>
<mat-panel-title>
<ng-container i18n="Video files title">
Video
</ng-container>
</mat-panel-title>
<mat-panel-description>
<ng-container i18n="Video files description">
Your video files are here
</ng-container>
</mat-panel-description>
</mat-expansion-panel-header>
<div *ngIf="mp4s.length > 0;else nomp4s">
<mat-grid-list style="margin-bottom: 15px;" (window:resize)="onResize($event)" [cols]="files_cols" rowHeight="150px">
<mat-grid-tile *ngFor="let file of mp4s; index as i;">
<app-file-card #videofilecard (removeFile)="removeFromMp4($event)" [file]="file" [title]="file.title" [name]="file.id" [uid]="file.uid" [thumbnailURL]="file.thumbnailURL"
[length]="file.duration" [isAudio]="false" [use_youtubedl_archive]="use_youtubedl_archive"></app-file-card>
<mat-progress-bar *ngIf="downloading_content['video'][file.id]" class="download-progress-bar" mode="indeterminate"></mat-progress-bar>
</mat-grid-tile>
</mat-grid-list>
<mat-divider></mat-divider>
<div style="width: 100%; text-align: center; margin-top: 10px;">
<h6 i18n="Playlists title">Playlists</h6>
</div>
<mat-grid-list *ngIf="playlists.video.length > 0" (window:resize)="onResize($event)" [cols]="files_cols" rowHeight="150px">
<mat-grid-tile *ngFor="let playlist of playlists.video; let i = index;">
<app-file-card #videofilecard (removeFile)="removePlaylistMp4(playlist.id, i)" [title]="playlist.name" [name]="playlist.id" [thumbnailURL]="playlist_thumbnails[playlist.id]"
[length]="null" [isAudio]="false" [isPlaylist]="true" [count]="playlist.fileNames.length" [use_youtubedl_archive]="use_youtubedl_archive"></app-file-card>
<mat-progress-bar *ngIf="downloading_content['video'][playlist.id]" class="download-progress-bar" mode="indeterminate"></mat-progress-bar>
</mat-grid-tile>
</mat-grid-list>
<!-- Add video playlist button -->
<div class="add-playlist-button"><button (click)="openCreatePlaylistDialog('video')" mat-fab><mat-icon>add</mat-icon></button></div>
<div *ngIf="playlists.video.length === 0">
<ng-container i18n="No video playlists available text">
No playlists available. Create one from your downloading video files by clicking the blue plus button.
</ng-container>
</div>
</div>
</mat-expansion-panel>
</mat-accordion>
</div>
<ng-template #nomp3s>
</ng-template>
<ng-template #nomp4s>
</ng-template>