Skip to content

Commit

Permalink
Set up iOS alias color tokens (#2481)
Browse files Browse the repository at this point in the history
### Platforms Impacted
- [x] iOS
- [ ] macOS
- [ ] win32 (Office)
- [ ] windows
- [ ] android

### Description of changes

Set up iOS alias color tokens in FURN (just neutral and brand colors for now; shared colors will be done in a future PR), so the tokens specified in updated Fluent2 designs can be accessed through the theme.

1. The pipeline output is retrieved by getTokens.ios.ts
   - Also moved apple-theme/getiOSTokens.ts to theme-tokens/getTokens.ios.ts, as per #2190. Slightly unrelated but also recombined the existing android/windows getTokens/getShadowTokens files - they were separated to make android token integration more simple but since that work is complete, should be fine to recombine them and have less files 
3. The output gets mapped in an AliasColorTokens object through mapPipelineToTheme
   - The AliasColorTokens object was updated to include some new mobile tokens
   - The existing mapPipelineToTheme method in the mapPipelineToTheme.ios.ts file was copied from the original mapPipelineToTheme.ts file. Updated it to match designs - for this file reviewing commit by commit should make the changes more clear
4. The AliasColorTokens object gets added to the iOS color palette in paletteFromAppleColors  by createiOSColorAliasTokens

Out of scope for this PR:
1. Shared colors (ex. dangerbackground1) - there's been some questions raised about the definitions for these tokens so they haven't been added to the design-tokens package yet
2. Moving all createAliasTokens files from platform-specific themes into the theme-tokens folder - this seemed to have been planned for all the platforms but none of them do this yet. Planning to do this in a future PR

### Verification

Initial verification since the actual tokens aren't part of FURN yet - copied some tokens into the IOS alias-tokens files in node_modules, and checked that they were part of the final iOS palette.

No visual changes otherwise. Will add these tokens to the Notification component in a future PR for additional verification.

### Pull request checklist

This PR has considered (when applicable):
- [ ] Automated Tests
- [ ] Documentation and examples
- [ ] Keyboard Accessibility
- [ ] Voiceover
- [ ] Internationalization and Right-to-left Layouts
  • Loading branch information
lyzhan7 authored Jan 10, 2023
1 parent 15e7ff1 commit bd23a4a
Show file tree
Hide file tree
Showing 19 changed files with 225 additions and 154 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
{
"type": "minor",
"comment": "Set up iOS color alias tokens",
"packageName": "@fluentui-react-native/apple-theme",
"email": "78454019+lyzhan7@users.noreply.github.com",
"dependentChangeType": "patch"
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
{
"type": "minor",
"comment": "Bump iOS token packages to include iOS color alias tokens",
"packageName": "@fluentui-react-native/theme-tokens",
"email": "78454019+lyzhan7@users.noreply.github.com",
"dependentChangeType": "patch"
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
{
"type": "minor",
"comment": "Set up iOS color alias tokens",
"packageName": "@fluentui-react-native/theme-types",
"email": "78454019+lyzhan7@users.noreply.github.com",
"dependentChangeType": "patch"
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
{
"type": "minor",
"comment": "Set up iOS color alias tokens",
"packageName": "@fluentui-react-native/theming-utils",
"email": "78454019+lyzhan7@users.noreply.github.com",
"dependentChangeType": "patch"
}
3 changes: 2 additions & 1 deletion packages/theming/apple-theme/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -32,10 +32,11 @@
},
"dependencies": {
"@fluentui-react-native/default-theme": ">=0.16.22 <1.0.0",
"@fluentui-react-native/design-tokens-ios": "^0.36.0",
"@fluentui-react-native/design-tokens-ios": "^0.38.0",
"@fluentui-react-native/design-tokens-macos": "^0.36.0",
"@fluentui-react-native/memo-cache": "^1.1.7",
"@fluentui-react-native/theme": ">=0.7.15 <1.0.0",
"@fluentui-react-native/theme-tokens": "^0.22.5",
"@fluentui-react-native/theme-types": ">=0.28.0 <1.0.0",
"@fluentui-react-native/theming-utils": "^0.21.0",
"assert-never": "^1.2.1"
Expand Down
10 changes: 10 additions & 0 deletions packages/theming/apple-theme/src/appleColors.ios.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
import { ThemeColorDefinition } from '@fluentui-react-native/theme-types';
import { getCurrentAppearance } from '@fluentui-react-native/theming-utils';
import { Appearance } from 'react-native';
import { ApplePalette } from './appleColors.types.ios';
import { createiOSColorAliasTokens } from './createiOSAliasTokens';

function getFluentUIAppleLightPalette(): ApplePalette {
return {
Expand Down Expand Up @@ -215,7 +218,14 @@ function getFluentUIAppleDarkPalette(): ApplePalette {
export function paletteFromAppleColors(isLightMode: boolean): ThemeColorDefinition {
const fluentApple = isLightMode ? getFluentUIAppleLightPalette() : getFluentUIAppleDarkPalette();

const appearance = Appearance.getColorScheme();
const mode = getCurrentAppearance(appearance, 'light');

return {
/* Color Alias Tokens */

...createiOSColorAliasTokens(mode),

/* PaletteBackgroundColors & PaletteTextColors */

background: fluentApple.surfacePrimary,
Expand Down
15 changes: 11 additions & 4 deletions packages/theming/apple-theme/src/createiOSAliasTokens.ts
Original file line number Diff line number Diff line change
@@ -1,11 +1,18 @@
import { getiOSShadowTokens } from './getiOSTokens';
import { AppearanceOptions } from '@fluentui-react-native/theme-types';
import { mapPipelineToShadow } from '@fluentui-react-native/theming-utils';
import { getAliasTokens, getShadowTokens } from '@fluentui-react-native/theme-tokens';
import { AliasColorTokens, AppearanceOptions } from '@fluentui-react-native/theme-types';
import { mapPipelineToTheme, mapPipelineToShadow } from '@fluentui-react-native/theming-utils';
import { memoize } from '@fluentui-react-native/memo-cache';
import { ThemeShadowDefinition } from '@fluentui-react-native/theme-types/lib/Shadow.types';

function createiOSColorAliasTokensWorker(mode: AppearanceOptions): AliasColorTokens {
const aliasTokens = getAliasTokens(mode);
return mapPipelineToTheme(aliasTokens);
}

export const createiOSColorAliasTokens = memoize(createiOSColorAliasTokensWorker);

function createiOSShadowAliasTokensWorker(mode: AppearanceOptions): ThemeShadowDefinition {
const aliasTokens = getiOSShadowTokens(mode);
const aliasTokens = getShadowTokens(mode);
return mapPipelineToShadow(aliasTokens);
}

Expand Down
16 changes: 0 additions & 16 deletions packages/theming/apple-theme/src/getiOSTokens.ts

This file was deleted.

2 changes: 1 addition & 1 deletion packages/theming/theme-tokens/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@
"license": "MIT",
"dependencies": {
"@fluentui-react-native/design-tokens-android": "^0.37.0",
"@fluentui-react-native/design-tokens-ios": "^0.36.0",
"@fluentui-react-native/design-tokens-ios": "^0.38.0",
"@fluentui-react-native/design-tokens-win32": "^0.36.0",
"@fluentui-react-native/design-tokens-windows": "^0.36.0",
"@fluentui-react-native/theme-types": ">=0.28.0 <1.0.0",
Expand Down
13 changes: 0 additions & 13 deletions packages/theming/theme-tokens/src/getShadowTokens.android.ts

This file was deleted.

15 changes: 0 additions & 15 deletions packages/theming/theme-tokens/src/getShadowTokens.ts

This file was deleted.

18 changes: 18 additions & 0 deletions packages/theming/theme-tokens/src/getTokens.android.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
import lightAliasTokens from '@fluentui-react-native/design-tokens-android/light/tokens-aliases.json';
import darkAliasTokens from '@fluentui-react-native/design-tokens-android/dark/tokens-aliases.json';
import lightShadowTokens from '@fluentui-react-native/design-tokens-android/light/tokens-shadow.json';
import darkShadowTokens from '@fluentui-react-native/design-tokens-android/dark/tokens-shadow.json';

import { AppearanceOptions } from '@fluentui-react-native/theme-types';

export function getAliasTokens(mode: AppearanceOptions) {
Expand All @@ -8,5 +11,20 @@ export function getAliasTokens(mode: AppearanceOptions) {
} else if (mode === 'dark') {
return darkAliasTokens;
}

// TODO #2492 we should be throwing an error if highContrast mode is set in Android, but currently
// the default theme tries to create a highContrast mode so as a workaround we return the light mode tokens.
return lightAliasTokens;
}

export function getShadowTokens(mode: AppearanceOptions) {
if (mode === 'light') {
return lightShadowTokens;
} else if (mode === 'dark') {
return darkShadowTokens;
}

// TODO #2492 we should be throwing an error if highContrast mode is set in Android, but currently
// the default theme tries to create a highContrast mode so as a workaround we return the light mode tokens.
return lightShadowTokens;
}
35 changes: 35 additions & 0 deletions packages/theming/theme-tokens/src/getTokens.ios.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
import iOSLightAliasTokens from '@fluentui-react-native/design-tokens-ios/light/tokens-aliases.json';
import iOSDarkAliasTokens from '@fluentui-react-native/design-tokens-ios/dark/tokens-aliases.json';
import iOSLightShadowTokens from '@fluentui-react-native/design-tokens-ios/light/tokens-shadow.json';
import iOSDarkShadowTokens from '@fluentui-react-native/design-tokens-ios/dark/tokens-shadow.json';

import { AppearanceOptions } from '@fluentui-react-native/theme-types';
import { assertNever } from 'assert-never';

export function getAliasTokens(mode: AppearanceOptions) {
if (mode === 'light') {
return iOSLightAliasTokens;
} else if (mode === 'dark') {
return iOSDarkAliasTokens;
} else if (mode === 'highContrast') {
// TODO #2492 we should be throwing an error if highContrast mode is set in iOS, but currently
// the default theme tries to create a highContrast mode so as a workaround we return the light mode tokens.
return iOSLightAliasTokens;
} else {
assertNever(mode);
}
}

export function getShadowTokens(mode: AppearanceOptions) {
if (mode === 'light') {
return iOSLightShadowTokens;
} else if (mode === 'dark') {
return iOSDarkShadowTokens;
} else if (mode === 'highContrast') {
// TODO #2492 we should be throwing an error if highContrast mode is set in iOS, but currently
// the default theme tries to create a highContrast mode so as a workaround we return the light mode tokens.
return iOSLightShadowTokens;
} else {
assertNever(mode);
}
}
15 changes: 15 additions & 0 deletions packages/theming/theme-tokens/src/getTokens.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
import lightAliasTokens from '@fluentui-react-native/design-tokens-windows/light/tokens-aliases.json';
import darkAliasTokens from '@fluentui-react-native/design-tokens-windows/dark/tokens-aliases.json';
import lightShadowTokens from '@fluentui-react-native/design-tokens-windows/light/tokens-shadow.json';
import darkShadowTokens from '@fluentui-react-native/design-tokens-windows/dark/tokens-shadow.json';
import hcShadowTokens from '@fluentui-react-native/design-tokens-win32/hc/tokens-shadow.json';

import { hcAliasTokens } from './highContrast/tokens-alias';
import { AppearanceOptions } from '@fluentui-react-native/theme-types';
import { assertNever } from 'assert-never';
Expand All @@ -17,3 +21,14 @@ export function getAliasTokens(mode: AppearanceOptions) {

return lightAliasTokens;
}

export function getShadowTokens(mode: AppearanceOptions) {
if (mode === 'light') {
return lightShadowTokens;
} else if (mode === 'dark') {
return darkShadowTokens;
}

// HC mode.
return hcShadowTokens;
}
3 changes: 1 addition & 2 deletions packages/theming/theme-tokens/src/index.ts
Original file line number Diff line number Diff line change
@@ -1,3 +1,2 @@
export { default as globalTokens } from './tokens-global';
export { getAliasTokens } from './getTokens';
export { getShadowTokens } from './getShadowTokens';
export { getAliasTokens, getShadowTokens } from './getTokens';
24 changes: 24 additions & 0 deletions packages/theming/theme-types/src/Color.types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -522,6 +522,14 @@ export interface AliasColorTokens {
/** @platform android, iOS */
neutralForegroundOnColor?: ColorValue;

// TODO #2440: Add to android
/** @platform iOS */
neutralForegroundDarkStatic?: ColorValue;

// TODO #2440: Add to android
/** @platform iOS */
neutralForegroundLightStatic?: ColorValue;

/** @platform macOS, win32, windows */
neutralForegroundOnBrand?: ColorValue;

Expand Down Expand Up @@ -661,6 +669,14 @@ export interface AliasColorTokens {
/** @platform android, iOS, macOS, win32, windows */
neutralBackground6?: ColorValue;

// TODO #2440: Add to android
/** @platform iOS */
neutralBackgroundCanvas?: ColorValue;

// TODO #2440: Add to android
/** @platform iOS */
neutralBackgroundDarkStatic?: ColorValue;

/** @platform android, iOS, macOS, win32, windows */
neutralBackgroundInverted?: ColorValue;

Expand Down Expand Up @@ -788,6 +804,14 @@ export interface AliasColorTokens {
/** @platform android, iOS, macOS, win32, windows */
neutralStrokeDisabled?: ColorValue;

// TODO #2440: Add to android
/** @platform iOS */
neutralStrokeFocus1?: ColorValue;

// TODO #2440: Add to android
/** @platform iOS */
neutralStrokeFocus2?: ColorValue;

/** @platform macOS, win32, windows */
strokeFocus1?: ColorValue;

Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,6 @@
import { AliasColorTokens, Variants, VariantValue } from '@fluentui-react-native/theme-types';

// API that translates tokens coming for android to Theme color values.
// This is implemented in a per-plaform fashion, for each endpoint that maps to similar token sets in design - i.e. map to similar
// pipeline output.
// API that maps tokens coming from the android token pipeline to Theme color values.
export function mapPipelineToTheme(pipelineOutput: any): AliasColorTokens {
return {
neutralForeground1: pipelineOutput.neutralForeground1.fillColorRest,
Expand Down
Loading

0 comments on commit bd23a4a

Please sign in to comment.