Skip to content

Commit

Permalink
feat(logos): support auto-sizing mode
Browse files Browse the repository at this point in the history
  • Loading branch information
LitoMore committed Jun 19, 2023
1 parent 6f78e6f commit d544d98
Show file tree
Hide file tree
Showing 13 changed files with 220 additions and 18 deletions.
5 changes: 5 additions & 0 deletions badge-maker/lib/constants.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
const DEFAULT_LOGO_HEIGHT = 14

module.exports = {
DEFAULT_LOGO_HEIGHT,
}
5 changes: 4 additions & 1 deletion badge-maker/lib/make-badge.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
const { normalizeColor, toSvgColor } = require('./color')
const badgeRenderers = require('./badge-renderers')
const { stripXmlWhitespace } = require('./xml')
const { DEFAULT_LOGO_HEIGHT } = require('./constants')

/*
note: makeBadge() is fairly thinly wrapped so if we are making changes here
Expand All @@ -17,6 +18,7 @@ module.exports = function makeBadge({
labelColor,
logo,
logoPosition,
logoSize,
logoWidth,
links = ['', ''],
}) {
Expand Down Expand Up @@ -45,7 +47,7 @@ module.exports = function makeBadge({
throw new Error(`Unknown badge style: '${style}'`)
}

logoWidth = +logoWidth || (logo ? 14 : 0)
logoWidth = +logoWidth || (logo ? DEFAULT_LOGO_HEIGHT : 0)

return stripXmlWhitespace(
render({
Expand All @@ -55,6 +57,7 @@ module.exports = function makeBadge({
logo,
logoPosition,
logoWidth,
logoSize,
logoPadding: logo && label.length ? 3 : 0,
color: toSvgColor(color),
labelColor: toSvgColor(labelColor),
Expand Down
1 change: 1 addition & 0 deletions core/base-service/base.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -373,6 +373,7 @@ describe('BaseService', function () {
namedLogo: undefined,
logo: undefined,
logoWidth: undefined,
logoSize: undefined,
logoPosition: undefined,
links: [],
labelColor: undefined,
Expand Down
25 changes: 23 additions & 2 deletions core/base-service/coalesce-badge.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,8 @@ import {
decodeDataUrlFromQueryParam,
prepareNamedLogo,
} from '../../lib/logos.js'
import { svg2base64 } from '../../lib/svg-helpers.js'
import { svg2base64, getIconSize } from '../../lib/svg-helpers.js'
import { DEFAULT_LOGO_HEIGHT } from '../../badge-maker/lib/constants.js'
import coalesce from './coalesce.js'
import toArray from './to-array.js'

Expand Down Expand Up @@ -55,7 +56,9 @@ export default function coalesceBadge(
} = overrides
let {
logoWidth: overrideLogoWidth,
logoHeight: overrideLogoHeight,
logoPosition: overrideLogoPosition,
logoSize: overrideLogoSize,
color: overrideColor,
labelColor: overrideLabelColor,
} = overrides
Expand All @@ -76,6 +79,7 @@ export default function coalesceBadge(
overrideLabelColor = `${overrideLabelColor}`
}
overrideLogoWidth = +overrideLogoWidth || undefined
overrideLogoHeight = +overrideLogoHeight || undefined
overrideLogoPosition = +overrideLogoPosition || undefined

const {
Expand All @@ -88,6 +92,7 @@ export default function coalesceBadge(
namedLogo: serviceNamedLogo,
logoColor: serviceLogoColor,
logoWidth: serviceLogoWidth,
logoHeight: serviceLogoHeight,
logoPosition: serviceLogoPosition,
link: serviceLink,
cacheSeconds: serviceCacheSeconds,
Expand Down Expand Up @@ -119,7 +124,12 @@ export default function coalesceBadge(
style = 'flat'
}

let namedLogo, namedLogoColor, logoWidth, logoPosition, logoSvgBase64
let namedLogo,
namedLogoColor,
logoWidth,
logoHeight,
logoPosition,
logoSvgBase64
if (overrideLogo) {
// `?logo=` could be a named logo or encoded svg.
const overrideLogoSvgBase64 = decodeDataUrlFromQueryParam(overrideLogo)
Expand All @@ -134,6 +144,7 @@ export default function coalesceBadge(
// If the logo has been overridden it does not make sense to inherit the
// original width or position.
logoWidth = overrideLogoWidth
logoHeight = overrideLogoHeight
logoPosition = overrideLogoPosition
} else {
if (serviceLogoSvg) {
Expand All @@ -146,12 +157,21 @@ export default function coalesceBadge(
namedLogoColor = coalesce(overrideLogoColor, serviceLogoColor)
}
logoWidth = coalesce(overrideLogoWidth, serviceLogoWidth)
logoHeight = coalesce(overrideLogoHeight, serviceLogoHeight)
logoPosition = coalesce(overrideLogoPosition, serviceLogoPosition)
}
if (namedLogo) {
const iconSize = getIconSize(String(namedLogo).toLowerCase())

if (!logoWidth && iconSize && overrideLogoSize === 'auto') {
logoWidth =
(iconSize.width / iconSize.height) * (logoHeight || DEFAULT_LOGO_HEIGHT)
}

logoSvgBase64 = prepareNamedLogo({
name: namedLogo,
color: namedLogoColor,
size: overrideLogoSize,
style,
})
}
Expand Down Expand Up @@ -179,6 +199,7 @@ export default function coalesceBadge(
logo: logoSvgBase64,
logoWidth,
logoPosition,
logoSize: overrideLogoSize,
links: toArray(overrideLink || serviceLink),
cacheLengthSeconds: coalesce(serviceCacheSeconds, defaultCacheSeconds),
}
Expand Down
34 changes: 34 additions & 0 deletions core/base-service/openapi.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,9 @@ const globalParamRefs = [
{ $ref: '#/components/parameters/style' },
{ $ref: '#/components/parameters/logo' },
{ $ref: '#/components/parameters/logoColor' },
{ $ref: '#/components/parameters/logoSize' },
{ $ref: '#/components/parameters/logoWidth' },
{ $ref: '#/components/parameters/logoHeight' },
{ $ref: '#/components/parameters/label' },
{ $ref: '#/components/parameters/labelColor' },
{ $ref: '#/components/parameters/color' },
Expand Down Expand Up @@ -264,6 +267,37 @@ function category2openapi(category, services) {
},
example: 'violet',
},
logoSize: {
name: 'logoSize',
in: 'query',
required: false,
description:
"Make icons adaptively resize by setting `auto`. It's useful for some wider logos like `amd` and `amg`.",
schema: {
type: 'string',
},
example: 'auto',
},
logoWidth: {
name: 'logoWidth',
in: 'query',
required: false,
description: 'The width of the logo, default to `14`',
schema: {
type: 'string',
},
example: '20',
},
logoHeight: {
name: 'logoHeight',
in: 'query',
required: false,
description: 'The height of the logo, default to `14`',
schema: {
type: 'string',
},
example: '12',
},
label: {
name: 'label',
in: 'query',
Expand Down
43 changes: 43 additions & 0 deletions core/base-service/openapi.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -105,6 +105,37 @@ const expected = {
schema: { type: 'string' },
example: 'violet',
},
logoSize: {
name: 'logoSize',
in: 'query',
required: false,
description:
"Make icons adaptively resize by setting `auto`. It's useful for some wider logos like `amd` and `amg`.",
schema: {
type: 'string',
},
example: 'auto',
},
logoWidth: {
name: 'logoWidth',
in: 'query',
required: false,
description: 'The width of the logo, default to `14`',
schema: {
type: 'string',
},
example: '20',
},
logoHeight: {
name: 'logoHeight',
in: 'query',
required: false,
description: 'The height of the logo, default to `14`',
schema: {
type: 'string',
},
example: '12',
},
label: {
name: 'label',
in: 'query',
Expand Down Expand Up @@ -170,6 +201,9 @@ const expected = {
{ $ref: '#/components/parameters/style' },
{ $ref: '#/components/parameters/logo' },
{ $ref: '#/components/parameters/logoColor' },
{ $ref: '#/components/parameters/logoSize' },
{ $ref: '#/components/parameters/logoWidth' },
{ $ref: '#/components/parameters/logoHeight' },
{ $ref: '#/components/parameters/label' },
{ $ref: '#/components/parameters/labelColor' },
{ $ref: '#/components/parameters/color' },
Expand Down Expand Up @@ -225,6 +259,9 @@ const expected = {
{ $ref: '#/components/parameters/style' },
{ $ref: '#/components/parameters/logo' },
{ $ref: '#/components/parameters/logoColor' },
{ $ref: '#/components/parameters/logoSize' },
{ $ref: '#/components/parameters/logoWidth' },
{ $ref: '#/components/parameters/logoHeight' },
{ $ref: '#/components/parameters/label' },
{ $ref: '#/components/parameters/labelColor' },
{ $ref: '#/components/parameters/color' },
Expand Down Expand Up @@ -279,6 +316,9 @@ const expected = {
{ $ref: '#/components/parameters/style' },
{ $ref: '#/components/parameters/logo' },
{ $ref: '#/components/parameters/logoColor' },
{ $ref: '#/components/parameters/logoSize' },
{ $ref: '#/components/parameters/logoWidth' },
{ $ref: '#/components/parameters/logoHeight' },
{ $ref: '#/components/parameters/label' },
{ $ref: '#/components/parameters/labelColor' },
{ $ref: '#/components/parameters/color' },
Expand Down Expand Up @@ -325,6 +365,9 @@ const expected = {
{ $ref: '#/components/parameters/style' },
{ $ref: '#/components/parameters/logo' },
{ $ref: '#/components/parameters/logoColor' },
{ $ref: '#/components/parameters/logoSize' },
{ $ref: '#/components/parameters/logoWidth' },
{ $ref: '#/components/parameters/logoHeight' },
{ $ref: '#/components/parameters/label' },
{ $ref: '#/components/parameters/labelColor' },
{ $ref: '#/components/parameters/color' },
Expand Down
9 changes: 4 additions & 5 deletions lib/load-simple-icons.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
import * as originalSimpleIcons from 'simple-icons/icons'
import { svg2base64 } from './svg-helpers.js'

function loadSimpleIcons() {
const simpleIcons = {}
Expand All @@ -16,10 +15,10 @@ function loadSimpleIcons() {
const icon = originalSimpleIcons[key]
const { title, slug, hex } = icon

icon.base64 = {
default: svg2base64(icon.svg.replace('<svg', `<svg fill="#${hex}"`)),
light: svg2base64(icon.svg.replace('<svg', '<svg fill="whitesmoke"')),
dark: svg2base64(icon.svg.replace('<svg', '<svg fill="#333"')),
icon.styles = {
default: icon.svg.replace('<svg', `<svg fill="#${hex}"`),
light: icon.svg.replace('<svg', '<svg fill="whitesmoke"'),
dark: icon.svg.replace('<svg', '<svg fill="#333"'),
}

// There are a few instances where multiple icons have the same title
Expand Down
2 changes: 1 addition & 1 deletion lib/load-simple-icons.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ describe('loadSimpleIcons', function () {
})

it('prepares three color themes', function () {
expect(simpleIcons.sentry.base64).to.have.all.keys(
expect(simpleIcons.sentry.styles).to.have.all.keys(
'default',
'light',
'dark'
Expand Down
31 changes: 23 additions & 8 deletions lib/logos.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ import {
normalizeColor,
} from '../badge-maker/lib/color.js'
import coalesce from '../core/base-service/coalesce.js'
import { svg2base64 } from './svg-helpers.js'
import { svg2base64, getIconSize, resetIconPosition } from './svg-helpers.js'
import loadLogos from './load-logos.js'
import loadSimpleIcons from './load-simple-icons.js'
const logos = loadLogos()
Expand Down Expand Up @@ -88,25 +88,38 @@ function getSimpleIconStyle({ icon, style }) {
return 'default'
}

function getSimpleIcon({ name, color, style }) {
function getSimpleIcon({ name, color, style, size = 'contain' }) {
const key = name === 'travis' ? 'travis-ci' : name.replace(/ /g, '-')

if (!(key in simpleIcons)) {
return undefined
}

let iconSvg

const svgColor = toSvgColor(color)
if (svgColor) {
return svg2base64(
simpleIcons[key].svg.replace('<svg', `<svg fill="${svgColor}"`)
)
iconSvg = simpleIcons[key].svg.replace('<svg', `<svg fill="${svgColor}"`)
} else {
const iconStyle = getSimpleIconStyle({ icon: simpleIcons[key], style })
return simpleIcons[key].base64[iconStyle]
iconSvg = simpleIcons[key].styles[iconStyle]
}

if (size === 'auto') {
const { width: iconWidth, height: iconHeight } = getIconSize(key)

if (iconWidth > iconHeight) {
const path = resetIconPosition(simpleIcons[key].path)
iconSvg = iconSvg
.replace('viewBox="0 0 24 24"', `viewBox="0 0 24 ${iconHeight}"`)
.replace(/<path d=".*"\/>/, `<path d="${path}"/>`)
}
}

return svg2base64(iconSvg)
}

function prepareNamedLogo({ name, color, style }) {
function prepareNamedLogo({ name, color, style, size }) {
if (typeof name !== 'string') {
return undefined
}
Expand All @@ -118,7 +131,8 @@ function prepareNamedLogo({ name, color, style }) {
}

return (
getShieldsIcon({ name, color }) || getSimpleIcon({ name, color, style })
getShieldsIcon({ name, color }) ||
getSimpleIcon({ name, color, style, size })
)
}

Expand All @@ -131,6 +145,7 @@ function makeLogo(defaultNamedLogo, overrides) {
name: coalesce(overrides.logo, defaultNamedLogo),
color: overrides.logoColor,
style: overrides.style,
size: overrides.logoSize,
})
}
}
Expand Down
Loading

0 comments on commit d544d98

Please sign in to comment.