1
0
mirror of https://github.com/xuthus83/pigallery2.git synced 2024-11-03 21:04:03 +08:00

Improving icons #587

This commit is contained in:
Patrik J. Braun 2023-08-26 13:45:51 +02:00
parent 4714bafdc5
commit 68a033e47b

View File

@ -119,13 +119,19 @@ export class PublicRouter {
name: Config.Server.applicationTitle, name: Config.Server.applicationTitle,
icons: [ icons: [
{ {
src: 'icon_inv.svg', src: 'icon_auto.svg',
sizes: '48x48 72x72 96x96 128x128 256x256 512x512', sizes: 'any',
type: 'image/svg+xml', type: 'image/svg+xml',
purpose: 'any maskable' purpose: 'any'
}, },
{ {
src: 'icon_inv.png', src: 'icon_padding_auto.svg',
sizes: 'any',
type: 'image/svg+xml',
purpose: 'maskable'
},
{
src: 'icon_white.png',
sizes: '48x48 72x72 96x96 128x128 256x256', sizes: '48x48 72x72 96x96 128x128 256x256',
}, },
], ],
@ -135,44 +141,111 @@ export class PublicRouter {
], ],
start_url: start_url:
Config.Server.publicUrl === '' ? '.' : Config.Server.publicUrl, Config.Server.publicUrl === '' ? '.' : Config.Server.publicUrl,
background_color: '#000000', background_color: '#212529',
theme_color: '#000000', theme_color: '#000000',
}); });
}); });
const getIcon = (theme: 'auto' | string | null = null, paddingPercent = 0): string => {
const vBs = (Config.Server.svgIcon.viewBox || '').split(' ').slice(0, 4).map(s => parseFloat(s));
vBs[0] = vBs[0] || 0;
vBs[1] = vBs[1] || 0;
vBs[2] = vBs[2] || 512;
vBs[3] = vBs[3] || 512;
// make icon rectangle
//add padding to all sides equally. ie: center icon
const icon_size = Math.max(vBs[2], vBs[3]);
const pw = icon_size - vBs[2];
const ph = icon_size - vBs[3];
vBs[0] -= pw / 2;
vBs[1] -= ph / 2;
vBs[2] = icon_size;
vBs[3] = icon_size;
const addPadding = (p: number) => {
if (p <= 0) {
return;
}
const size = Math.max(vBs[2], vBs[3]);
vBs[0] -= size * (p / 2);
vBs[1] -= size * (p / 2);
vBs[2] += size * (p);
vBs[3] += size * (p);
};
const circle_size = icon_size * 1.38;
addPadding(0.38);
addPadding(paddingPercent);
const canvasMid = {
x: vBs[2] / 2 + vBs[0],
y: vBs[3] / 2 + vBs[1],
};
return '<svg ' +
' xmlns="http://www.w3.org/2000/svg"' +
' viewBox="' + vBs.join(' ') + '">' +
(theme === 'auto' ? ('<style>' +
' path, circle {' +
' fill: black;' +
' }' +
' circle.bg {' +
' fill: white;' +
' }' +
' @media (prefers-color-scheme: dark) {' +
' path, circle {' +
' fill: white;' +
' }' +
' circle.bg {' +
' fill: black;' +
' }' +
' }' +
' </style>') :
(theme != null ?
('<style>' +
' path, circle {' +
' fill: ' + theme + ';' +
' }' +
' circle.bg {' +
' fill: black;' +
' }' +
' </style>')
: '<style>' +
' circle.bg {' +
' fill: white;' +
' }' +
' </style>')) +
'<circle class="bg" cy="' + (canvasMid.y) + '" cx="' + (canvasMid.x) + '" r="' + (circle_size / 2) + '"></circle>' +
Config.Server.svgIcon.items + '</svg>';
};
app.get('/icon.svg', (req: Request, res: Response) => { app.get('/icon.svg', (req: Request, res: Response) => {
res.set('Cache-control', 'public, max-age=31536000'); res.set('Cache-control', 'public, max-age=31536000');
res.header('Content-Type', 'image/svg+xml'); res.header('Content-Type', 'image/svg+xml');
res.send('<svg xmlns="http://www.w3.org/2000/svg"' + res.send(getIcon());
' viewBox="' + (Config.Server.svgIcon.viewBox || '0 0 512 512') + '">' + });
Config.Server.svgIcon.items + '</svg>');
app.get('/icon_padding_auto.svg', (req: Request, res: Response) => {
res.set('Cache-control', 'public, max-age=31536000');
res.header('Content-Type', 'image/svg+xml');
// Use 40% padding: https://w3c.github.io/manifest/#icon-masks
res.send(getIcon('auto', 0.4));
}); });
app.get('/icon_auto.svg', (req: Request, res: Response) => { app.get('/icon_auto.svg', (req: Request, res: Response) => {
res.set('Cache-control', 'public, max-age=31536000'); res.set('Cache-control', 'public, max-age=31536000');
res.header('Content-Type', 'image/svg+xml'); res.header('Content-Type', 'image/svg+xml');
res.send('<svg xmlns="http://www.w3.org/2000/svg"' + res.send(getIcon('auto'));
' viewBox="' + (Config.Server.svgIcon.viewBox || '0 0 512 512') + '">' +
'<style>' +
' path, circle {' +
' fill: black;' +
' }' +
' @media (prefers-color-scheme: dark) {' +
' path, circle {' +
' fill: white;' +
' }' +
' }' +
' </style>' +
Config.Server.svgIcon.items + '</svg>');
}); });
app.get('/icon_inv.svg', (req: Request, res: Response) => { app.get('/icon_white.svg', (req: Request, res: Response) => {
res.set('Cache-control', 'public, max-age=31536000'); res.set('Cache-control', 'public, max-age=31536000');
res.header('Content-Type', 'image/svg+xml'); res.header('Content-Type', 'image/svg+xml');
res.send('<svg style="fill:white" width="512" height="512" xmlns="http://www.w3.org/2000/svg"' + res.send(getIcon('white'));
' viewBox="' + (Config.Server.svgIcon.viewBox || '0 0 512 512') + '">' +
Config.Server.svgIcon.items + '</svg>');
}); });
@ -189,7 +262,7 @@ export class PublicRouter {
} }
}); });
app.get('/icon_inv.png', async (req: Request, res: Response, next: NextFunction) => { app.get('/icon_white.png', async (req: Request, res: Response, next: NextFunction) => {
try { try {
const p = path.join(ProjectPath.TempFolder, '/icon_inv.png'); const p = path.join(ProjectPath.TempFolder, '/icon_inv.png');
await PhotoProcessing.renderSVG(Config.Server.svgIcon, p, 'white'); await PhotoProcessing.renderSVG(Config.Server.svgIcon, p, 'white');