diff --git a/web/packages/core/src/config.ts b/web/packages/core/src/config.ts index dc22ae1a1..f7dcd37cf 100644 --- a/web/packages/core/src/config.ts +++ b/web/packages/core/src/config.ts @@ -46,4 +46,5 @@ export const DEFAULT_CONFIG: Required = { openInNewTab: null, socketProxy: [], fontSources: [], + defaultFonts: {}, }; diff --git a/web/packages/core/src/load-options.ts b/web/packages/core/src/load-options.ts index 477271a31..ee187ba64 100644 --- a/web/packages/core/src/load-options.ts +++ b/web/packages/core/src/load-options.ts @@ -267,6 +267,30 @@ export interface SocketProxy { proxyUrl: string; } +/** + * Defines the names of the fonts to use for each "default" Flash device font. + * + * The name of each font provided will be used, in priority order. + * + * For example, defining `sans: ["Helvetica", "Arial"]` would use Helvetica if present, before trying Arial. + */ +export interface DefaultFonts { + /** + * `_sans`, a Sans-Serif font (similar to Helvetica or Arial) + */ + sans?: Array; + + /** + * `_serif`, a Serif font (similar to Times Roman) + */ + serif?: Array; + + /** + * `_typewriter`, a Monospace font (similar to Courier) + */ + typewriter?: Array; +} + /** * Any options used for loading a movie. */ @@ -574,6 +598,13 @@ export interface BaseLoadOptions { * @default [] */ fontSources?: Array; + + /** + * The font names to use for each "default" Flash device font. + * + * @default {} + */ + defaultFonts?: DefaultFonts; } /** diff --git a/web/packages/core/src/ruffle-player.ts b/web/packages/core/src/ruffle-player.ts index 2f7587f41..15f86ec7b 100644 --- a/web/packages/core/src/ruffle-player.ts +++ b/web/packages/core/src/ruffle-player.ts @@ -731,6 +731,25 @@ export class RufflePlayer extends HTMLElement { } } + if (this.loadedConfig?.defaultFonts?.sans) { + this.instance!.set_default_font( + "sans", + this.loadedConfig?.defaultFonts.sans, + ); + } + if (this.loadedConfig?.defaultFonts?.serif) { + this.instance!.set_default_font( + "serif", + this.loadedConfig?.defaultFonts.serif, + ); + } + if (this.loadedConfig?.defaultFonts?.typewriter) { + this.instance!.set_default_font( + "typewriter", + this.loadedConfig?.defaultFonts.typewriter, + ); + } + this.instance!.set_volume(this.volumeSettings.get_volume()); this.rendererDebugInfo = this.instance!.renderer_debug_info(); diff --git a/web/src/lib.rs b/web/src/lib.rs index f3ac7fab8..2c43395ba 100644 --- a/web/src/lib.rs +++ b/web/src/lib.rs @@ -19,8 +19,8 @@ use ruffle_core::external::{ ExternalInterfaceMethod, ExternalInterfaceProvider, FsCommandProvider, Value as ExternalValue, Value, }; -use ruffle_core::swf; use ruffle_core::tag_utils::SwfMovie; +use ruffle_core::{swf, DefaultFont}; use ruffle_core::{ Color, Player, PlayerBuilder, PlayerEvent, SandboxType, StageAlign, StageScaleMode, StaticCallstack, ViewportDimensions, @@ -494,6 +494,27 @@ impl Ruffle { }); } + pub fn set_default_font(&mut self, default_name: &str, fonts: Vec) { + let _ = self.with_core_mut(|core| { + let default = match default_name { + "sans" => DefaultFont::Sans, + "serif" => DefaultFont::Serif, + "typewriter" => DefaultFont::Typewriter, + name => { + tracing::error!("Unknown default font name '{name}'"); + return; + } + }; + core.set_default_font( + default, + fonts + .into_iter() + .flat_map(|value| value.as_string()) + .collect(), + ); + }); + } + #[allow(clippy::boxed_local)] // for js_bind pub fn call_exposed_callback(&self, name: &str, args: Box<[JsValue]>) -> JsValue { let args: Vec = args.iter().map(js_to_external_value).collect();