Skip to content

Commit 6f511fa

Browse files
committed
Use one buffer only.
1 parent 28f791e commit 6f511fa

1 file changed

Lines changed: 64 additions & 46 deletions

File tree

src/components/shared/thread/ActivityGraphFills.tsx

Lines changed: 64 additions & 46 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,10 @@ import type {
1313
DevicePixels,
1414
CssPixels,
1515
} from 'firefox-profiler/types';
16-
import { SAMPLE_RELATION_TO_SELECTED_STATE_MASK, SelectedState } from 'firefox-profiler/types';
16+
import {
17+
SAMPLE_RELATION_TO_SELECTED_STATE_MASK,
18+
SelectedState,
19+
} from 'firefox-profiler/types';
1720
import type { HoveredPixelState } from './ActivityGraph';
1821

1922
/**
@@ -88,10 +91,6 @@ export type CategoryDrawStyles = ReadonlyArray<{
8891
readonly filteredOutByTransformFillStyle: CanvasPattern | string;
8992
}>;
9093

91-
// These Float32Arrays are mutated in place during the computation step.
92-
// buffers[selectedState] is the buffer for the given SelectedState enum value.
93-
type SelectedPercentageAtPixelBuffers = Int32Array<ArrayBuffer>[];
94-
9594
export type CpuRatioInTimeRange = {
9695
readonly cpuRatio: number;
9796
readonly timeRange: Milliseconds;
@@ -146,7 +145,7 @@ export function precomputePositions(
146145
sampleIndexOffset > 0
147146
? fullThreadSampleTimes[sampleIndexOffset - 1]
148147
: fullThreadSampleTimes[0] - interval;
149-
// Go through the samples and accumulate the category into the percentageBuffers.
148+
// Go through the samples and accumulate the category into the percentageBuffer.
150149
for (let i = 0; i < sampleCount; i++) {
151150
const sampleTime = fullThreadSampleTimes[sampleIndexOffset + i];
152151
samplePositions[i] =
@@ -178,16 +177,16 @@ export function precomputePositions(
178177
export function computeActivityGraphFills(
179178
renderedComponentSettings: RenderedComponentSettings
180179
) {
181-
const mutablePercentageBuffers = _createSelectedPercentageAtPixelBuffers(
180+
const mutablePercentageBuffer = _createSelectedPercentageAtPixelBuffers(
182181
renderedComponentSettings
183182
);
184183
const mutableFills = _getCategoryFills(
185184
renderedComponentSettings.categoryDrawStyles,
186-
mutablePercentageBuffers
185+
mutablePercentageBuffer
187186
);
188187
const activityGraphFills = new ActivityGraphFillComputer(
189188
renderedComponentSettings,
190-
mutablePercentageBuffers,
189+
mutablePercentageBuffer,
191190
mutableFills
192191
);
193192

@@ -213,16 +212,16 @@ export function computeActivityGraphFills(
213212
export class ActivityGraphFillComputer {
214213
readonly renderedComponentSettings: RenderedComponentSettings;
215214
// The fills and percentages are mutated in place.
216-
readonly mutablePercentageBuffers: SelectedPercentageAtPixelBuffers[];
215+
readonly mutablePercentageBuffer: Int32Array;
217216
readonly mutableFills: CategoryFill[];
218217

219218
constructor(
220219
renderedComponentSettings: RenderedComponentSettings,
221-
mutablePercentageBuffers: SelectedPercentageAtPixelBuffers[],
220+
mutablePercentageBuffer: Int32Array,
222221
mutableFills: CategoryFill[]
223222
) {
224223
this.renderedComponentSettings = renderedComponentSettings;
225-
this.mutablePercentageBuffers = mutablePercentageBuffers;
224+
this.mutablePercentageBuffer = mutablePercentageBuffer;
226225
this.mutableFills = mutableFills;
227226
}
228227

@@ -293,18 +292,20 @@ export class ActivityGraphFillComputer {
293292
* with these methods.
294293
*/
295294
_accumulateSampleCategories() {
295+
const { mutablePercentageBuffer: buffer, renderedComponentSettings } = this;
296296
const {
297+
canvasPixelWidth,
297298
rangeFilteredThread: { samples },
298299
sampleSelectedStates,
299300
precomputedPositions,
300-
} = this.renderedComponentSettings;
301+
} = renderedComponentSettings;
301302

302303
if (samples.length === 0) {
303304
// If we have no samples, there's nothing to do.
304305
return;
305306
}
306307

307-
// Go through the samples and accumulate the category into the percentageBuffers.)
308+
// Go through the samples and accumulate the category into the buffer.
308309
const { samplePositions, halfwayPositions } = precomputedPositions;
309310
const { threadCPUPercent } = samples;
310311
let beforeSampleCpuPercent = threadCPUPercent[0];
@@ -316,10 +317,10 @@ export class ActivityGraphFillComputer {
316317
const afterSampleCpuPercent = threadCPUPercent[i + 1];
317318
const category = samples.category[i];
318319

319-
const percentageBuffers = this.mutablePercentageBuffers[category];
320320
const bufferIndex =
321321
sampleSelectedStates[i] & SAMPLE_RELATION_TO_SELECTED_STATE_MASK;
322-
const percentageBuffer = percentageBuffers[bufferIndex];
322+
const bufferRow = category * SELECTED_STATE_BUFFER_COUNT + bufferIndex;
323+
const baseIndex = bufferRow * canvasPixelWidth;
323324
const samplePosition = samplePositions[i];
324325

325326
// Samples have two parts to be able to present the different CPU usages properly.
@@ -362,21 +363,21 @@ export class ActivityGraphFillComputer {
362363
const intEndPos = endPos >> FIXED_POINT_BITS;
363364

364365
if (intStartPos === intEndPos) {
365-
percentageBuffer[intStartPos] += cpuPercent * (endPos - startPos);
366+
buffer[baseIndex + intStartPos] += cpuPercent * (endPos - startPos);
366367
} else {
367368
if (intStartPos + 1 < intEndPos) {
368-
percentageBuffer.fill(
369+
buffer.fill(
369370
cpuPercent << FIXED_POINT_BITS,
370-
intStartPos + 1,
371-
intEndPos
371+
baseIndex + intStartPos + 1,
372+
baseIndex + intEndPos
372373
);
373374
}
374375

375376
const startPosFrac = startPos & FIXED_POINT_MASK;
376-
percentageBuffer[intStartPos] +=
377+
buffer[baseIndex + intStartPos] +=
377378
cpuPercent * ((1 << FIXED_POINT_BITS) - startPosFrac);
378379
const endPosFrac = endPos & FIXED_POINT_MASK;
379-
percentageBuffer[intEndPos] += cpuPercent * endPosFrac;
380+
buffer[baseIndex + intEndPos] += cpuPercent * endPosFrac;
380381
}
381382
}
382383

@@ -389,21 +390,21 @@ export class ActivityGraphFillComputer {
389390
const intEndPos = endPos >> FIXED_POINT_BITS;
390391

391392
if (intStartPos === intEndPos) {
392-
percentageBuffer[intStartPos] += cpuPercent * (endPos - startPos);
393+
buffer[baseIndex + intStartPos] += cpuPercent * (endPos - startPos);
393394
} else {
394395
if (intStartPos + 1 < intEndPos) {
395-
percentageBuffer.fill(
396+
buffer.fill(
396397
cpuPercent << FIXED_POINT_BITS,
397-
intStartPos + 1,
398-
intEndPos
398+
baseIndex + intStartPos + 1,
399+
baseIndex + intEndPos
399400
);
400401
}
401402

402403
const startPosFrac = startPos & FIXED_POINT_MASK;
403-
percentageBuffer[intStartPos] +=
404+
buffer[baseIndex + intStartPos] +=
404405
cpuPercent * ((1 << FIXED_POINT_BITS) - startPosFrac);
405406
const endPosFrac = endPos & FIXED_POINT_MASK;
406-
percentageBuffer[intEndPos] += cpuPercent * endPosFrac;
407+
buffer[baseIndex + intEndPos] += cpuPercent * endPosFrac;
407408
}
408409
}
409410

@@ -765,14 +766,9 @@ function _createSelectedPercentageAtPixelBuffers({
765766
}: {
766767
categoryDrawStyles: CategoryDrawStyles;
767768
canvasPixelWidth: number;
768-
}): SelectedPercentageAtPixelBuffers[] {
769-
return categoryDrawStyles.map(() => {
770-
const percentageBuffers = [];
771-
for (let i = 0; i <= SELECTED_STATE_BUFFER_COUNT; i++) {
772-
percentageBuffers[i] = new Int32Array(canvasPixelWidth);
773-
}
774-
return percentageBuffers;
775-
});
769+
}): Int32Array<ArrayBuffer> {
770+
const rowCount = categoryDrawStyles.length * SELECTED_STATE_BUFFER_COUNT;
771+
return new Int32Array(canvasPixelWidth * rowCount);
776772
}
777773

778774
/**
@@ -786,47 +782,69 @@ function _createSelectedPercentageAtPixelBuffers({
786782
*/
787783
function _getCategoryFills(
788784
categoryDrawStyles: CategoryDrawStyles,
789-
percentageBuffers: SelectedPercentageAtPixelBuffers[]
785+
percentageBuffer: Int32Array<ArrayBuffer>
790786
): CategoryFill[] {
787+
const canvasPixelWidth =
788+
percentageBuffer.length /
789+
categoryDrawStyles.length /
790+
SELECTED_STATE_BUFFER_COUNT;
791+
791792
// Sort all of the categories by their gravity.
792793
const categoryIndexesByGravity = categoryDrawStyles
793794
.map((_, i) => i)
794795
.sort(
795796
(a, b) => categoryDrawStyles[b].gravity - categoryDrawStyles[a].gravity
796797
);
797798

799+
function bufferForCategoryAndSelectedState(
800+
category: IndexIntoCategoryList,
801+
selectedState: SelectedState
802+
): Int32Array<ArrayBuffer> {
803+
const rowIndex = category * SELECTED_STATE_BUFFER_COUNT + selectedState;
804+
const sliceStart = rowIndex * canvasPixelWidth;
805+
const sliceEnd = sliceStart + canvasPixelWidth;
806+
return percentageBuffer.subarray(sliceStart, sliceEnd);
807+
}
808+
798809
const nestedFills: CategoryFill[][] = categoryIndexesByGravity.map(
799810
(categoryIndex) => {
800811
const categoryDrawStyle = categoryDrawStyles[categoryIndex];
801-
const buffer = percentageBuffers[categoryIndex];
802-
const canvasPixelWidth =
803-
buffer[SelectedState.UnselectedOrderedBeforeSelected].length;
804812
// For every category we draw four fills, for the four selection kinds:
805813
return [
806814
{
807815
category: categoryDrawStyle.category,
808816
fillStyle: categoryDrawStyle.getUnselectedFillStyle(),
809-
perPixelContribution:
810-
buffer[SelectedState.UnselectedOrderedBeforeSelected],
817+
perPixelContribution: bufferForCategoryAndSelectedState(
818+
categoryIndex,
819+
SelectedState.UnselectedOrderedBeforeSelected
820+
),
811821
accumulatedUpperEdge: new Float32Array(canvasPixelWidth),
812822
},
813823
{
814824
category: categoryDrawStyle.category,
815825
fillStyle: categoryDrawStyle.getSelectedFillStyle(),
816-
perPixelContribution: buffer[SelectedState.Selected],
826+
perPixelContribution: bufferForCategoryAndSelectedState(
827+
categoryIndex,
828+
SelectedState.Selected
829+
),
817830
accumulatedUpperEdge: new Float32Array(canvasPixelWidth),
818831
},
819832
{
820833
category: categoryDrawStyle.category,
821834
fillStyle: categoryDrawStyle.getUnselectedFillStyle(),
822-
perPixelContribution:
823-
buffer[SelectedState.UnselectedOrderedAfterSelected],
835+
perPixelContribution: bufferForCategoryAndSelectedState(
836+
categoryIndex,
837+
SelectedState.UnselectedOrderedAfterSelected
838+
),
824839
accumulatedUpperEdge: new Float32Array(canvasPixelWidth),
825840
},
826841
{
827842
category: categoryDrawStyle.category,
828843
fillStyle: categoryDrawStyle.filteredOutByTransformFillStyle,
829-
perPixelContribution: buffer[SelectedState.FilteredOutByTransform],
844+
perPixelContribution: bufferForCategoryAndSelectedState(
845+
categoryIndex,
846+
SelectedState.FilteredOutByTransform
847+
),
830848
accumulatedUpperEdge: new Float32Array(canvasPixelWidth),
831849
},
832850
];

0 commit comments

Comments
 (0)