Skip to content

Commit

Permalink
feat: customisable font scale
Browse files Browse the repository at this point in the history
  • Loading branch information
Julusian committed Mar 28, 2022
1 parent 9c06dd2 commit 951d121
Show file tree
Hide file tree
Showing 2 changed files with 27 additions and 8 deletions.
15 changes: 14 additions & 1 deletion src/atem.ts
Original file line number Diff line number Diff line change
Expand Up @@ -240,11 +240,13 @@ export class BasicAtem extends EventEmitter<AtemEvents> {

export class Atem extends BasicAtem {
#multiviewerFontFace: Promise<FontFace>
#multiviewerFontScale: number

constructor(options?: AtemOptions) {
super(options)

this.#multiviewerFontFace = PLazy.from(async () => loadFont())
this.#multiviewerFontScale = 1.0
}

/**
Expand All @@ -264,6 +266,17 @@ export class Atem extends BasicAtem {

this.#multiviewerFontFace = Promise.resolve(loadedFont)
}
/**
* Set the scale factor for the multiviewer text. Default is 1
*/
public setMultiviewerFontScale(scale: number | null): void {
if (typeof scale === 'number') {
if (scale <= 0) throw new Error('Scale must be greater than 0')
this.#multiviewerFontScale = scale
} else if (scale === null) {
this.#multiviewerFontScale = 1.0
}
}

public async changeProgramInput(input: number, me = 0): Promise<void> {
const command = new Commands.ProgramInputCommand(me, input)
Expand Down Expand Up @@ -1019,7 +1032,7 @@ export class Atem extends BasicAtem {

const fontFace = await this.#multiviewerFontFace

const buffer = generateMultiviewerLabel(fontFace, text, props)
const buffer = generateMultiviewerLabel(fontFace, this.#multiviewerFontScale, text, props)
// Note: we should probably validate the buffer looks like it doesn't contain crashy data, but as we generate we can trust it
return this.dataTransferManager.uploadMultiViewerLabel(inputId, buffer)
}
Expand Down
20 changes: 13 additions & 7 deletions src/lib/multiviewLabel.ts
Original file line number Diff line number Diff line change
Expand Up @@ -136,17 +136,19 @@ function calculateWidthAndTrimText(

function drawTextToBuffer(
face: FontFace,
fontScale: number,
buffer: Buffer,
spec: ResolutionSpec,
rawText: string,
bufferYOffset: number,
bufferWidth: number
): void {
face.setPixelSizes(spec.fontHeight, spec.fontHeight)
const fontHeight = spec.fontHeight * fontScale
face.setPixelSizes(fontHeight, fontHeight)

const { width: textWidth, str: newStr } = calculateWidthAndTrimText(face, rawText, spec.width - spec.xPad * 2)
const boundaryWidth = Math.floor(textWidth + spec.xPad * 2)
const boundaryHeight = Math.floor(spec.fontHeight + spec.yPadTop + spec.yPadBottom)
const boundaryHeight = Math.floor(fontHeight + spec.yPadTop + spec.yPadBottom)
const bufferXOffset = Math.floor((bufferWidth - spec.width) / 2)

// Fill background of boundary, and a 2px border
Expand Down Expand Up @@ -190,7 +192,7 @@ function drawTextToBuffer(

const maxLeft = boundaryXOffset + spec.width + spec.xPad
let charLeft = boundaryXOffset + spec.xPad
const textTop = boundaryYOffset + spec.fontHeight + spec.yPadTop
const textTop = boundaryYOffset + fontHeight + spec.yPadTop

// Draw text characters
for (let i = 0; i < newStr.length; i++) {
Expand Down Expand Up @@ -239,7 +241,12 @@ export interface GenerateMultiviewerLabelProps {
* @param props Specify which resolutions to generate for
* @returns Buffer
*/
export function generateMultiviewerLabel(face: FontFace, str: string, props: GenerateMultiviewerLabelProps): Buffer {
export function generateMultiviewerLabel(
face: FontFace,
fontScale: number,
str: string,
props: GenerateMultiviewerLabelProps
): Buffer {
// Calculate the sizes
let width: number | undefined
let height = 0
Expand All @@ -264,7 +271,7 @@ export function generateMultiviewerLabel(face: FontFace, str: string, props: Gen

let yOffset = 0
const drawRes = (spec: ResolutionSpec): void => {
drawTextToBuffer(face, buffer, spec, str, yOffset, width2)
drawTextToBuffer(face, fontScale, buffer, spec, str, yOffset, width2)
yOffset += spec.height
}

Expand Down Expand Up @@ -325,8 +332,7 @@ export function calculateGenerateMultiviewerLabelProps(
}

export async function loadFont(fontPath?: string): Promise<FontFace> {
// if (!fontPath) fontPath = path.join(__dirname, '../../assets/roboto/Roboto-Regular.ttf')
if (!fontPath) fontPath = path.join(__dirname, '../../assets/Helvetica.ttf')
if (!fontPath) fontPath = path.join(__dirname, '../../assets/roboto/Roboto-Regular.ttf')

const fontFile = await readFile(fontPath)
return NewMemoryFace(fontFile)
Expand Down

0 comments on commit 951d121

Please sign in to comment.