-
Notifications
You must be signed in to change notification settings - Fork 82
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
v3 #124
Conversation
Okay, starting from scratch here. import type { Theme } from '@theme-ui/css'
export interface DripsyBaseTheme extends Omit<Theme, 'fonts'> {
customFonts?: { [key: string | number]: Record<string, string> }
fonts?: Partial<Record<'root', string>> & Partial<Record<string, string>>
}
export interface DripsyCustomTheme {
//
}
export interface DripsyFinalTheme extends DripsyBaseTheme, DripsyCustomTheme {} And then type SxProp = {
[key in keyof ThemeUICSSProperties]?: // | ThemeUICSSProperties[key]
keyof DripsyFinalTheme
} In this case, you can only use the dripsy theme keys. Ok cool. But when I add back import type { ThemeUICSSProperties } from '@theme-ui/css'
type SxProp = {
[key in keyof ThemeUICSSProperties]?:
| ThemeUICSSProperties[key]
| keyof DripsyFinalTheme
} It recognizes that a certain type is wrong, but it does not give suggestions: This is solved (I think) by adding the type SxProp = {
[key in keyof ThemeUICSSProperties]?:
| (ThemeUICSSProperties[key] & {})
| keyof DripsyFinalTheme
} Good start... |
Solved: type Tokenize<Theme> = Extract<
keyof {
[Key in Extract<keyof Theme, 'string'> as Theme[Key] extends
| string
| number
| ''
| never
| undefined
| null
? `${Key}`
: // if we're iterating over the key of the theme
// for example, if key = 'colors'
// and colors: { primary: '...' }
// then we should allow either colors.primary, OR colors
`${Key}.${Tokenize<Theme[Key]>}`]: true
},
string | number | '' | never | undefined | null
> |
Got rid of array keys: type HiddenArrayKeys = Exclude<keyof [], number>
type Tokenize<Theme> = Extract<
keyof {
[Key in Extract<keyof Theme, string | number> as Theme[Key] extends
| string
| number
| ''
| never
| undefined
| null
? Key extends HiddenArrayKeys
? `${number}`
: `${Key}`
: Theme[Key] extends undefined
? `${Key}`
: // if we're iterating over the key of the theme
// for example, if key = 'colors'
// and colors: { primary: '...' }
// then we should allow either colors.primary, OR colors
`${Key}.${Tokenize<Theme[Key]>}`]: true
},
string | number | '' | never | undefined | null
> |
Investigate if this is a better getter for dotted paths: https://github.com/system-ui/theme-ui/pull/1090/files#diff-7ef5a8c1a0ef5be9914c14678b6cf85955e354f070f14769ab856c495d3879a4R22 |
Bumps [tmpl](https://github.com/daaku/nodejs-tmpl) from 1.0.4 to 1.0.5. - [Release notes](https://github.com/daaku/nodejs-tmpl/releases) - [Commits](https://github.com/daaku/nodejs-tmpl/commits/v1.0.5) --- updated-dependencies: - dependency-name: tmpl dependency-type: indirect ... Signed-off-by: dependabot[bot] <support@github.com>
I published the first version of this at yarn add dripsy@canary |
Added many new updates to the readme, including all things related to v3 and upgrading. https://github.com/nandorojo/dripsy/tree/typez |
Exports scales and aliases for usage outside of dripsy
….0.5 Bump tmpl from 1.0.4 to 1.0.5
This is deployed at beatgig.com and battle tested. I'll do a full release on Tuesday. I'll be speaking at Next.js Conf about React Native + Next.js – don't miss it! |
Code.-.App.tsx.dripsy.mp4
Closes #6, #72, #123 and many other requests for improved types & intellisense for Dripsy.
Features / Improvements 🥸
DX 👨🏽💻
useDripsyTheme
sx
propgradient
andcolors
on@dripsy/gradient
useResponsiveValue(theme => [theme.colors.background])
useSx
sx
factory (sx={theme => ({ color: theme.colors.text })}
makeTheme
function to override default one with a custom theme@theme-ui/core
@theme-ui/css
for types onlyDripsyProvider
to use internal Dripsy context rather than Theme UI (BREAKING if you use thejsx
pragma in your app)styled
andcreateThemedComponent
themeKey
instyled
variant
andvariants
variant
only pick based on the specifiedthemeKey
backgroundColor
should only get tokens from thetheme.colors
. (Is this blocking? It could take a lot of effort. Not sure if it should be blocking)padding
can be$1
from the theme and1
, but not"1"
if that's not in the theme)""
as a style?Tokenize
is performant for large themesPerformance 🦦
sx
prop under the hoodGradient
memoizationFeatures 🛩
Pressable
's factorystyle={interaction => ({ ... })}
proptextShadows
to themeshadows
to theme with RN styletransform
tosx
propboxShadow
tosx
prop with intellisensetextShadow
tosx
prop with intellisenseUpgrade Guide
Install v3
yarn add dripsy@canary # if you use this package, upgrade it too yarn add @dripsy/gradient@canary
Versions
Make sure you have at least TypeScript 4.4+:
Add
makeTheme
All you have to do to upgrade is wrap your
theme
withmakeTheme
, and then use module declaration.You now get intellisense 🥳
Gotchas
If you don't see autocomplete, there could be a few reasons.
Possibility 1. Your theme uses non-strict objects:
To fix this, either use
as const
for colors, or write it inline:Still not getting intellisense?
If it still isn't working, please open an issue! But it should work now.
Strict Types
If you want to enforce strict types for your
sx
prop, you can do so with the newtheme.types
field:By setting
types.onlyAllowThemeValues
toalways
, you restrict yourself to only using theme values in yoursx
prop. While this may feel like overkill, it is a good pattern of enforcing consistent design.This will only apply to theme values that are set. For example, if you haven't set the
theme.space
property, then strict types won't enforce forpadding
,margin
, etc.Incremental strict types
It's possible you want to implement strict types on a per-scale basis. The
types.onlyAllowThemeValues
also accepts an object with per-scale definitions.Now, our
sx
prop's space-related properties (such as margin, padding, etc) will only accept one of the values intheme.space
. To take full advantage of this feature, it is recommended that you don't use arrays, and instead make a dictionary with$
prefixes, such as thespace
one above.Recommendation
The strict types feature is especially useful if you want to upgrade to Dripsy 3, have no breaking changes with your types, but slowly transition your app to have stricter types.
It also makes changing your theme much easier. For example, imagine that you change your
space
from an array to a dictionary:After changing your
theme.space
, you likely have hundreds of invalid styles throughout your app. Finding them all would be a mess.However, with incremental strict types, you could achieve this code refactor in seconds.
Now, simply run your TypeScript type-checker (
yarn tsc --noEmit
) to see all the places you need to update. You'll get useful errors like this:Enforce React Native types
default:
false
If you set this field to
true
, then you can only pass styles that fit a React Native style object.For example, on web, you can set
fontWeight
as a number, like so:fontWeight: 400
. With React Native, font weights must be strings (fontWeight: '400'
). Using a number here would probably work with dripsy if you've utilized thecustomFonts
feature in your theme.I recommend setting this field to
true
. However, it will default tofalse
to avoid breaking changes with users who are on v2 (like me) who don't want to refactor everywhere. If your app is just adding Dripsy, you should set this field totrue
. And it may work to set it totrue
either way. If it riddles your type checker with errors, then you can easily disable it.To clarify: when this is
false
, it will allow either theme-ui types for a given field, or React Native types. When it's set totrue
, it will only allow React Native types (if they exist.)Since React Native has no
cursor
property, for instance, using this field will always pull from the theme-ui web types.Breaking Changes
There are essentially no breaking changes.
If you are a very advanced user with a custom setup, this might be breaking for you:
Removed
@theme-ui/core
dependencytheme-ui
on web, you'll need to wrap your app withtheme-ui
'sThemeProvider
yourself. Previously, Dripsy used that provider under the hood.Removed
Button
component (just import it fromreact-native
instead ofdripsy
)Array values
If your theme had any array values, turn them into objects.Arrays in theme were added to
v3
!