Add start at checkbox in share modal

This commit is contained in:
Chocobozzz 2018-08-27 15:59:00 +02:00
parent c9d5c64f98
commit 11b8762f9c
No known key found for this signature in database
GPG Key ID: 583A612D890159BE
8 changed files with 67 additions and 36 deletions

View File

@ -51,6 +51,18 @@ function dateToHuman (date: string) {
return datePipe.transform(date, 'medium') return datePipe.transform(date, 'medium')
} }
function durationToString (duration: number) {
const hours = Math.floor(duration / 3600)
const minutes = Math.floor((duration % 3600) / 60)
const seconds = duration % 60
const minutesPadding = minutes >= 10 ? '' : '0'
const secondsPadding = seconds >= 10 ? '' : '0'
const displayedHours = hours > 0 ? hours.toString() + ':' : ''
return displayedHours + minutesPadding + minutes.toString() + ':' + secondsPadding + seconds.toString()
}
function immutableAssign <A, B> (target: A, source: B) { function immutableAssign <A, B> (target: A, source: B) {
return Object.assign({}, target, source) return Object.assign({}, target, source)
} }
@ -114,6 +126,7 @@ function sortBy (obj: any[], key1: string, key2?: string) {
export { export {
sortBy, sortBy,
durationToString,
objectToUrlEncoded, objectToUrlEncoded,
getParameterByName, getParameterByName,
populateAsyncUserVideoChannels, populateAsyncUserVideoChannels,

View File

@ -2,7 +2,7 @@ import { User } from '../'
import { Video as VideoServerModel, VideoPrivacy, VideoState } from '../../../../../shared' import { Video as VideoServerModel, VideoPrivacy, VideoState } from '../../../../../shared'
import { Avatar } from '../../../../../shared/models/avatars/avatar.model' import { Avatar } from '../../../../../shared/models/avatars/avatar.model'
import { VideoConstant } from '../../../../../shared/models/videos/video-constant.model' import { VideoConstant } from '../../../../../shared/models/videos/video-constant.model'
import { getAbsoluteAPIUrl } from '../misc/utils' import { durationToString, getAbsoluteAPIUrl } from '../misc/utils'
import { peertubeTranslate, ServerConfig } from '../../../../../shared/models' import { peertubeTranslate, ServerConfig } from '../../../../../shared/models'
import { Actor } from '@app/shared/actor/actor.model' import { Actor } from '@app/shared/actor/actor.model'
import { VideoScheduleUpdate } from '../../../../../shared/models/videos/video-schedule-update.model' import { VideoScheduleUpdate } from '../../../../../shared/models/videos/video-schedule-update.model'
@ -70,18 +70,6 @@ export class Video implements VideoServerModel {
return '/videos/watch/' + videoUUID return '/videos/watch/' + videoUUID
} }
private static createDurationString (duration: number) {
const hours = Math.floor(duration / 3600)
const minutes = Math.floor((duration % 3600) / 60)
const seconds = duration % 60
const minutesPadding = minutes >= 10 ? '' : '0'
const secondsPadding = seconds >= 10 ? '' : '0'
const displayedHours = hours > 0 ? hours.toString() + ':' : ''
return displayedHours + minutesPadding + minutes.toString() + ':' + secondsPadding + seconds.toString()
}
constructor (hash: VideoServerModel, translations = {}) { constructor (hash: VideoServerModel, translations = {}) {
const absoluteAPIUrl = getAbsoluteAPIUrl() const absoluteAPIUrl = getAbsoluteAPIUrl()
@ -95,7 +83,7 @@ export class Video implements VideoServerModel {
this.state = hash.state this.state = hash.state
this.description = hash.description this.description = hash.description
this.duration = hash.duration this.duration = hash.duration
this.durationLabel = Video.createDurationString(hash.duration) this.durationLabel = durationToString(hash.duration)
this.id = hash.id this.id = hash.id
this.uuid = hash.uuid this.uuid = hash.uuid
this.isLocal = hash.isLocal this.isLocal = hash.isLocal

View File

@ -17,6 +17,11 @@
</div> </div>
</div> </div>
<div class="form-group qr-code-group">
<label i18n>QR-Code</label>
<ngx-qrcode qrc-element-type="url" [qrc-value]="getVideoUrl()" qrc-errorCorrectionLevel="Q"></ngx-qrcode>
</div>
<div class="form-group"> <div class="form-group">
<label i18n>Embed</label> <label i18n>Embed</label>
<div class="input-group input-group-sm"> <div class="input-group input-group-sm">
@ -32,15 +37,17 @@
<div i18n *ngIf="notSecure()" class="alert alert-warning"> <div i18n *ngIf="notSecure()" class="alert alert-warning">
The url is not secured (no HTTPS), so the embed video won't work on HTTPS websites (web browsers block non secured HTTP requests on HTTPS websites). The url is not secured (no HTTPS), so the embed video won't work on HTTPS websites (web browsers block non secured HTTP requests on HTTPS websites).
</div> </div>
<div class="form-group qr-code-group">
<label i18n>QR-Code</label>
<ngx-qrcode qrc-element-type="url" [qrc-value]="getVideoUrl()" qrc-errorCorrectionLevel="Q"></ngx-qrcode>
</div> </div>
<div *ngIf="currentVideoTimestampString" class="start-at">
<my-peertube-checkbox
inputName="startAt" [(ngModel)]="startAtCheckbox"
i18n-labelText [labelText]="getStartCheckboxLabel()"
></my-peertube-checkbox>
</div> </div>
<div class="modal-footer inputs"> <div class="modal-footer inputs">
<span i18n class="action-button action-button-cancel" (click)="hide()">Cancel</span> <span i18n class="action-button action-button-cancel" (click)="hide()">Close</span>
</div> </div>
</ng-template> </ng-template>

View File

@ -12,3 +12,9 @@
.qr-code-group { .qr-code-group {
text-align: center; text-align: center;
} }
.start-at {
display: flex;
justify-content: center;
margin-top: 10px;
}

View File

@ -1,9 +1,10 @@
import { Component, ElementRef, Input, ViewChild } from '@angular/core' import { Component, ElementRef, Input, ViewChild } from '@angular/core'
import { NotificationsService } from 'angular2-notifications' import { NotificationsService } from 'angular2-notifications'
import { VideoDetails } from '../../../shared/video/video-details.model' import { VideoDetails } from '../../../shared/video/video-details.model'
import { buildVideoEmbed } from '../../../../assets/player/utils' import { buildVideoEmbed, buildVideoLink } from '../../../../assets/player/utils'
import { I18n } from '@ngx-translate/i18n-polyfill' import { I18n } from '@ngx-translate/i18n-polyfill'
import { NgbModal } from '@ng-bootstrap/ng-bootstrap' import { NgbModal } from '@ng-bootstrap/ng-bootstrap'
import { durationToString } from '@app/shared/misc/utils'
@Component({ @Component({
selector: 'my-video-share', selector: 'my-video-share',
@ -11,9 +12,14 @@ import { NgbModal } from '@ng-bootstrap/ng-bootstrap'
styleUrls: [ './video-share.component.scss' ] styleUrls: [ './video-share.component.scss' ]
}) })
export class VideoShareComponent { export class VideoShareComponent {
@ViewChild('modal') modal: ElementRef
@Input() video: VideoDetails = null @Input() video: VideoDetails = null
@ViewChild('modal') modal: ElementRef startAtCheckbox = false
currentVideoTimestampString: string
private currentVideoTimestamp: number
constructor ( constructor (
private modalService: NgbModal, private modalService: NgbModal,
@ -23,16 +29,21 @@ export class VideoShareComponent {
// empty // empty
} }
show () { show (currentVideoTimestamp?: number) {
this.currentVideoTimestamp = Math.floor(currentVideoTimestamp)
this.currentVideoTimestampString = durationToString(this.currentVideoTimestamp)
this.modalService.open(this.modal) this.modalService.open(this.modal)
} }
getVideoIframeCode () { getVideoIframeCode () {
return buildVideoEmbed(this.video.embedUrl) const embedUrl = buildVideoLink(this.getVideoTimestampIfEnabled(), this.video.embedUrl)
return buildVideoEmbed(embedUrl)
} }
getVideoUrl () { getVideoUrl () {
return window.location.href return buildVideoLink(this.getVideoTimestampIfEnabled())
} }
notSecure () { notSecure () {
@ -42,4 +53,14 @@ export class VideoShareComponent {
activateCopiedMessage () { activateCopiedMessage () {
this.notificationsService.success(this.i18n('Success'), this.i18n('Copied')) this.notificationsService.success(this.i18n('Success'), this.i18n('Copied'))
} }
getStartCheckboxLabel () {
return this.i18n('Start at {{timestamp}}', { timestamp: this.currentVideoTimestampString })
}
private getVideoTimestampIfEnabled () {
if (this.startAtCheckbox === true) return this.currentVideoTimestamp
return undefined
}
} }

View File

@ -204,7 +204,9 @@ export class VideoWatchComponent implements OnInit, OnDestroy {
} }
showShareModal () { showShareModal () {
this.videoShareModal.show() const currentTime = this.player ? this.player.currentTime() : undefined
this.videoShareModal.show(currentTime)
} }
showDownloadModal (event: Event) { showDownloadModal (event: Event) {
@ -258,12 +260,6 @@ export class VideoWatchComponent implements OnInit, OnDestroy {
return this.video.isUnblacklistableBy(this.user) return this.video.isUnblacklistableBy(this.user)
} }
getVideoPoster () {
if (!this.video) return ''
return this.video.previewUrl
}
getVideoTags () { getVideoTags () {
if (!this.video || Array.isArray(this.video.tags) === false) return [] if (!this.video || Array.isArray(this.video.tags) === false) return []

View File

@ -23,9 +23,8 @@ function isMobile () {
return /iPhone|iPad|iPod|Android/i.test(navigator.userAgent) return /iPhone|iPad|iPod|Android/i.test(navigator.userAgent)
} }
function buildVideoLink (time?: number) { function buildVideoLink (time?: number, url?: string) {
const baseEmbedPath = window.location.pathname.replace('/embed/', '/watch/') if (!url) url = window.location.origin + window.location.pathname.replace('/embed/', '/watch/')
const baseEmbedURL = window.location.origin + baseEmbedPath
if (time) { if (time) {
const timeInt = Math.floor(time) const timeInt = Math.floor(time)
@ -33,10 +32,10 @@ function buildVideoLink (time?: number) {
const params = new URLSearchParams(window.location.search) const params = new URLSearchParams(window.location.search)
params.set('start', secondsToTime(timeInt)) params.set('start', secondsToTime(timeInt))
return baseEmbedURL + '?' + params.toString() return url + '?' + params.toString()
} }
return baseEmbedURL return url
} }
function timeToInt (time: number | string) { function timeToInt (time: number | string) {

View File

@ -4,6 +4,7 @@
- [import-videos.js](#import-videosjs) - [import-videos.js](#import-videosjs)
- [upload.js](#uploadjs) - [upload.js](#uploadjs)
- [Server tools](#server-tools) - [Server tools](#server-tools)
- [parse-log](#parse-log)
- [create-transcoding-job.js](#create-transcoding-jobjs) - [create-transcoding-job.js](#create-transcoding-jobjs)
- [create-import-video-file-job.js](#create-import-video-file-jobjs) - [create-import-video-file-job.js](#create-import-video-file-jobjs)
- [prune-storage.js](#prune-storagejs) - [prune-storage.js](#prune-storagejs)