Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat:add support for manualReloadFromPropChanges prop #67

Merged
merged 2 commits into from
Jan 31, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 10 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ This library has [the same support characteristics as the Brightcove Player Load
- [Props](#props)
- [`attrs`](#attrs)
- [`baseUrl`](#baseurl)
- [`manualReloadFromPropChanges`](#manualreloadfrompropchanges)
- [Other Props](#other-props)
- [Effects of Prop Changes](#effects-of-prop-changes)
- [View the Demo](#view-the-demo)
Expand Down Expand Up @@ -96,6 +97,14 @@ Used to override the base URL for the Brightcove Player being embedded.

Most users will never need this prop. By default, players are loaded from Brightcove's player CDN (`players.brightcove.net`).

### `manualReloadFromPropChanges`

Type: `boolean`

Used to specify if reloading the player after prop changes will be handled manually. This can be done by calling `refToReactPlayerLoader.loadPlayer()`.

See [Effects of Prop Changes](#effects-of-prop-changes) below for the effects of prop changes.

### Other Props

All props not specified above are passed to the [Brightcove Player Loader](https://github.com/brightcove/player-loader#parameters) with a few differences:
Expand All @@ -119,7 +128,7 @@ The following props will update the player's state _without_ a reload:
- `playlistVideoId`
- `videoId`

All other prop changes will cause a complete dispose/reload.
All other prop changes, excluding props that are `function`'s, will cause a complete dispose/reload.

## View the Demo

Expand Down
29 changes: 25 additions & 4 deletions src/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -45,13 +45,18 @@ class ReactPlayerLoader extends React.Component {
* @param {Object} [props.attrs]
* Used to set attributes on the component element that contains the
* embedded Brightcove Player.
*
* @param {boolean} [props.manualReloadFromPropChanges]
* Used to specify if reloading the player after prop changes will be handled manually.
*
*/
constructor(props) {
super(props);
this.refNode = null;
this.setRefNode = ref => {
this.refNode = ref;
};
this.loadPlayer = this.loadPlayer.bind(this);
}

/**
Expand Down Expand Up @@ -123,6 +128,7 @@ class ReactPlayerLoader extends React.Component {
// Delete props that are not meant to be passed to player-loader.
delete options.attrs;
delete options.baseUrl;
delete options.manualReloadFromPropChanges;

// If a base URL is provided, it should only apply to this player load.
// This means we need to back up the original base URL and restore it
Expand Down Expand Up @@ -325,17 +331,32 @@ class ReactPlayerLoader extends React.Component {
const previous = prevProps[key];
const current = this.props[key];

// Do not compare functions
if (typeof current === 'function') {
return acc;
}

if (typeof current === 'object' && current !== null) {
if (JSON.stringify(current) !== JSON.stringify(previous)) {
acc[key] = true;
}

return acc;
}

if (current !== previous) {
acc[key] = true;
}

return acc;
}, {});

// Dispose and recreate the player if any changed keys cannot be handled.
if (Object.keys(changes).some(k => UPDATEABLE_PROPS.indexOf(k) === -1)) {
this.loadPlayer();
return;
if (!this.props.manualReloadFromPropChanges) {
// Dispose and recreate the player if any changed keys cannot be handled.
if (Object.keys(changes).some(k => UPDATEABLE_PROPS.indexOf(k) === -1)) {
this.loadPlayer();
return;
}
}

this.updatePlayer(changes);
Expand Down
62 changes: 62 additions & 0 deletions test/index.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -623,4 +623,66 @@ QUnit.module('ReactPlayerLoader', {

rerender = render(React.createElement(ReactPlayerLoader, props)).rerender;
});

QUnit.test('loadPlayer() method reloads player', function(assert) {
const done = assert.async(2);

const props = {
accountId: '1',
applicationId: 'foo',
onSuccess: ({ref, type}) => {
assert.ok(true, 'the success callback was called');
done();
}
};

const reactPlayerLoader = ReactDOM.render(
React.createElement(ReactPlayerLoader, props),
this.fixture
);

reactPlayerLoader.loadPlayer();
});

QUnit.test('set manualReloadFromPropChanges to true', function(assert) {
const done = assert.async(2);
let rerender;
const props = {
accountId: '1',
applicationId: 'foo',
manualReloadFromPropChanges: true,
onSuccess: ({ref, type}) => {
if (props.applicationId !== 'bar') {
props.applicationId = 'bar';
done();
}
rerender(React.createElement(ReactPlayerLoader, props));
assert.ok(true, 'the success callback was called');
done();
}
};

rerender = render(React.createElement(ReactPlayerLoader, props)).rerender;
});

QUnit.test('set manualReloadFromPropChanges to false', function(assert) {
const done = assert.async(3);
let rerender;
const props = {
accountId: '1',
applicationId: 'foo',
manualReloadFromPropChanges: false,
onSuccess: ({ref, type}) => {
if (props.applicationId !== 'bar') {
props.applicationId = 'bar';
done();
}
rerender(React.createElement(ReactPlayerLoader, props));
assert.ok(true, 'the success callback was called');
done();
}
};

rerender = render(React.createElement(ReactPlayerLoader, props)).rerender;
});
});