0

I need to render N items that are x pixels wide with N-1 spaces y pixels wide between them.

I need to calculate how many items will fir on the screen. What I'm doing is rendering an array of amplitudes as columns. This is my test produce without spaces:

enter image description here

I first calculate how many items will fit, then resample the original array to get exactly the number of values that will fit on the screen. This is the same with 5 pixels per column, you can see that the original array has been resampled:

enter image description here

The formula I use now is no_items = Math.floor(canvasWidth/(barWidth+spaceWidth)):

/**
 * Recalculates waveform data for given width of canvas
 * @param {number} canvasWidth Image width in pixels
 * @param {number} barWidth Width of waveform bars
 * @param {number} spaceWidth Width of spaces between bars
 * @returns {Uint8Array} recalculated bytes
 */
recalculateForWidth(canvasWidth, barWidth, spaceWidth) {
    const no_items = Math.floor(canvasWidth/(barWidth+spaceWidth))
    const result = new Uint8Array(no_items);
    // Resampling code follows
    ...
    return result;
}

But that clearly assumes one extra space at the end of the data - it simply calculates with item width being bar width+ space width.

I want to render bars without space at the end, so how do I calculate how many will fit with spaces but without space at the end?

Community
  • 1
  • 1
Tomáš Zato
  • 50,171
  • 52
  • 268
  • 778

2 Answers2

2

To simplify, let's make a small example. Say you have 103 pixels, and you want bars 5 pixels wide and spaces of 2 pixels between them. As you say, there is 1 more bar than spaces. You want this last bar to be at the end of your screen, so reduce your width by this amount, that is, 98px.

Then, the rest of the width will be divided by pairs bar-space, each with total length barWidth + spaceWidth. That is, you have 98/7 = 14 of these pairs. In total, you have 15 bars.

So, your formula should be

(canvasWidth - barWidth) / (barWidth + spaceWidth) + 1

where the final +1 is for the last bar.

Hope that fixes it for you.

Alex Pinto
  • 162
  • 1
  • 7
1

Your total width will be:

barWidth(NumberBars) + spaceWidth(NumberBars - 1) = TotalWidth

which expands to:

barWidth(NumberBars) + (spaceWidth)(NumberBars) - spaceWidth = TotalWidth

add spaceWidth to both sides:

barWidth(NumberBars) + spaceWidth(NumberBars) = TotalWidth + spaceWidth

Factor left side:

NumberBars(barWidth + spaceWidth) = TotalWidth + spaceWidth

and divide:

NumberBars = (TotalWidth + spaceWidth) / (barWidth + spaceWidth)
Mark
  • 90,562
  • 7
  • 108
  • 148