playwright/utils/generate_chromium_default_font_families.js
Dmitry Gozman ba0cfaeb2d
fix(chromium): work around about:blank issue on Chromium (#14068)
fix(chromium): work around about:blank issue on Chromium

We don't receive the `loaderId` which translates to `newDocumentId`,
so we expect the same-document navigation. Instead, we can wait
for any new-document navigation as a workaround, only for `about:blank`.

This also reverts commit f0f65fa247.
2022-05-10 20:32:19 +01:00

117 lines
4.4 KiB
JavaScript

/**
* Copyright (c) Microsoft Corporation.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
// @ts-check
const xml2js = require('xml2js');
const fs = require('fs');
const path = require('path');
const { argv } = require('process');
// From https://source.chromium.org/chromium/chromium/src/+/main:chrome/browser/ui/prefs/prefs_tab_helper.cc;l=130;drc=62b77bef90de54f0136b51935fa2d5814a1b4da9
// and https://source.chromium.org/chromium/chromium/src/+/main:third_party/blink/renderer/platform/text/locale_to_script_mapping.cc;l=44;drc=befcb6de95fb8c88c162ce1f64111f6c17351b13
// note that some suffixes like _JAPANESE, _KOREAN don't have matching icu codes.
const codeToScriptName = new Map([
['ARABIC', 'arab'],
['CYRILLIC', 'cyrl'],
['GREEK', 'grek'],
['JAPANESE', 'jpan'],
['KOREAN', 'hang'],
['SIMPLIFIED_HAN', 'hans'],
['TRADITIONAL_HAN', 'hant'],
]);
const idToProtocol = new Map([
['IDS_STANDARD_FONT_FAMILY', 'standard'],
['IDS_SANS_SERIF_FONT_FAMILY','sansSerif'],
['IDS_SERIF_FONT_FAMILY', 'serif'],
['IDS_CURSIVE_FONT_FAMILY', 'cursive'],
['IDS_FANTASY_FONT_FAMILY', 'fantasy'],
['IDS_FIXED_FONT_FAMILY', 'fixed'],
]);
class ScriptFontFamilies {
scriptToFontFamilies = new Map();
setFont(scriptName, familyName, value) {
let fontFamilies = this.scriptToFontFamilies.get(scriptName);
if (!fontFamilies) {
fontFamilies = {};
this.scriptToFontFamilies.set(scriptName, fontFamilies);
}
fontFamilies[familyName] = value;
}
toJSON() {
const forScripts = Array.from(this.scriptToFontFamilies.entries()).filter(([name, _]) => !!name).map(([script, fontFamilies]) => ({ script, fontFamilies }));
return {
fontFamilies: this.scriptToFontFamilies.get(''),
forScripts: forScripts.length ? forScripts : undefined
};
}
}
if (argv.length < 3)
throw new Error('Expected path to "chromium/src" checkout as first argument')
// Upstream files location is https://chromium.googlesource.com/chromium/src/+/main/chrome/app/resources/locale_settings_linux.grd
const resourceDir = path.join(argv[2], 'chrome/app/resources/');
if (!fs.existsSync(resourceDir))
throw new Error(`Path ${resourceDir} does not exist`);
function parseXML(xml) {
let result;
xml2js.parseString(xml, {trim: true}, (err, r) => result = r);
return result;
}
const result = {};
for (const platform of ['linux', 'mac', 'win']) {
const f = path.join(resourceDir, `locale_settings_${platform}.grd`);
const xmlDataStr = fs.readFileSync(f);
let jsonObj = parseXML(xmlDataStr);
if (!jsonObj)
throw new Error('Failed to parse ' + f);
const fontFamilies = new ScriptFontFamilies();
const defaults = jsonObj.grit.release[0].messages[0].message;
defaults.forEach(e => {
const name = e['$']['name'];
let scriptName = '';
let familyName;
for (const id of idToProtocol.keys()) {
if (!name.startsWith(id))
continue;
familyName = idToProtocol.get(id);
if (name !== id) {
const suffix = name.substring(id.length + 1);
// We don't support this, see https://source.chromium.org/chromium/chromium/src/+/main:chrome/browser/ui/prefs/prefs_tab_helper.cc;l=384-390;drc=62b77bef90de54f0136b51935fa2d5814a1b4da9
if (suffix === 'ALT_WIN')
continue;
scriptName = codeToScriptName.get(suffix);
if (!scriptName)
throw new Error('NO Script name for: ' + suffix);
}
break;
}
// Skip things like IDS_NTP_FONT_FAMILY, IDS_MINIMUM_FONT_SIZE etc.
if (!familyName)
return;
fontFamilies.setFont(scriptName, familyName, e['_'])
});
result[platform] = fontFamilies.toJSON();
}
console.log(JSON.stringify(result, null, 2).replaceAll('"', `'`));