Skip to content

Commit

Permalink
Initial commit
Browse files Browse the repository at this point in the history
  • Loading branch information
Dan-Shields committed Oct 15, 2018
0 parents commit 43972b1
Show file tree
Hide file tree
Showing 6 changed files with 1,681 additions and 0 deletions.
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
node_modules/
build/
6 changes: 6 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
1. Install and enable OBS Websocket - https://obsproject.com/forum/resources/obs-websocket-remote-control-of-obs-studio-made-easy.466/
2. Create camera sources in OBS named with the SteamID64 of the player it shows
3. Copy the "gamestate_integration_dota-cams.cfg" file into "<Steam_install_directory>/steamapps/common/dota 2 beta/game/dota/cfg/" and edit if necessary
4. Ensure the config file ("config/default.json") is correct. It's setup to use the defaults for GSI and OBS.
5. Run the executable
6. The program will detect when the game is in spectate mode, and begin showing/hiding the cams.
11 changes: 11 additions & 0 deletions config/default.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
{
"d2gsi": {
"ip": "localhost",
"port": 9091,
"tokens": ""
},
"obs": {
"address": "localhost:4444",
"password": ""
}
}
127 changes: 127 additions & 0 deletions index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,127 @@
const config = require('config');
const d2gsi = require('dota2-gsi');
const clone = require('clone');
const OBSWebSocket = require('obs-websocket-js');

const d2gsiConf = config.get('d2gsi');

const gsiServer = new d2gsi(d2gsiConf);

const obs = new OBSWebSocket();
var sourceList = [];

const obsConf = config.get('obs');
obs.connect(obsConf)
.then(() => {
console.log(`Successfully connected to OBS.`);
return obs.GetSourcesList();
})
.then(data => {
// populate sourceList
sourceList = data.sources.filter(source => source.type == 'input');

// start with none visible
sourceList.forEach((source) => {
obs.SetSceneItemProperties({item: source.name, visible: false})
});
})
.then(() => {
gsiServer.events.on('newclient', function(client) {
console.log("New GSI client connection, IP address: " + client.ip);

var shownPlayerID = null;

client.on('newdata', newdata => {
var data = clone(newdata);

try {
// combine the two team's players/heroes
var allHeroes = Object.assign(data.hero.team2, data.hero.team3);
var allPlayers = Object.assign(data.player.team2, data.player.team3);
}
catch (err) {
// indicates not in spectate slot
return;
}

// find the selected hero (null if none)
var newShown = null;
for (var player in allHeroes) {
if (allHeroes[player].selected_unit) {
newShown = allPlayers[player];
}
}

// show/hide sources depending on what is selected
if (newShown == null && shownPlayerID !== null) {
console.log('no player selected');

// hide previous cam (all will be hidden)
obs.SetSceneItemProperties({item: shownPlayerID, visible: false})
.catch(err => {
console.log(err.error + ' (' + shownPlayerID + ')');
});

shownPlayerID = null;
} else if (newShown !== null && shownPlayerID !== newShown.steamid) {
if (sourceList.find(obj => obj.name == newShown.steamid) === undefined) {
// source not found for player
console.log('no source for ' + newShown.name + ' (' + newShown.steamid + ')');

if (shownPlayerID !== null) {
obs.SetSceneItemProperties({item: shownPlayerID, visible: false})
.catch(err => {
console.log(err.error + ' (' + shownPlayerID + ')');
});
}

} else {
// source found for player
console.log('showing ' + newShown.name + ' (' + newShown.steamid + ')');

// hide existing cam if one is shown
if (shownPlayerID) {
obs.SetSceneItemProperties({item: shownPlayerID, visible: false})
.catch(err => {
console.log(err.error + ' (' + shownPlayerID + ')');
});
}

// show new cam
obs.SetSceneItemProperties({item: newShown.steamid, visible: true})
.catch(err => {
console.log(err.error + ' (' + newShown.steamid + ')');
});
}

shownPlayerID = newShown.steamid;
}
});
});
})
.catch(err => {
console.log(err);
});

//handle added sources
obs.on('SceneItemAdded', (data) => {
sourceList += data.item-name;
});

//handle removed sources
obs.on('SceneItemRemoved', (data)=> {
var obj = sourceList.find(obj => obj.name = data.name)

if (obj !== undefined) {
sourceList.splice( list.indexOf(obj), 1 );
}
});

//handle scene changes
obs.on('SwitchScenes', (data) => {
sourceList = data.sources;
});

obs.on('error', err => {
console.error('socket error:', err);
});
Loading

0 comments on commit 43972b1

Please sign in to comment.