Skip to content

Commit

Permalink
complete porting ohms-law a11y strings into fluent, see phetsims/jois…
Browse files Browse the repository at this point in the history
  • Loading branch information
jessegreenberg committed Nov 18, 2024
1 parent a88070c commit 9c16a0f
Show file tree
Hide file tree
Showing 5 changed files with 104 additions and 77 deletions.
42 changes: 41 additions & 1 deletion js/OhmsLawFluentMessages.js
Original file line number Diff line number Diff line change
Expand Up @@ -104,6 +104,46 @@ class PatternMessageProperty extends DerivedProperty {
}
}

/**
* Changes a set of arguments for the message into a set of values that can easily be used to
* format the message. Does things like get Property values and converts enumeration values to strings.
*/
const handleArgs = args => {
const keys = Object.keys( args );

const newArgs = {};
keys.forEach( key => {
let value = args[ key ];

// If the value is a Property, get the value.
if ( isTReadOnlyProperty( value ) ) {
value = value.value;
}

// If the value is an EnumerationValue, automatically use the enum name.
if ( value && value.name ) {
value = value.name;
}

newArgs[ key ] = value;
} );

return newArgs;
};

/**
* Directly format a fluent message. Most of the time, you should use a PatternMessageProperty instead.
* This should only be used when the string does not need to be changed when the locale changes. Real-time
* alerts are a good exaple.
*
* TODO: Would live in another utility file, https://github.com/phetsims/joist/issues/992
*/
const formatMessage = ( localizedMessageProperty, args ) => {
const newArgs = handleArgs( args );
console.log( newArgs );
return localizedMessageProperty.bundleProperty.value.format( localizedMessageProperty.value, newArgs );
};

/**
* Converts a camelCase id to a message key. For example, 'choose-unit-for-current' becomes
* 'chooseUnitForCurrentMessageProperty'.
Expand All @@ -122,4 +162,4 @@ for ( const [ id ] of englishBundle.messages ) {
}

export default OhmsLawFluentMessages;
export { PatternMessageProperty };
export { PatternMessageProperty, formatMessage };
24 changes: 1 addition & 23 deletions js/ohms-law/OhmsLawConstants.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,22 +10,6 @@ import Range from '../../../dot/js/Range.js';
import RangeWithValue from '../../../dot/js/RangeWithValue.js';
import PhetFont from '../../../scenery-phet/js/PhetFont.js';
import ohmsLaw from '../ohmsLaw.js';
import OhmsLawA11yStrings from './OhmsLawA11yStrings.js';

const tinyString = OhmsLawA11yStrings.tiny.value;
const verySmallString = OhmsLawA11yStrings.verySmall.value;
const smallString = OhmsLawA11yStrings.small.value;
const mediumSizeString = OhmsLawA11yStrings.mediumSize.value;
const largeString = OhmsLawA11yStrings.large.value;
const veryLargeString = OhmsLawA11yStrings.veryLarge.value;
const hugeString = OhmsLawA11yStrings.huge.value;
const muchMuchSmallerThanString = OhmsLawA11yStrings.muchMuchSmallerThan.value;
const muchSmallerThanString = OhmsLawA11yStrings.muchSmallerThan.value;
const slightlySmallerThanString = OhmsLawA11yStrings.slightlySmallerThan.value;
const comparableToString = OhmsLawA11yStrings.comparableTo.value;
const slightlyLargerThanString = OhmsLawA11yStrings.slightlyLargerThan.value;
const muchLargerThanString = OhmsLawA11yStrings.muchLargerThan.value;
const muchMuchLargerThanString = OhmsLawA11yStrings.muchMuchLargerThan.value;

// constants used by other constants
const RESISTANCE_RANGE = new RangeWithValue( 10, 1000, 500 ); // in ohms
Expand Down Expand Up @@ -78,13 +62,7 @@ const OhmsLawConstants = {
BATTERIES_OFFSET: BATTERIES_OFFSET,
BATTERY_HEIGHT: 38,
AA_VOLTAGE: AA_VOLTAGE,
BATTERY_WIDTH: ( WIRE_WIDTH - BATTERIES_OFFSET * 2 ) / MAX_NUMBER_OF_BATTERIES,

RELATIVE_SIZE_STRINGS: [ tinyString, verySmallString, smallString, mediumSizeString,
largeString, veryLargeString, hugeString ],

COMPARISON_SIZE_STRINGS: [ muchMuchSmallerThanString, muchSmallerThanString, slightlySmallerThanString,
comparableToString, slightlyLargerThanString, muchLargerThanString, muchMuchLargerThanString ]
BATTERY_WIDTH: ( WIRE_WIDTH - BATTERIES_OFFSET * 2 ) / MAX_NUMBER_OF_BATTERIES
};

ohmsLaw.register( 'OhmsLawConstants', OhmsLawConstants );
Expand Down
26 changes: 12 additions & 14 deletions js/ohms-law/view/ControlPanel.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,8 +17,8 @@ import ohmsLaw from '../../ohmsLaw.js';
import OhmsLawFluentMessages, { PatternMessageProperty } from '../../OhmsLawFluentMessages.js';
import OhmsLawStrings from '../../OhmsLawStrings.js';
import OhmsLawModel from '../model/OhmsLawModel.js';
import OhmsLawA11yStrings from '../OhmsLawA11yStrings.js';
import OhmsLawConstants from '../OhmsLawConstants.js';
import { EquationLetter, SizeChange } from './OhmsLawDescriber.js';
import SliderUnit from './SliderUnit.js';

const resistanceString = OhmsLawStrings.resistance;
Expand All @@ -27,13 +27,6 @@ const voltageString = OhmsLawStrings.voltage;
const voltageSymbolString = OhmsLawStrings.voltageSymbol;
const voltageUnitsString = OhmsLawStrings.voltageUnits;

// can provide translators with context
const letterRString = OhmsLawA11yStrings.letterR.value;
const letterVString = OhmsLawA11yStrings.letterV.value;
const shrinksString = OhmsLawA11yStrings.shrinks.value;
const growsString = OhmsLawA11yStrings.grows.value;
const aLotString = OhmsLawA11yStrings.aLot.value;

// constants
const NUMBER_OF_LETTER_SIZES = 6; // pdom - the number of sizes that letters can be described as.

Expand Down Expand Up @@ -94,8 +87,8 @@ class ControlPanel extends Panel {

if ( oldVoltage !== newVoltage ) {
// pdom - when V changes, announce an alert that describes the change
const sizeChange = newVoltage - oldVoltage > 0 ? growsString : shrinksString;
voltageUtterance.alert = ohmsLawDescriber.getValueChangeAlertString( letterVString, sizeChange, sizeChange );
const sizeChange = newVoltage - oldVoltage > 0 ? SizeChange.GROWS : SizeChange.SHRINKS;
voltageUtterance.alert = ohmsLawDescriber.getValueChangeAlertString( EquationLetter.V, sizeChange, sizeChange );
voltageSlider.alertDescriptionUtterance( voltageUtterance );
}
}
Expand Down Expand Up @@ -124,11 +117,16 @@ class ControlPanel extends Panel {
const resistanceChange = newResistance - oldResistance;
const currentChange = newCurrent - oldCurrent;

const rSizeChange = resistanceChange > 0 ? growsString : shrinksString;
let iSizeChange = resistanceChange < 0 ? growsString : shrinksString;
iSizeChange += Math.abs( currentChange ) > twoSizeCurrentThreshhold ? ` ${aLotString}` : '';
const rSizeChange = resistanceChange > 0 ? SizeChange.GROWS : SizeChange.SHRINKS;
let iSizeChange;
if ( resistanceChange < 0 ) {
iSizeChange = Math.abs( currentChange ) > twoSizeCurrentThreshhold ? SizeChange.GROWS_A_LOT : SizeChange.GROWS;
}
else {
iSizeChange = Math.abs( currentChange ) > twoSizeCurrentThreshhold ? SizeChange.SHRINKS_A_LOT : SizeChange.SHRINKS;
}

resistanceUtterance.alert = ohmsLawDescriber.getValueChangeAlertString( letterRString, rSizeChange, iSizeChange );
resistanceUtterance.alert = ohmsLawDescriber.getValueChangeAlertString( EquationLetter.R, rSizeChange, iSizeChange );
resistanceSlider.alertDescriptionUtterance( resistanceUtterance );
}
};
Expand Down
60 changes: 27 additions & 33 deletions js/ohms-law/view/OhmsLawDescriber.js
Original file line number Diff line number Diff line change
Expand Up @@ -9,16 +9,10 @@
import DerivedProperty from '../../../../axon/js/DerivedProperty.js';
import EnumerationValue from '../../../../phet-core/js/EnumerationValue.js';
import Enumeration from '../../../../phet-core/js/Enumeration.js';
import StringUtils from '../../../../phetcommon/js/util/StringUtils.js';
import Utils from '../../../../dot/js/Utils.js';
import OhmsLawFluentMessages, { formatMessage } from '../../OhmsLawFluentMessages.js';
import OhmsLawConstants from '../OhmsLawConstants.js';
import ohmsLaw from '../../ohmsLaw.js';
import CurrentUnit from '../model/CurrentUnit.js';
import OhmsLawA11yStrings from '../OhmsLawA11yStrings.js';

const currentMilliampsString = OhmsLawA11yStrings.currentMilliamps.value;
const currentAmpsString = OhmsLawA11yStrings.currentAmps.value;
const sliderChangeAlertPatternString = OhmsLawA11yStrings.sliderChangeAlertPattern.value;

// enum for describing resistance impurities
class ResistorImpurities extends EnumerationValue {
Expand All @@ -32,6 +26,23 @@ class ResistorImpurities extends EnumerationValue {
static enumeration = new Enumeration( ResistorImpurities );
}

// enum for describing a letter in the ohms-law equation
export class EquationLetter extends EnumerationValue {
static V = new EquationLetter();
static I = new EquationLetter();
static R = new EquationLetter();
static enumeration = new Enumeration( EquationLetter );
}

// enum for describing the size change of a letter in the ohms-law equation
export class SizeChange extends EnumerationValue {
static GROWS = new SizeChange();
static SHRINKS = new SizeChange();
static GROWS_A_LOT = new SizeChange();
static SHRINKS_A_LOT = new SizeChange();
static enumeration = new Enumeration( SizeChange );
}

class OhmsLawDescriber {

/**
Expand Down Expand Up @@ -62,41 +73,24 @@ class OhmsLawDescriber {
* "As letter V grows, letter I grows. Current now 10.0 milliamps with voltage at 5.0 volts."
* Used for a11y.
*
* @param {string} initLetter - letter representing the model property that was changed
* @param {string} initSizeChange - string describing change in size of letter representing changed model Property
* @param {string} iSizeChange - string describing size change of letter I
* @param {EquationLetter} firstLetter - enum value representing the first letter of the phrase.
* @param {SizeChange} firstSizeChange - enum value representing the size change of the first letter
* @param {SizeChange} iSizeChange - enum value describing size change of letter I
* @param {number} currentVal - value of model current Property
* @returns {string} string
* @public
*/
getValueChangeAlertString( initLetter, initSizeChange, iSizeChange ) {
getValueChangeAlertString( firstLetter, firstSizeChange, iSizeChange ) {
const currentVal = this.model.getFixedCurrent();
return StringUtils.fillIn( sliderChangeAlertPatternString, {
initLetter: initLetter,
initSizeChange: initSizeChange,

return formatMessage( OhmsLawFluentMessages.sliderChangeAlertPatternMessageProperty, {
firstLetter: firstLetter,
firstSizeChange: firstSizeChange,
iSizeChange: iSizeChange,
currentVal: currentVal,
unit: this.getUnitForCurrent()
unit: this.model.currentUnitsProperty
} );
}


/**
* Get the current current unit
* @returns {string}
* @public
*/
getUnitForCurrent() {
switch( this.model.currentUnitsProperty.value ) {
case CurrentUnit.AMPS:
return currentAmpsString;
case CurrentUnit.MILLIAMPS:
return currentMilliampsString;
default:
break;
}
throw new Error( 'unexpected value for currentUnitsProperty' );
}
}

ohmsLaw.register( 'OhmsLawDescriber', OhmsLawDescriber );
Expand Down
29 changes: 23 additions & 6 deletions ohms-law-strings_en.ftl
Original file line number Diff line number Diff line change
Expand Up @@ -79,9 +79,26 @@ current-summary-pattern = current, <strong>I</strong>, is <em>{ $value } { $unit
# Slider strings
slider-controls = Slider Controls
sliders-description = Voltage and resistance sliders allow changes to equation and circuit.
slider-change-alert-pattern = As letter { $initLetter } { $initSizeChange }, letter I { $iSizeChange }. Current now { $currentVal } { $unit }.
letter-r = R
letter-v = V
shrinks = shrinks
grows = grows
a-lot = a lot
-letter-r = R
-letter-v = V
-shrinks = shrinks
-grows = grows
-shrinks-a-lot = shrinks a lot
-grows-a-lot = grows a lot
slider-change-alert-pattern = As letter { $firstLetter ->
[R] { -letter-r }
*[V] { -letter-v }
} { $firstSizeChange ->
[SHRINKS] { -shrinks }
[SHRINKS_A_LOT] { -shrinks-a-lot }
[GROWS] { -grows }
*[GROWS_A_LOT] { -grows-a-lot }
}, letter I { $iSizeChange ->
[SHRINKS] { -shrinks }
[SHRINKS_A_LOT] { -shrinks-a-lot }
[GROWS] { -grows }
*[GROWS_A_LOT] { -grows-a-lot }
}. Current now { $currentVal } { $unit ->
[AMPS] { -amps }
*[MILLIAMPS] { -milliamps }
}.

0 comments on commit 9c16a0f

Please sign in to comment.