flutter3d_game_ui 1.0.0-rc.2
flutter3d_game_ui: ^1.0.0-rc.2 copied to clipboard
Every widget around a flutter3d game, one library each: HUD and maps, touch controls, settings, accessibility, title and credits screens, photo mode, sharing a run.
1.0.0-rc.2 #
-
Breaking: one concept has one spelling. A field of view is
fieldOfView(where it wasfovY,yfovorfov), a ray is cast withrayCastand half a size ishalfExtents, as the rest of the engine names them:Lens.at,Lens.fovYAt,Lens.widened. The same values under the one name; serialized keys are unchanged, anddart fixrenames the calls, the arguments and the overrides. -
Breaking:
TuningChange.tuningissettings, with the parameters ofRolesApart. A parameter or a field that holds a…Settingsis namedsettings, as every other one is, where some weretuning,configoroptions: the same value under one name.dart fixrenames the arguments and the fields. -
Breaking:
PrivacySection.onChangedisonAnswered. It is handed nothing, where every otheronChangedis handed the new value.dart fixrenames it. -
Breaking: results that were records are final classes.
TouchButtonanswered or held a record, which can never gain a field. Each answers a final class now, with the record's field names (a positional$1has a name of its own),==andhashCode. A field read compiles as before; a destructuring pattern names the class, andflutter3d_build:migraterewrites the$1reads. -
Breaking:
LicenseEntryisLicenseSection.LicenseEntryandLicenseRecordchanged with it:package:flutter/foundation.dartexports aLicenseEntry, the license registry's, so a credits screen importing both had to hide one.dart fixrenames it. -
Breaking:
SpokenEventsisflutter3d_game_ui.spoken_eventsby default, where it wasflutter3d_addon_access.spoken_events. A run recorded under the old id reads as naming the new one. -
Breaking: every widget and painter is a
final class. A widget is composed, not extended, and a new option on one is then an addition: a plain class could be implemented, so it could never gain a field. -
Breaking: a photo control and a settings section take one context.
PhotoControls.steertakes aPhotoSteerContext(new) with the camera, the frame's seconds, the input and the look, whichPhotoModereuses every frame;SettingsSection.buildtakes aSettingsSectionContext(new) with the build context, the settings and the panel's state. A game's own control or section then keeps compiling when a minor hands it more. -
Every widget here keeps WCAG 2.2 at level AA, and
test/accessibility_test.dart(tagaccessibility) holds each screen to it at the platform text size and at twice it, over a white frame and a black one: labelled targets of 24 pixels or more, text contrast measured from the pixels, every line on the platform'stextScalerand none cut off. -
WcagandContrastPairare new (theme.dart): the numbers AA asks for, the WCAG contrast ratio, and a pair of colours with the ratio it keeps over every grey frame from black to white, a control counted by the better of its face and its rim.GameUiTheme.contrastPairsnames every pair the widgets draw. -
GameUiTheme's defaults are the ones that pass. The touch controls are dark faces with a light rim, where they were a third of white over the picture;panelis darker,errorandhudLabellighter, the maps' colours moved to keep three to one. Two tokens are new:sheet(what a title or an ending puts over the game) andnotice(the amber line on it).GameUiTheme.controlsThemegives Flutter's own controls on these dark panels a dark scheme seeded fromaccent, so a light app theme no longer puts a purple button on the settings scrim. -
No colour is typed into a widget any more.
HudTallyStyle.color,HudBanner.color,EndingSheet.titleColorandMiniMapPainter's three colours are nullable and fall back to the theme;EndingSheet.backdropis the opacity ofGameUiTheme.sheet. A tally, a banner, a cutscene's subtitle and its skip button sit onpanel, and the settings gear has a panel behind it. -
The text grows with the player's text size and is never cut. The heads-up label column, the settings columns and the share strip grow with the
textScaler; a touch control's label grows up to what its face holds and is scaled back into it rather than clipped. -
FlashLimitis new (access.dart): a full-screen brightness held to three flashes in any second (WCAG 2.3.1).CutsceneOverlaysends its fade through one, so a sequence that strobes is drawn at the limit, and is aStatefulWidgetfor it. -
The camera-motion slider shows the system's answer until the player gives one, as the high-contrast switch does: with reduce-motion on it reads nought, which is what the game keeps.
-
A screen reader can name and use every control.
TouchStickandSteeringBandtake alabel(defaultFlutter3dGameLocalizations.stickandsteering, new, in English and Russian);TitleSheetandTapToRestartare buttons a reader's double tap begins or restarts; a volume slider carries its bus's name; a banner, a cutscene's subtitle, the photo bar's last sentence, the share strip's answer and the unsaved settings line are live regions. -
RoleRings.ofanswers aLinearColor, the colourActorVisuals.outlineOfandFixtureVisuals.outlineOftake now. -
Photo mode's sprint flies faster again.
ActionPhotoControlsandKeyPhotoControlsscale the time byPhotoControls.fastFactorrather than the intent, whichPhotoCamera.flycut back to length one, so the sprint key had no effect. -
Every widget around a game is here. The touch controls, the settings panel and its sections, the privacy questions, the automap, the credits, the loss screen,
GameUiThemeandFlutter3dGameLocalizationscome fromflutter3d_game. Two new libraries hold what had no home here:settings.dart(the panel) andtheme.dart(the colours and the words); the rest joinedtouch.dart,hud.dartandscreens.dart. -
Breaking: one widget per job.
TouchClusterisTouchControls, which gained its numbered slots and its corner switch (toggle:iscorner:); a game that hands neither gets the stick and row it had.PedalisTouchButton.pedal, the same held button in the shape of a pedal. The credits are one file:Credit,CreditsSection,CreditLedgerandLicenseRecordtogether.MiniMapandAutomapViewstay two widgets, because a course's outline and the cells a player has walked are two different maps. -
Portablecomes fromflutter3d_foundation, so the lens no longer needs the physics package. -
Breaking:
ReelShot.film(clearColor:)takes aLinearColor, linear asRenderView.clearColoris, where it took an sRGBVector4:LinearColor.fromSrgb(r, g, b, a)draws the same picture. -
Breaking:
RoleRingsreads the settings through a function,RoleRings(roles, () => controller.settings), sinceGameSettingsis a value and a change makes a new one;RolesApart.applyreturns the settings with the moved roles written in rather than editing them. -
Breaking: an ending's number is
EndingTally, notTally, which is the simulation's counter influtter3d_sim; a game importing both no longer hides one. -
MiniMap,PedalandSteeringBandreadGameUiTheme.MiniMap.playerColorandothersColorare nullable and default to the theme'sminiMapPlayerandminiMapOthers; its line and box areminiMapTrackandminiMapBackdrop, andMiniMapPainter.trackColoris new. The pedals and the steering band take thetouch*roles. -
New: one package for what was six.
flutter3d_addon_hud,flutter3d_addon_touch,flutter3d_addon_access,flutter3d_addon_screens,flutter3d_addon_photo_mode,flutter3d_addon_captureare libraries of this package now:hud.dart,touch.dart,access.dart,screens.dart,photo_mode.dart,capture.dart, each with the API its package had, andflutter3d_game_ui.dartexports them all.dart run flutter3d_build:migratemoves a project's dependencies and imports; the packages' own histories are indoc/changelogs/.
hud.dart, from flutter3d_addon_hud 1.0.0-rc.1 #
-
Breaking: public constants are lowerCamelCase, without the k prefix, as Effective Dart asks.
kBeaconGlowisbeaconGlow. The values are the same;dart fixcarries the renames. -
Breaking: American spelling in identifiers, as Flutter and Dart use.
accentColourisaccentColor,colouriscolor,metresPerSecondismetersPerSecond,othersColourisothersColor,playerColourisplayerColor. Only the Dart names changed: a file keeps the keys it was written with, anddart fixcarries the renames. -
Breaking: the HUD's colours are the theme's.
HudLine.defaultAccentandHudLine.labelWidthare gone;GameUiTheme(aThemeExtensioninflutter3d_game) holds the accent, the label colour, the label column's width and the panel's background, with the old values as its fallback.HudLine.accentColoris nullable and overrides the theme's accent.Speedometersays its unit in the player's language. -
The HUD pieces the demos each drew for themselves.
HudPanelandHudLinefrom racing,HudTallyandHudBannerfrom the platformer and strategy (one widget each now, with aHudTallyStylefor the ink and the sizes that differed), and theSpeedometer, which takes metres a second rather than a race's readout. -
The minimap draws any course.
MiniMaptakes an outline and a list of markers, the first the player's, and fits the course to its box.MiniMapPainter.placesays where a point lands, for a HUD that lays out its own frame. -
A hint is a rule.
MomentHintis a sentence and the moment it is true;MomentHintssays each of several once, one a step, untilforget. The dungeon's first-shot hint is one. -
An objective that can be found in the dark.
lightBeaconraises what already glows on an object tobeaconGlow, normalised so a second call changes nothing. -
The stereo HUD panel is part of this package.
StereoHudPanelbuilds a HUD once and redraws it from aValueListenable, for a surface in front of a stereo camera. Too small for a package of its own.
touch.dart, from flutter3d_addon_touch 1.0.0-rc.1 #
-
Breaking:
TouchDrive's labels come from the player's language.throttleLabel,brakeLabelandhandbrakeLabelare nullable, null forFlutter3dGameLocalizations's words; a game's own still override. -
The controls bind to actions of every kind.
SteeringBand.axisandTouchDrive.steerwrite the wheel as oneAxisActionbeside the two magnitudes, andTouchCluster.stickActionputs the stick on anyDualAxisAction. -
Breaking:
SteeringBand,TouchCluster,TouchDriveas the snapshot counts it: a new optional field on each. No caller changes. -
An analogue axis under a thumb.
SteeringBandwrites how far left or right of centre the thumb is as two actions' magnitudes, sets the idle side to nought so a key held on the same machine cannot steer against it, and withdraws both on release so the keyboard has them back. -
A pedal is a held button with a name.
Pedalpresses its action while one finger is on it, lets go on lift, cancel or unmount, and says its label to a screen reader. -
Two layouts, each for a kind of game.
TouchDriveis a band and pedals with one button in the far corner, never wanted mid-corner.TouchClusteris a stick, a cluster of buttons, numbered slots and a switch, placed by how often each is wanted and how bad it is to press by mistake. -
Out of the demos. The racing demo's band, pedals and layout, and the dungeon demo's cluster, moved here; each demo keeps only which of its actions go where.
access.dart, from flutter3d_addon_access 1.0.0-rc.1 #
-
Breaking: one suffix for settings, Settings, and Descriptor in the HAL.
GameConfigisGameSettings. Every settings class isfinalwith aconstconstructor and acopyWithover every field; a nullable field is reset withcopyWith(clearX: true).dart fixcarries the renames. -
Breaking:
announceToandannounceToImplicitViewspeak in the platform's direction. Theirdirectiondefaulted to left to right, so a sentence in Arabic or Hebrew was read in the wrong order; null now asks the platform's language (platformTextDirection), andannounceIn(context)speaks on the context's view in its ambientDirectionality. A caller that passed a direction is unchanged. -
Rings in the colour a player chose.
RoleRingsgives the high-contrast look's ring colour for a role, read from the settings on every call, so a change in the panel is the ring's colour on the next frame. The dungeon's rings are built on it; which things are worth a ring stays the game's question. -
Roles moved apart for the player's eyes.
RolesApart.choicesForsays which palette colour each colliding role should take for the deficiency the player named, andapplywrites it into the settings. With none named it moves nothing. -
What happens, said to a screen reader.
SpokenEventsis a view plugin on the bus's frame channel: a table of event types and sentences, said as announcements through Flutter's semantics. The same sentence waits a number of steps before it is said again; the limit is counted in steps, so it needs no clock. Nothing is written back, so the game is the same with it installed.
screens.dart, from flutter3d_addon_screens 1.0.0-rc.1 #
-
Breaking: a field of view is
fovY, in radians, wherever this package names one (docs/CONTRACTS.md). -
Breaking: American spelling in identifiers, as Flutter and Dart use.
colouriscolor,licenceislicense,LicenceEntryisLicenseEntry,LicenceRecordisLicenseRecord,licenceUrlislicenseUrl. Only the Dart names changed: a file keeps the keys it was written with, anddart fixcarries the renames. -
Breaking: one home for
Credit. The barrel re-exportedCreditandCreditsSectionfromflutter3d_game, so the type had two libraries to be imported from; it no longer does. Importflutter3d_game. -
Breaking:
EndingSheet.creditsHeadingcomes from the player's language. It is nullable, null forFlutter3dGameLocalizations.artInThisGame.creditsFootnoteonEndingSheetandTitleSheetis the game's own line under the credits, sinceCreditsSectionno longer has a default one. -
The screens around play, out of the games.
TitleSheet,EndingSheetwithTallyandTallyView, andCutsceneOverlaywere laid out by hand in the platformer, the dungeon and racing, the same way each time. A game now hands them its words and its numbers and keeps nothing of the layout. -
Credits held to the licence record.
CreditLedgeris the list a game ships withowedanduntraced, which five games wrote out identically.LicenseRecordreads theLICENSES.mdbeside the models, in both shapes the games keep it in, anddisagreementsWithnames every file the record does not mention and every licence or author the two state differently. The games' tests used to search the record's text for a file name. -
A lens that keeps the view on a narrow screen.
Lensis the platformer's single base projection withwidened, and addsat: below itsdesignAspectthe vertical field of view opens so the horizontal one stays what it was designed to be.
photo_mode.dart, from flutter3d_addon_photo_mode 1.0.0-rc.1 #
-
Breaking: a boolean reads as a question, and no
boolis positional.PhotoMode.activeisisActive;PhotoMode.manualExposureisusesManualExposure;PhotoMode.busyisisBusy.dart fixcarries the renames. -
Breaking: the photo bar's words come from
Flutter3dGameLocalizations.PhotoMode.walkingKeysandPhotoMode.exposureKeysare gone, andkeysHintis nullable: null shows the walking keys in the player's language, and a game with other keys still passes its own line. The package depends onflutter3d_gamefor them. -
One photo mode for every game.
PhotoModeandPhotoBarhold the engine'sPhotoCameraandPhotoFiltertogether and own the filter, tilt, zoom and capture keys while it is open. Four demos had their own copy; they build this one now. -
The game says how its keys fly the camera.
ActionPhotoControlsreads the game's own actions and mouse,KeyPhotoControlsthe keyboard as held, with the arrows turning it if the game asks. Either is read, never stepped: the loop is paused and nothing of the flying reaches the run. -
Its lens, not a default one. The picture is taken through the lens the game hands in, zoomed, so a far plane or a chase camera's widened view survives the moment photo mode opens.
-
A game whose keys would stick says so.
takesEveryKeykeeps every key and its release while photo mode is open, so a throttle held when the picture was framed is not still held when the run comes back. -
Aperture, shutter and ISO (
B6.22).PhotoMode.exposureis aPhysicalCamerathe keys 1 to 6 move a third of a stop at a time, and 0 hands the exposure back to the game;enter(camera:)starts the dials at the game's own.PhotoMode.settingsapplies it once a dial is turned — the physical camera on, auto exposure off — and, with the game's depth of field on, focuses at the camera's aperture.PhotoBarshows the setting and the keys.
capture.dart, from flutter3d_addon_capture 1.0.0-rc.1 #
-
Breaking:
reelOutis gone;Reel.outis the game's. The folder was a constant read from--dart-define=REEL_OUT, so every game on the engine answered to one variable.Reel.outdefaults toreel, and an entry point that wants the define reads it itself. -
Breaking:
ShareStrip's words come fromFlutter3dGameLocalizations.shareLabel,codeHintandopenLabelare nullable; null says them in the player's language (English and Russian ship), and a game's own words still override. The package depends onflutter3d_gamefor them. -
A game filmed frame by frame.
ReelandReelShotstep nothing themselves: a game places its camera and steps its worldreelFrameStepa frame, andfilmdraws the frame at full size and writes it as<out>/<shot>/frame_NNNN.png. Five demos filmed the 0.9 reel with their own PNG writers and folder shelves; they film through this now. -
One tile unless asked. A frame is drawn whole by default, so a pass that reads its neighbours is not cut at a tile's edge; a reel that wants photo mode's tiles says so.
-
A hole stops the reel. A frame that could not be written throws with the shelf's sentence, rather than leaving a numbered sequence with one missing for an encoder to stumble on.
-
Sharing in a sentence.
ShareStripfiles the run just played and says its code, and opens a friend's; every answer is a sentence, because a share that failed silently is a code nobody can open. Its words are the game's.