can't get to work NativeWind for Expo Mobile and Web

Hi, I've been trying the whole day to achieve this. I've installed NativeWind, followed the guide (https://www.nativewind.dev/quick-starts/expo) and it worked for mobile but not for web. So, after playing a while with webpack and postcss, I managed to get it work, but then it stopped working for mobile.
import { StatusBar } from "expo-status-bar";
import { Text, View } from "react-native";

/* import "./style.css"; */

export default function App() {
return (
<View className="flex-1 items-center justify-center bg-white">
<Text className="text-red-600 text-2xl">Tailwind is up now! :D</Text>
<StatusBar style="auto" />
</View>
);
}
import { StatusBar } from "expo-status-bar";
import { Text, View } from "react-native";

/* import "./style.css"; */

export default function App() {
return (
<View className="flex-1 items-center justify-center bg-white">
<Text className="text-red-600 text-2xl">Tailwind is up now! :D</Text>
<StatusBar style="auto" />
</View>
);
}
If I import the stylesheet, it works for web but not for mobile. If I don't, it works the other way around (i think). Adding
NativeWindStyleSheet.setOutput({ default: "native" });
NativeWindStyleSheet.setOutput({ default: "native" });
solved the problem, but this is a workaround for Expo SDK <=45, as stated in the docs. I'd love to make it work the intended way
Expo | NativeWind
A example of an Expo project can be found on Github
3 Replies
Gus
Gus16mo ago
package.json
{
"name": "sticker-smash",
"version": "1.0.0",
"main": "node_modules/expo/AppEntry.js",
"scripts": {
"start": "expo start",
"android": "expo start --android",
"ios": "expo start --ios",
"web": "expo start --web"
},
"dependencies": {
"expo": "48.0.18",
"expo-status-bar": "~1.4.4",
"nativewind": "^2.0.11",
"react": "18.2.0",
"react-dom": "18.2.0",
"react-native": "0.71.8",
"react-native-web": "~0.18.10"
},
"devDependencies": {
"@babel/core": "^7.20.0",
"@expo/webpack-config": "^18.1.1",
"autoprefixer": "^10.4.14",
"postcss": "^8.4.25",
"postcss-loader": "^4.2.0",
"tailwindcss": "^3.3.2"
},
"private": true
}
{
"name": "sticker-smash",
"version": "1.0.0",
"main": "node_modules/expo/AppEntry.js",
"scripts": {
"start": "expo start",
"android": "expo start --android",
"ios": "expo start --ios",
"web": "expo start --web"
},
"dependencies": {
"expo": "48.0.18",
"expo-status-bar": "~1.4.4",
"nativewind": "^2.0.11",
"react": "18.2.0",
"react-dom": "18.2.0",
"react-native": "0.71.8",
"react-native-web": "~0.18.10"
},
"devDependencies": {
"@babel/core": "^7.20.0",
"@expo/webpack-config": "^18.1.1",
"autoprefixer": "^10.4.14",
"postcss": "^8.4.25",
"postcss-loader": "^4.2.0",
"tailwindcss": "^3.3.2"
},
"private": true
}
babel.config.js
module.exports = function(api) {
api.cache(true);
return {
presets: ['babel-preset-expo'],
plugins: ["nativewind/babel"],
};
};
module.exports = function(api) {
api.cache(true);
return {
presets: ['babel-preset-expo'],
plugins: ["nativewind/babel"],
};
};
postcss.config.js
module.exports = {
plugins: [require("tailwindcss"), require("autoprefixer"), [require("nativewind/postcss")]],
};
module.exports = {
plugins: [require("tailwindcss"), require("autoprefixer"), [require("nativewind/postcss")]],
};
tailwind.config.js
/** @type {import('tailwindcss').Config} */

const nativeWind = require("nativewind/tailwind/css");

module.exports = {
content: ["./App.{js,jsx,ts,tsx}", "./src/**/*.{js,jsx,ts,tsx}"],
theme: {
extend: {},
},
plugins: [nativeWind],
};
/** @type {import('tailwindcss').Config} */

const nativeWind = require("nativewind/tailwind/css");

module.exports = {
content: ["./App.{js,jsx,ts,tsx}", "./src/**/*.{js,jsx,ts,tsx}"],
theme: {
extend: {},
},
plugins: [nativeWind],
};
webpack.config.js
const createExpoWebpackConfigAsync = require("@expo/webpack-config");

module.exports = async function (env, argv) {
const config = await createExpoWebpackConfigAsync(
{
...env,
babel: {
dangerouslyAddModulePathsToTranspile: ["nativewind"],
},
},
argv
);

config.module.rules.push({
test: /\.css$/i,
use: ["postcss-loader"],
});

return config;
};
const createExpoWebpackConfigAsync = require("@expo/webpack-config");

module.exports = async function (env, argv) {
const config = await createExpoWebpackConfigAsync(
{
...env,
babel: {
dangerouslyAddModulePathsToTranspile: ["nativewind"],
},
},
argv
);

config.module.rules.push({
test: /\.css$/i,
use: ["postcss-loader"],
});

return config;
};
style.css
@tailwind base;
@tailwind components;
@tailwind utilities;
@tailwind base;
@tailwind components;
@tailwind utilities;
App.js (final version)
import { StatusBar } from "expo-status-bar";
import { NativeWindStyleSheet } from "nativewind";
import { Text, View } from "react-native";

/* import "./style.css"; */

NativeWindStyleSheet.setOutput({ default: "native" });

export default function App() {
return (
<View className="flex-1 items-center justify-center bg-white">
<Text className="text-red-600 text-2xl">Tailwind should be up now! :D</Text>
<StatusBar style="auto" />
</View>
);
}
import { StatusBar } from "expo-status-bar";
import { NativeWindStyleSheet } from "nativewind";
import { Text, View } from "react-native";

/* import "./style.css"; */

NativeWindStyleSheet.setOutput({ default: "native" });

export default function App() {
return (
<View className="flex-1 items-center justify-center bg-white">
<Text className="text-red-600 text-2xl">Tailwind should be up now! :D</Text>
<StatusBar style="auto" />
</View>
);
}
If I can share something more, please tell me, I've been thinking about it all day long and I can't figure it out
oadster
oadster16mo ago
I would honestly just not use web for this and stick to mobile make a seperate nextjs site for web
Gus
Gus16mo ago
That would be a nice suggestion actually, but it seems weird that it doesn't work like it's supposed to...
Want results from more Discord servers?
Add your server