Compare commits
6 Commits
4a53a2fb55
...
509485e173
| Author | SHA1 | Date | |
|---|---|---|---|
| 509485e173 | |||
| e250443ca3 | |||
| 6b9c03eb84 | |||
| 9f1320a907 | |||
| d68ebdef79 | |||
| a025fcad43 |
33
package-lock.json
generated
33
package-lock.json
generated
@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "peer-calls",
|
"name": "peer-calls",
|
||||||
"version": "3.0.5",
|
"version": "3.0.8",
|
||||||
"lockfileVersion": 1,
|
"lockfileVersion": 1,
|
||||||
"requires": true,
|
"requires": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
@ -4877,8 +4877,7 @@
|
|||||||
},
|
},
|
||||||
"kind-of": {
|
"kind-of": {
|
||||||
"version": "6.0.2",
|
"version": "6.0.2",
|
||||||
"resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.2.tgz",
|
"resolved": "",
|
||||||
"integrity": "sha512-s5kLOcnH0XqDO+FvuaLX8DDjZ18CGFk7VygH40QoKPUQhW4e2rvM0rwUq0t8IQDOwYSeLK01U90OjzBTme2QqA==",
|
|
||||||
"dev": true
|
"dev": true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -14274,6 +14273,15 @@
|
|||||||
"integrity": "sha512-nfMOlASu9OnRJo1mbEk2cz0D56a1MBNrJ7orjRZQG10XDyuvwksKbuXNp6qa+kbn839HwjwhBzhFmdsaEAfauA==",
|
"integrity": "sha512-nfMOlASu9OnRJo1mbEk2cz0D56a1MBNrJ7orjRZQG10XDyuvwksKbuXNp6qa+kbn839HwjwhBzhFmdsaEAfauA==",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
|
"rtcpeerconnection-shim": {
|
||||||
|
"version": "1.2.15",
|
||||||
|
"resolved": "https://registry.npmjs.org/rtcpeerconnection-shim/-/rtcpeerconnection-shim-1.2.15.tgz",
|
||||||
|
"integrity": "sha512-C6DxhXt7bssQ1nHb154lqeL0SXz5Dx4RczXZu2Aa/L1NJFnEVDxFwCBo3fqtuljhHIGceg5JKBV4XJ0gW5JKyw==",
|
||||||
|
"dev": true,
|
||||||
|
"requires": {
|
||||||
|
"sdp": "^2.6.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
"run-async": {
|
"run-async": {
|
||||||
"version": "2.3.0",
|
"version": "2.3.0",
|
||||||
"resolved": "https://registry.npmjs.org/run-async/-/run-async-2.3.0.tgz",
|
"resolved": "https://registry.npmjs.org/run-async/-/run-async-2.3.0.tgz",
|
||||||
@ -14452,6 +14460,12 @@
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"sdp": {
|
||||||
|
"version": "2.12.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/sdp/-/sdp-2.12.0.tgz",
|
||||||
|
"integrity": "sha512-jhXqQAQVM+8Xj5EjJGVweuEzgtGWb3tmEEpl3CLP3cStInSbVHSg0QWOGQzNq8pSID4JkpeV2mPqlMDLrm0/Vw==",
|
||||||
|
"dev": true
|
||||||
|
},
|
||||||
"semver": {
|
"semver": {
|
||||||
"version": "5.6.0",
|
"version": "5.6.0",
|
||||||
"resolved": "https://registry.npmjs.org/semver/-/semver-5.6.0.tgz",
|
"resolved": "https://registry.npmjs.org/semver/-/semver-5.6.0.tgz",
|
||||||
@ -14805,8 +14819,7 @@
|
|||||||
},
|
},
|
||||||
"kind-of": {
|
"kind-of": {
|
||||||
"version": "6.0.2",
|
"version": "6.0.2",
|
||||||
"resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.2.tgz",
|
"resolved": "",
|
||||||
"integrity": "sha512-s5kLOcnH0XqDO+FvuaLX8DDjZ18CGFk7VygH40QoKPUQhW4e2rvM0rwUq0t8IQDOwYSeLK01U90OjzBTme2QqA==",
|
|
||||||
"dev": true
|
"dev": true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -16325,6 +16338,16 @@
|
|||||||
"integrity": "sha512-YQ+BmxuTgd6UXZW3+ICGfyqRyHXVlD5GtQr5+qjiNW7bF0cqrzX500HVXPBOvgXb5YnzDd+h0zqyv61KUD7+Sg==",
|
"integrity": "sha512-YQ+BmxuTgd6UXZW3+ICGfyqRyHXVlD5GtQr5+qjiNW7bF0cqrzX500HVXPBOvgXb5YnzDd+h0zqyv61KUD7+Sg==",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
|
"webrtc-adapter": {
|
||||||
|
"version": "7.5.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/webrtc-adapter/-/webrtc-adapter-7.5.0.tgz",
|
||||||
|
"integrity": "sha512-cUqlw310uLLSYvO8FTNCVmGWSMlMt6vuSDkcYL1nW+RUvAILJ3jEIvAUgFQU5EFGnU+mf9/No14BFv3U+hoxBQ==",
|
||||||
|
"dev": true,
|
||||||
|
"requires": {
|
||||||
|
"rtcpeerconnection-shim": "^1.2.15",
|
||||||
|
"sdp": "^2.12.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
"whatwg-encoding": {
|
"whatwg-encoding": {
|
||||||
"version": "1.0.5",
|
"version": "1.0.5",
|
||||||
"resolved": "https://registry.npmjs.org/whatwg-encoding/-/whatwg-encoding-1.0.5.tgz",
|
"resolved": "https://registry.npmjs.org/whatwg-encoding/-/whatwg-encoding-1.0.5.tgz",
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "peer-calls",
|
"name": "peer-calls",
|
||||||
"version": "3.0.5",
|
"version": "3.0.8",
|
||||||
"description": "Group peer to peer video calls for anybody.",
|
"description": "Group peer to peer video calls for anybody.",
|
||||||
"repository": "https://github.com/jeremija/peer-calls",
|
"repository": "https://github.com/jeremija/peer-calls",
|
||||||
"main": "lib/index.js",
|
"main": "lib/index.js",
|
||||||
@ -112,6 +112,7 @@
|
|||||||
"ts-node": "^8.5.2",
|
"ts-node": "^8.5.2",
|
||||||
"tsify": "^4.0.1",
|
"tsify": "^4.0.1",
|
||||||
"typescript": "^3.7.2",
|
"typescript": "^3.7.2",
|
||||||
"watchify": "^3.11.1"
|
"watchify": "^3.11.1",
|
||||||
|
"webrtc-adapter": "^7.5.0"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -16,6 +16,7 @@ export interface VideoProps {
|
|||||||
|
|
||||||
export default class Video extends React.PureComponent<VideoProps> {
|
export default class Video extends React.PureComponent<VideoProps> {
|
||||||
videoRef = React.createRef<HTMLVideoElement>()
|
videoRef = React.createRef<HTMLVideoElement>()
|
||||||
|
timeout?: number
|
||||||
|
|
||||||
static defaultProps = {
|
static defaultProps = {
|
||||||
muted: false,
|
muted: false,
|
||||||
@ -23,8 +24,26 @@ export default class Video extends React.PureComponent<VideoProps> {
|
|||||||
}
|
}
|
||||||
handleClick: ReactEventHandler<HTMLVideoElement> = e => {
|
handleClick: ReactEventHandler<HTMLVideoElement> = e => {
|
||||||
const { onClick, userId } = this.props
|
const { onClick, userId } = this.props
|
||||||
this.props.play()
|
if (this.timeout) {
|
||||||
onClick(userId)
|
// if the timeout was cancelled, execute click
|
||||||
|
this.props.play()
|
||||||
|
onClick(userId)
|
||||||
|
}
|
||||||
|
this.timeout = undefined
|
||||||
|
}
|
||||||
|
handleMouseDown: ReactEventHandler<HTMLVideoElement> = e => {
|
||||||
|
clearTimeout(this.timeout)
|
||||||
|
this.timeout = window.setTimeout(this.toggleCover, 300)
|
||||||
|
}
|
||||||
|
handleMouseUp: ReactEventHandler<HTMLVideoElement> = e => {
|
||||||
|
clearTimeout(this.timeout)
|
||||||
|
}
|
||||||
|
toggleCover = () => {
|
||||||
|
this.timeout = undefined
|
||||||
|
const v = this.videoRef.current
|
||||||
|
if (v) {
|
||||||
|
v.style.objectFit = v.style.objectFit ? '' : 'cover'
|
||||||
|
}
|
||||||
}
|
}
|
||||||
componentDidMount () {
|
componentDidMount () {
|
||||||
this.componentDidUpdate()
|
this.componentDidUpdate()
|
||||||
@ -52,6 +71,10 @@ export default class Video extends React.PureComponent<VideoProps> {
|
|||||||
id={`video-${socket.id}`}
|
id={`video-${socket.id}`}
|
||||||
autoPlay
|
autoPlay
|
||||||
onClick={this.handleClick}
|
onClick={this.handleClick}
|
||||||
|
onMouseDown={this.handleMouseDown}
|
||||||
|
onTouchStart={this.handleMouseDown}
|
||||||
|
onMouseUp={this.handleMouseUp}
|
||||||
|
onTouchEnd={this.handleMouseUp}
|
||||||
onLoadedMetadata={() => this.props.play()}
|
onLoadedMetadata={() => this.props.play()}
|
||||||
playsInline
|
playsInline
|
||||||
ref={this.videoRef}
|
ref={this.videoRef}
|
||||||
|
|||||||
@ -1,6 +1,7 @@
|
|||||||
jest.mock('../actions/CallActions')
|
jest.mock('../actions/CallActions')
|
||||||
jest.mock('../socket')
|
jest.mock('../socket')
|
||||||
jest.mock('../window')
|
jest.mock('../window')
|
||||||
|
jest.useFakeTimers()
|
||||||
|
|
||||||
import React from 'react'
|
import React from 'react'
|
||||||
import ReactDOM from 'react-dom'
|
import ReactDOM from 'react-dom'
|
||||||
@ -108,9 +109,14 @@ describe('App', () => {
|
|||||||
})
|
})
|
||||||
|
|
||||||
describe('video', () => {
|
describe('video', () => {
|
||||||
it('can be activated', () => {
|
beforeEach(() => {
|
||||||
dispatchSpy.mockReset()
|
dispatchSpy.mockReset()
|
||||||
|
})
|
||||||
|
|
||||||
|
it('can be activated', () => {
|
||||||
const video = node.querySelector('video')!
|
const video = node.querySelector('video')!
|
||||||
|
TestUtils.Simulate.mouseDown(video)
|
||||||
|
TestUtils.Simulate.mouseUp(video)
|
||||||
TestUtils.Simulate.click(video)
|
TestUtils.Simulate.click(video)
|
||||||
expect(dispatchSpy.mock.calls[0][0].type).toBe(constants.MEDIA_PLAY)
|
expect(dispatchSpy.mock.calls[0][0].type).toBe(constants.MEDIA_PLAY)
|
||||||
expect(dispatchSpy.mock.calls.slice(1)).toEqual([[{
|
expect(dispatchSpy.mock.calls.slice(1)).toEqual([[{
|
||||||
@ -118,6 +124,18 @@ describe('App', () => {
|
|||||||
payload: { userId: constants.ME + '_0' },
|
payload: { userId: constants.ME + '_0' },
|
||||||
}]])
|
}]])
|
||||||
})
|
})
|
||||||
|
|
||||||
|
it('can toggle object-fit to/from cover by long-pressing', () => {
|
||||||
|
['cover', ''].forEach(objectFit => {
|
||||||
|
const video = node.querySelector('video')!
|
||||||
|
TestUtils.Simulate.mouseDown(video)
|
||||||
|
jest.runAllTimers()
|
||||||
|
TestUtils.Simulate.mouseUp(video)
|
||||||
|
TestUtils.Simulate.click(video)
|
||||||
|
expect(video.style.objectFit).toBe(objectFit)
|
||||||
|
expect(dispatchSpy.mock.calls.slice(1)).toEqual([])
|
||||||
|
})
|
||||||
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
})
|
})
|
||||||
|
|||||||
@ -1,4 +1,5 @@
|
|||||||
import '@babel/polyfill'
|
import '@babel/polyfill'
|
||||||
|
import 'webrtc-adapter'
|
||||||
import App from './containers/App'
|
import App from './containers/App'
|
||||||
import React from 'react'
|
import React from 'react'
|
||||||
import ReactDOM from 'react-dom'
|
import ReactDOM from 'react-dom'
|
||||||
|
|||||||
@ -25,6 +25,10 @@
|
|||||||
width: 100%;
|
width: 100%;
|
||||||
height: 100%;
|
height: 100%;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.video-actions {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.video-container.active {
|
.video-container.active {
|
||||||
@ -43,6 +47,22 @@
|
|||||||
video {
|
video {
|
||||||
border-radius: 0;
|
border-radius: 0;
|
||||||
cursor: inherit;
|
cursor: inherit;
|
||||||
|
object-fit: contain;
|
||||||
|
}
|
||||||
|
|
||||||
|
.video-actions {
|
||||||
|
display: inherit;
|
||||||
|
position: absolute;
|
||||||
|
right: 0;
|
||||||
|
bottom: 0;
|
||||||
|
padding: 1rem;
|
||||||
|
font-family: monospace;
|
||||||
|
user-select: none;
|
||||||
|
|
||||||
|
.action:hover {
|
||||||
|
cursor: pointer;
|
||||||
|
color: white;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -101,8 +101,8 @@ body.call {
|
|||||||
}
|
}
|
||||||
|
|
||||||
input[type="text"] {
|
input[type="text"] {
|
||||||
font-size: 1rem;
|
font-size: 1.2rem;
|
||||||
padding: 1rem 1rem 0.75rem;
|
padding: 1rem 0rem 0.75rem;
|
||||||
width: 100%;
|
width: 100%;
|
||||||
margin-bottom: 1rem;
|
margin-bottom: 1rem;
|
||||||
background: none;
|
background: none;
|
||||||
@ -120,9 +120,9 @@ body.call {
|
|||||||
}
|
}
|
||||||
|
|
||||||
input[type="submit"] {
|
input[type="submit"] {
|
||||||
// font-family: $font-monospace;
|
font-family: $font-monospace;
|
||||||
@include button($color-primary, $color-warning);
|
@include button($color-primary, $color-warning);
|
||||||
font-size: 1rem;
|
font-size: 1.2rem;
|
||||||
padding: 1rem 1rem;
|
padding: 1rem 1rem;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user