Skip to content

Commit

Permalink
feat: support streamdeck plus
Browse files Browse the repository at this point in the history
  • Loading branch information
Julusian committed Dec 2, 2022
1 parent f021503 commit 5e9a19b
Showing 1 changed file with 89 additions and 6 deletions.
95 changes: 89 additions & 6 deletions src/device-types/streamdeck.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { StreamDeck } from '@elgato-stream-deck/node'
import { DeviceModelId, StreamDeck } from '@elgato-stream-deck/node'
import sharp = require('sharp')
import { CompanionSatelliteClient } from '../client'
import { CardGenerator } from '../cards'
Expand All @@ -12,6 +12,7 @@ export class StreamDeckWrapper implements WrappedDevice {

#queueOutputId: number
#queue: ImageWriteQueue | undefined
#queueLcdStrip: ImageWriteQueue | undefined

public get deviceId(): string {
return this.#deviceId
Expand Down Expand Up @@ -55,16 +56,55 @@ export class StreamDeckWrapper implements WrappedDevice {
}
})
}

if (this.#deck.LCD_ENCODER_SIZE) {
const encoderSize = this.#deck.LCD_ENCODER_SIZE
const xPad = (encoderSize.width - encoderSize.height) / 2
this.#queueLcdStrip = new ImageWriteQueue(async (key: number, buffer: Buffer) => {
const outputId = this.#queueOutputId

let newbuffer: Buffer
// scale if necessary
try {
newbuffer = await sharp(buffer, { raw: { width: 72, height: 72, channels: 3 } })
.resize(encoderSize.height, encoderSize.height)
.raw()
.toBuffer()
} catch (e) {
console.log(`device(${deviceId}): scale image failed: ${e}`)
return
}

// Check if generated image is still valid
if (this.#queueOutputId === outputId) {
try {
await this.#deck.fillLcdRegion(key * encoderSize.width + xPad, 0, newbuffer, {
format: 'rgb',
width: encoderSize.height,
height: encoderSize.height,
})
} catch (e_1) {
console.error(`device(${deviceId}): fillImage failed: ${e_1}`)
}
}
})
}
}

getRegisterProps(): DeviceRegisterProps {
return {
const info = {
keysTotal: this.#deck.NUM_KEYS,
keysPerRow: this.#deck.KEY_COLUMNS,
bitmaps: this.#deck.ICON_SIZE !== 0,
colours: false,
text: false,
}

if (this.#deck.MODEL === DeviceModelId.PLUS) {
info.keysTotal += this.#deck.NUM_ENCODERS * 2
}

return info
}

async close(): Promise<void> {
Expand All @@ -76,6 +116,44 @@ export class StreamDeckWrapper implements WrappedDevice {
this.#deck.on('down', (key) => client.keyDown(this.deviceId, key))
this.#deck.on('up', (key) => client.keyUp(this.deviceId, key))

if (this.#deck.MODEL === DeviceModelId.PLUS) {
this.#deck.on('encoderDown', (encoder) => {
const index = this.#deck.NUM_KEYS + this.#deck.NUM_ENCODERS + encoder
client.keyDown(this.deviceId, index)
})
this.#deck.on('encoderUp', (encoder) => {
const index = this.#deck.NUM_KEYS + this.#deck.NUM_ENCODERS + encoder
client.keyUp(this.deviceId, index)
})
this.#deck.on('rotateLeft', (encoder) => {
const index = this.#deck.NUM_KEYS + this.#deck.NUM_ENCODERS + encoder
client.rotateLeft(this.deviceId, index)
})
this.#deck.on('rotateRight', (encoder) => {
const index = this.#deck.NUM_KEYS + this.#deck.NUM_ENCODERS + encoder
client.rotateRight(this.deviceId, index)
})

this.#deck.on('lcdShortPress', (encoder) => {
const index = this.#deck.NUM_KEYS + encoder

client.keyDown(this.deviceId, index)

setTimeout(() => {
client.keyUp(this.deviceId, index)
}, 20)
})
this.#deck.on('lcdLongPress', (encoder) => {
const index = this.#deck.NUM_KEYS + encoder

client.keyDown(this.deviceId, index)

setTimeout(() => {
client.keyUp(this.deviceId, index)
}, 20)
})
}

// Start with blanking it
await this.blankDevice()

Expand All @@ -94,10 +172,15 @@ export class StreamDeckWrapper implements WrappedDevice {
async draw(d: DeviceDrawProps): Promise<void> {
if (this.#deck.ICON_SIZE !== 0) {
if (d.image) {
if (this.#queue) {
this.#queue.queue(d.keyIndex, d.image)
} else {
await this.#deck.fillKeyBuffer(d.keyIndex, d.image)
if (d.keyIndex < this.#deck.NUM_KEYS) {
if (this.#queue) {
this.#queue.queue(d.keyIndex, d.image)
} else {
await this.#deck.fillKeyBuffer(d.keyIndex, d.image)
}
} else if (this.#deck.MODEL === DeviceModelId.PLUS && d.keyIndex < this.#deck.NUM_KEYS + 4) {
const index = d.keyIndex - this.#deck.NUM_KEYS
this.#queueLcdStrip?.queue(index, d.image)
}
} else {
throw new Error(`Cannot draw for Streamdeck without image`)
Expand Down

0 comments on commit 5e9a19b

Please sign in to comment.