Skip to content

Commit

Permalink
Reduce GC on measureText
Browse files Browse the repository at this point in the history
  • Loading branch information
cmdcolin committed Jul 12, 2022
1 parent db7cb60 commit 7ea0e45
Show file tree
Hide file tree
Showing 3 changed files with 18 additions and 94 deletions.
13 changes: 6 additions & 7 deletions packages/core/util/Base1DUtils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -71,8 +71,9 @@ export function pxToBp(self: any, px: number) {
offsetPx,
displayedRegions,
interRegionPaddingWidth,
staticBlocks: { blocks },
staticBlocks,
} = self
const blocks = staticBlocks.contentBlocks
const bp = (offsetPx + px) * bpPerPx
if (bp < 0) {
const region = displayedRegions[0]
Expand All @@ -90,8 +91,7 @@ export function pxToBp(self: any, px: number) {
}

const interRegionPaddingBp = interRegionPaddingWidth * bpPerPx
let firstBlock = true
let currStaticBlock = blocks[0]?.regionNumber
let currBlock = 0
for (let i = 0; i < displayedRegions.length; i++) {
const region = displayedRegions[i]
const len = region.end - region.start
Expand All @@ -112,10 +112,9 @@ export function pxToBp(self: any, px: number) {

// add the interRegionPaddingWidth if the boundary is in the screen e.g. in
// a static block
if (currStaticBlock === i) {
bpSoFar += len + (firstBlock ? 0 : interRegionPaddingBp)
currStaticBlock++
firstBlock = false
if (blocks[currBlock]?.regionNumber === i) {
bpSoFar += len + interRegionPaddingBp
currBlock++
} else {
bpSoFar += len
}
Expand Down
79 changes: 2 additions & 77 deletions packages/core/util/Base1DViewModel.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { types, cast, getSnapshot, Instance } from 'mobx-state-tree'
import { types, cast, Instance } from 'mobx-state-tree'
import { clamp } from './index'
import { Feature } from './simpleFeature'
import { Region, ElementId } from './types/mst'
Expand Down Expand Up @@ -63,82 +63,7 @@ const Base1DView = types
},

pxToBp(px: number) {
let bpSoFar = 0
const bp = (self.offsetPx + px) * self.bpPerPx
const n = self.displayedRegions.length
if (bp < 0) {
const region = self.displayedRegions[0]
const offset = bp
const snap = getSnapshot(region)
return {
...(snap as Omit<typeof snap, symbol>),
oob: true,
coord: region.reversed
? Math.floor(region.end - offset) + 1
: Math.floor(region.start + offset) + 1,
offset,
index: 0,
}
}

const interRegionPaddingBp = self.interRegionPaddingWidth * self.bpPerPx
const minimumBlockBp = self.minimumBlockWidth * self.bpPerPx

for (let index = 0; index < self.displayedRegions.length; index += 1) {
const region = self.displayedRegions[index]
const len = region.end - region.start
const offset = bp - bpSoFar
if (len + bpSoFar > bp && bpSoFar <= bp) {
const snap = getSnapshot(region)
return {
...(snap as Omit<typeof snap, symbol>),
oob: false,
offset,
coord: region.reversed
? Math.floor(region.end - offset) + 1
: Math.floor(region.start + offset) + 1,
index,
}
}

// add the interRegionPaddingWidth if the boundary is in the screen
// e.g. offset>0 && offset<width
if (
region.end - region.start > minimumBlockBp &&
offset / self.bpPerPx > 0 &&
offset / self.bpPerPx < this.width
) {
bpSoFar += len + interRegionPaddingBp
} else {
bpSoFar += len
}
}

if (bp >= bpSoFar) {
const region = self.displayedRegions[n - 1]
const len = region.end - region.start
const offset = bp - bpSoFar + len
const snap = getSnapshot(region)
return {
...(snap as Omit<typeof snap, symbol>),
oob: true,
offset,
coord: region.reversed
? Math.floor(region.end - offset) + 1
: Math.floor(region.start + offset) + 1,
index: n - 1,
}
}
return {
coord: 0,
index: 0,
start: 0,
refName: '',
oob: true,
assemblyName: '',
offset: 0,
reversed: false,
}
return pxToBp(self, px)
},
}))
.views(self => ({
Expand Down
20 changes: 10 additions & 10 deletions packages/core/util/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -883,19 +883,19 @@ export const rIC =
: (cb: Function) => setTimeout(() => cb(), 1)
: (cb: Function) => cb()

// prettier-ignore
const widths = [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0.2796875,0.2765625,0.3546875,0.5546875,0.5546875,0.8890625,0.665625,0.190625,0.3328125,0.3328125,0.3890625,0.5828125,0.2765625,0.3328125,0.2765625,0.3015625,0.5546875,0.5546875,0.5546875,0.5546875,0.5546875,0.5546875,0.5546875,0.5546875,0.5546875,0.5546875,0.2765625,0.2765625,0.584375,0.5828125,0.584375,0.5546875,1.0140625,0.665625,0.665625,0.721875,0.721875,0.665625,0.609375,0.7765625,0.721875,0.2765625,0.5,0.665625,0.5546875,0.8328125,0.721875,0.7765625,0.665625,0.7765625,0.721875,0.665625,0.609375,0.721875,0.665625,0.94375,0.665625,0.665625,0.609375,0.2765625,0.3546875,0.2765625,0.4765625,0.5546875,0.3328125,0.5546875,0.5546875,0.5,0.5546875,0.5546875,0.2765625,0.5546875,0.5546875,0.221875,0.240625,0.5,0.221875,0.8328125,0.5546875,0.5546875,0.5546875,0.5546875,0.3328125,0.5,0.2765625,0.5546875,0.5,0.721875,0.5,0.5,0.5,0.3546875,0.259375,0.353125,0.5890625]

// xref https://gist.github.com/tophtucker/62f93a4658387bb61e4510c37e2e97cf
export function measureText(str: unknown, fontSize = 10) {
// prettier-ignore
const widths = [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0.2796875,0.2765625,0.3546875,0.5546875,0.5546875,0.8890625,0.665625,0.190625,0.3328125,0.3328125,0.3890625,0.5828125,0.2765625,0.3328125,0.2765625,0.3015625,0.5546875,0.5546875,0.5546875,0.5546875,0.5546875,0.5546875,0.5546875,0.5546875,0.5546875,0.5546875,0.2765625,0.2765625,0.584375,0.5828125,0.584375,0.5546875,1.0140625,0.665625,0.665625,0.721875,0.721875,0.665625,0.609375,0.7765625,0.721875,0.2765625,0.5,0.665625,0.5546875,0.8328125,0.721875,0.7765625,0.665625,0.7765625,0.721875,0.665625,0.609375,0.721875,0.665625,0.94375,0.665625,0.665625,0.609375,0.2765625,0.3546875,0.2765625,0.4765625,0.5546875,0.3328125,0.5546875,0.5546875,0.5,0.5546875,0.5546875,0.2765625,0.5546875,0.5546875,0.221875,0.240625,0.5,0.221875,0.8328125,0.5546875,0.5546875,0.5546875,0.5546875,0.3328125,0.5,0.2765625,0.5546875,0.5,0.721875,0.5,0.5,0.5,0.3546875,0.259375,0.353125,0.5890625]
const avg = 0.5279276315789471
return (
String(str)
.split('')
.map(c =>
c.charCodeAt(0) < widths.length ? widths[c.charCodeAt(0)] : avg,
)
.reduce((cur, acc) => acc + cur, 0) * fontSize
)
const s = String(str)
let total = 0
for (let i = 0; i < s.length; i++) {
const code = s.charCodeAt(i)
total += widths[code] ?? avg
}
return total * fontSize
}

export const defaultStarts = ['ATG']
Expand Down

0 comments on commit 7ea0e45

Please sign in to comment.