Commit 94238c80 authored by Jeff's avatar Jeff

Merge remote-tracking branch 'origin/develop' into develop

parents 588da09d 74fbaf1b
<template>
<div class="video-timeline">
<div
ref="sliderWidth"
v-drag
class="time-slider"
>
<div class="time-slider-rail"></div>
<div
class="time-slider-track"
:style="{ width: ((info.val - info.min) / info.max) * 100 + '%' }"
></div>
<div
data-action="handle"
class="time-slider-handle"
:style="{ left: ((info.val - info.min) / info.max) * 100 + '%' }"
></div>
</div>
</div>
</template>
<script>
export default {
name: 'VideoTimeline',
directives: {
drag(el, binding, vnode) {
let _this = vnode.context,
mousemove = null,
mouseup = null,
dataAction = ''
mousemove = (e) => {
_this.dragMove && _this.dragMove(e.pageX, dataAction, e)
}
mouseup = (e) => {
document.removeEventListener('mousemove', mousemove)
document.removeEventListener('mouseup', mouseup)
_this.dragUp && _this.dragUp(e.pageX, dataAction, e)
}
el.onmousedown = (e) => {
dataAction = e.target.dataset.action
if (e.which === 3 || e.which === 2) {
e.stopPropagation()
return
}
document.addEventListener('mousemove', mousemove)
document.addEventListener('mouseup', mouseup)
_this.dragDown && _this.dragDown(e.pageX, dataAction, e)
}
}
},
props: {
info: {
type: Object,
required: true,
default: function() {
return { step: 0.1, min: 0, max: 10, val: 0, cut: [0, 10] }
}
}
},
data() {
return {
width: 100
}
},
methods: {
dragDown(dis, action) {
if (!action) return
this.width = this.$refs.sliderWidth.clientWidth
this.action = action
this.dragHand = true
this.mpos = {
x: dis,
v: this.info.val
}
this.$emit('changeData', { val: this.mpos.v, action: action, type: 'start' })
},
dragMove(pos) {
if (!this.action) return
let val = 0
console.log(pos, '<_-------------')
// let pre = Math.round(((pos.x - this.mpos.x) / 120 * this.item.len + this.mpos.v) / this.item.step) / (1 / this.item.step);
// this.item.val = pre > this.item.max ? this.item.max : pre < this.item.min ? this.item.min : pre;
this.$emit('changeData', { val: val, action: this.action, type: 'change' })
},
dragUp() {
if (!this.action) return
let val = 0
this.mpos = null
this.dragHand = false
this.action = ''
this.$emit('changeData', { val: val, action: this.action, type: 'end' })
}
}
}
</script>
<style lang="scss" scoped>
.video-timeline {
width: 100%;
height: 50px;
background-color: beige;
}
.time-slider {
position: relative;
height: 15px;
padding: 5px 0;
width: 100%;
margin-right: 1px;
-ms-touch-action: none;
touch-action: none;
-webkit-box-sizing: border-box;
box-sizing: border-box;
-webkit-tap-highlight-color: rgba(0, 0, 0, 0);
* {
-webkit-box-sizing: border-box;
box-sizing: border-box;
-webkit-tap-highlight-color: rgba(0, 0, 0, 0);
}
.time-slider-rail {
position: absolute;
width: 100%;
background-color: #d9ddea;
height: 4px;
border-radius: 3px;
}
.time-slider-track {
position: absolute;
background-color: #737596;
border-radius: 3px;
height: 4px;
left: 0%;
width: 69.1515%;
}
.time-slider-handle {
position: absolute;
margin-left: -6px;
margin-top: -4px;
left: 69.1515%;
width: 12px;
height: 12px;
background-color: #737596;
cursor: -webkit-grab;
cursor: grab;
border-radius: 50%;
-ms-touch-action: pan-x;
touch-action: pan-x;
}
}
</style>
...@@ -10,13 +10,23 @@ ...@@ -10,13 +10,23 @@
></video> ></video>
</div> </div>
<div class="operate-area"> <div class="operate-area">
<div class="play-area">
<input <input
id="screenshot-input" id="screenshot-input"
type="file" type="file"
style="display:none;" style="display:none;"
@change="changeFile" @change="changeFile"
> >
<label id="select-btn">选择文件</label> <label id="select-btn">
<span>选择文件</span>
</label>
</div>
<div class="time-area">
<div id="ss-time-line">
<div class="track"></div>
</div>
</div>
<div class="clip-area"></div>
</div> </div>
</div> </div>
</template> </template>
...@@ -26,21 +36,26 @@ export default { ...@@ -26,21 +36,26 @@ export default {
name: 'Screenshot', name: 'Screenshot',
data() { data() {
return { return {
srcUrl: null srcUrl: null,
videoEle: null,
current: 0,
duration: 10
} }
}, },
created() {}, created() {},
mounted() { mounted() {
let input = document.getElementById('screenshot-input') let input = document.getElementById('screenshot-input')
let fileBtn = document.getElementById('select-btn') let fileBtn = document.getElementById('select-btn')
fileBtn.addEventListener('click', function () { fileBtn.addEventListener('click', function() {
input.click() input.click()
}) })
let video = document.getElementById('screenshot-video') let video = document.getElementById('screenshot-video')
video.onerror = function (e) {
this.videoEle = video
video.onerror = function(e) {
console.log('onerror', e) console.log('onerror', e)
} }
video.addEventListener('loadedmetadata', function (e) { video.addEventListener('loadedmetadata', function(e) {
console.log('loadedmetadata', e) console.log('loadedmetadata', e)
//webkitVideoDecodedByteCount //webkitVideoDecodedByteCount
if (e.target.webkitVideoDecodedByteCount < 1) { if (e.target.webkitVideoDecodedByteCount < 1) {
...@@ -51,24 +66,11 @@ export default { ...@@ -51,24 +66,11 @@ export default {
//loadedmetadata //loadedmetadata
}, },
methods: { methods: {
selectClick() {},
changeFile(e) { changeFile(e) {
//console.log('changeFile', e) //console.log('changeFile', e)
if (e.target.files[0]) { if (e.target.files[0]) {
this.srcUrl = URL.createObjectURL(e.target.files[0]) this.srcUrl = URL.createObjectURL(e.target.files[0])
// let _this = this
// let reader = new FileReader()
// reader.addEventListener(
// 'load',
// () => {
// console.log('_this.srcUrl', this)
// _this.srcUrl = reader.result
// },
// false
// )
// reader.readAsDataURL(e.target.files[0])
} }
//e.target
} }
} }
} }
...@@ -76,20 +78,27 @@ export default { ...@@ -76,20 +78,27 @@ export default {
<style lang="scss" scoped> <style lang="scss" scoped>
.screenshot { .screenshot {
position: relative;
width: 100%; width: 100%;
height: 100%; height: 100%;
margin: 30px;
display: flex; display: flex;
flex-direction: column; flex-direction: column;
.content { .content {
height: 90%; height: 100%;
margin: 20px 30px; margin: 20px 30px;
background-color: lightcyan; background-color: lightcyan;
} }
.operate-area { .operate-area {
background-color: aqua;
height: 200px;
display: flex;
flex-shrink: 0;
#select-btn { #select-btn {
width: 200px; background-color: bisque;
height: 100px; width: 100px;
height: 30px;
line-height: 30px;
} }
} }
} }
......
<template> <template>
<div class="video-cutter"> <div class="video-cutter">
<div class="video-content"> <div class="video-content">
<VideoPlayer <videoPlayer
@currentTime="changeTime" @currentTime="changeTime"
@end="playEnd" @end="playEnd"
@timeupdate="timeupdate" @timeupdate="timeupdate"
></VideoPlayer> ></videoPlayer>
</div> </div>
<div class="video-btn"> <div class="video-btn">
<videoChange @changeVideo="changeVideo"></videoChange> <videoChange @changeVideo="changeVideo"></videoChange>
...@@ -14,9 +14,18 @@ ...@@ -14,9 +14,18 @@
:now-time="nowTime" :now-time="nowTime"
@play="videoPlay" @play="videoPlay"
></videoControl> ></videoControl>
<div></div> <div class="video-water">
<input
id="cutterRemoveWater"
v-model="noWater"
type="checkbox"
>
<label for="cutterRemoveWater">去除水印</label>
</div>
</div>
<div class="timeline-content">
<videoTimeline :info="timelineObj"></videoTimeline>
</div> </div>
<div></div>
<div></div> <div></div>
</div> </div>
</template> </template>
...@@ -27,7 +36,8 @@ export default { ...@@ -27,7 +36,8 @@ export default {
components: { components: {
VideoPlayer: () => import('@/components/videoCutter/videoPlayer.vue'), VideoPlayer: () => import('@/components/videoCutter/videoPlayer.vue'),
VideoChange: () => import('@/components/videoCutter/videoChange.vue'), VideoChange: () => import('@/components/videoCutter/videoChange.vue'),
VideoControl: () => import('@/components/videoCutter/videoControl.vue') VideoControl: () => import('@/components/videoCutter/videoControl.vue'),
VideoTimeline: () => import('@/components/videoCutter/videoTimeline.vue')
}, },
data() { data() {
return { return {
...@@ -35,7 +45,9 @@ export default { ...@@ -35,7 +45,9 @@ export default {
nowTime: 0, nowTime: 0,
duration: 0, duration: 0,
playing: false, playing: false,
canPlay: false canPlay: false,
noWater: true,
timelineObj: { step: 0.1, min: 0, max: 10, val: 0 }
} }
}, },
created() {}, created() {},
...@@ -48,6 +60,7 @@ export default { ...@@ -48,6 +60,7 @@ export default {
}, },
canPlayFunc(data) { canPlayFunc(data) {
this.duration = data this.duration = data
this.timelineObj.max = this.duration
this.canPlay = true this.canPlay = true
}, },
videoPlay() { videoPlay() {
...@@ -59,6 +72,7 @@ export default { ...@@ -59,6 +72,7 @@ export default {
ob.play = true ob.play = true
if (this.nowTime >= this.duration) { if (this.nowTime >= this.duration) {
ob.time = 0 ob.time = 0
this.timelineObj.val = 0
} }
} }
this.playing = !this.playing this.playing = !this.playing
...@@ -70,9 +84,11 @@ export default { ...@@ -70,9 +84,11 @@ export default {
playEnd() { playEnd() {
this.playing = false this.playing = false
this.nowTime = this.duration this.nowTime = this.duration
this.timelineObj.val = this.nowTime
}, },
timeupdate(time) { timeupdate(time) {
this.nowTime = time this.nowTime = time
this.timelineObj.val = this.nowTime
} }
} }
} }
...@@ -92,4 +108,21 @@ export default { ...@@ -92,4 +108,21 @@ export default {
display: flex; display: flex;
justify-content: space-between; justify-content: space-between;
} }
.video-water {
display: flex;
align-items: center;
input {
margin-right: 4px;
}
* {
cursor: pointer;
}
}
.timeline-content {
width: 100%;
margin: 10px 0;
padding: 0 20px;
}
</style> </style>
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment