Steam Events
Some things do not happen because your game asked. A friend accepts an invite, a player clicks "Join Game" in their friends list, another player opens a direct connection, a DLC finishes installing. Steam raises those on its own, and this is how the game hears about them.
Two calls: pollEvents() lets Steam hand over whatever it has been holding and says whether anything is waiting, and popEvent() takes the oldest one. Call them from a loop or a timer.
Events are kept until you fetch them, up to 256. Past that the oldest go first, so a game that polls now and then still sees what is happening now.
Methods
pollEvents()
Lets Steam deliver, and says whether anything is waiting.
javascript
if (await steam.pollEvents()) {
// something arrived
}popEvent()
The oldest event, or null when there is none.
javascript
let event;
while ((event = await steam.popEvent())) {
console.log(event.type, event);
}The events
type | Fields | What happened |
|---|---|---|
overlayActivated | active | The Steam overlay opened or closed |
lobbyJoinRequested | lobbyId, friendId | The player accepted an invite from their friends list |
richPresenceJoinRequested | friendId, connect | The same, through your rich presence connect string |
p2pSessionRequest | steamId | Another player wants a direct connection |
dlcInstalled | appId | A DLC finished installing while the game was running |
inventoryResultReady | handle, result | An inventory call finished |
inventoryFullUpdate | handle | The player's inventory changed |
musicPlaybackStatusChanged | — | Steam Music started, stopped or paused |
musicVolumeChanged | volume | The player changed the Steam Music volume |
parentalSettingsChanged | — | Family View was changed while the game was running |
Steam ids and lobby ids arrive as decimal strings, because they are 64-bit numbers and JavaScript cannot hold those exactly.
Examples
One pump, in the game loop
javascript
async function pumpSteam() {
if (!(await steam.pollEvents())) return;
let e;
while ((e = await steam.popEvent())) {
switch (e.type) {
case 'lobbyJoinRequested':
await steam.joinLobby(e.lobbyId);
break;
case 'p2pSessionRequest':
await steam.acceptP2PSessionWithUser(e.steamId);
break;
case 'overlayActivated':
if (e.active) pauseGame();
break;
}
}
}
setInterval(pumpSteam, 100);Joining from the friends list
A player who clicks "Join Game" on a friend gets one of two events, depending on whether the friend's game published a lobby or a connect string. Handle both and the button works either way.
javascript
case 'lobbyJoinRequested':
await steam.joinLobby(e.lobbyId);
break;
case 'richPresenceJoinRequested':
// whatever you put in the 'connect' rich presence key
const params = new URLSearchParams(e.connect);
await joinServer(params.get('host'));
break;Waiting for a DLC
javascript
case 'dlcInstalled':
if (e.appId === MY_EXPANSION_APPID) {
await unlockExpansionContent();
showToast('Expansion installed');
}
break;Notes
- Polling costs almost nothing when there is nothing waiting. Once or twice a second is plenty for invites; every frame is fine too.
- The overlay also has its own callback,
overlay.onStateChange(), which is usually easier than watching foroverlayActivated. - Events need Steam running and
init()to have succeeded. Without Steam,pollEvents()answersfalsefor ever and nothing else happens.