I am using react-native-tvos to create an app.
I am trying to display SVG elements that respond to the remote.
I have tried using TouchableOpacity as well as Pressable on the elements.
Whenever I wrap the elements with those they no longer appear.
I've looked through dozens of S/O posts and have tried various things. Such as zIndex, flex on container. I also tried the react-native-gesture-handler, but that doesn't seem to work for tvos.
I've broken the code down to something very simple. Just a circle in the middle of the screen.
import Svg, {Circle} from 'react-native-svg';
import * as React from 'react';
import {TouchableOpacity, View,} from 'react-native';
const App = () => {
return (
<View>
<Svg x="0px" y="0px" viewBox="0 0 1920 1080" style="enable-background:new 0 0 1920 1080;">
<TouchableOpacity style={{
opacity: 1,
fill: "#FF0000",
stroke: "5",
zIndex: 100,
}} onPress={() => alert('PRESSED')}>
<Circle cx="960" cy="540" r="100" opacity="1" fill="#FF0000"/>
</TouchableOpacity>
</Svg>
</View>
);
};
export default App;
How to use expo vector icon in react native skia.
I want to use this icon,
<Ionicons name="md-checkmark-circle" size={32} color="green" /> in skia Canvas or Box
Thanks.
You can't use vector icons directly but you can add the icon as an SVG image like this:
import {
Canvas,
ImageSVG,
useSVG
} from "#shopify/react-native-skia";
const ImageSVGDemo = () => {
// Alternatively, you can pass an SVG URL directly
// for instance: const svg = useSVG("https://upload.wikimedia.org/wikipedia/commons/f/fd/Ghostscript_Tiger.svg");
const svg = useSVG(require("../../assets/checkmark.svg"));
return (
<Canvas style={{ flex: 1 }}>
{ svg && (
<ImageSVG
svg={svg}
x={0}
y={0}
width={256}
height={256}
/>)
}
</Canvas>
);
};
and the checkmark.svg file will be:
<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24"><path d="M12 0c-6.627 0-12 5.373-12 12s5.373 12 12 12 12-5.373 12-12-5.373-12-12-12zm-1.25 16.518l-4.5-4.319 1.396-1.435 3.078 2.937 6.105-6.218 1.421 1.409-7.5 7.626z"/></svg>
I have a component that generates a square linear gradient using react-native-svg. When I pass in different hue colors, it stays the same color.
Things I tried:
Passing in hex instead of hsl colors and the issue still arises
What am I missing?
Expo Snack: https://snack.expo.dev/#paulwongx/react-native-svg_color_stop_issue
Gradient.js
import * as React from 'react';
import Svg, { Defs, LinearGradient, Rect, Stop } from "react-native-svg";
export default function Gradient({hue}) {
return (
<Svg width={128} height={128} viewBox="0 0 24 24">
<Defs>
<LinearGradient id="gradient" x1="0%" y1="0%" x2="100%" y2="100%">
<Stop offset="0" stopColor={`hsl(${hue}, 100%, 74%)`} />
<Stop offset="1" stopColor={`hsl(${hue}, 100%, 55%)`} />
</LinearGradient>
</Defs>
<Rect width="100%" height="100%" fill="url(#gradient)" />
</Svg>
);
}
App.js
import * as React from 'react';
import { Text, View, StyleSheet } from 'react-native';
import Gradient from './Gradient';
export default function App() {
return (
<View style={{flexDirection: "row", flexWrap: "wrap"}}>
<Gradient hue={20} />
<Gradient hue={50} />
<Gradient hue={100} />
<Gradient hue={150} />
<Gradient hue={200} />
<Gradient hue={250} />
<Gradient hue={300} />
<Gradient hue={350} />
</View>
);
}
Output:
Looking at the rendered code within Inspect Element, the components show different hues but they all render the same colors.
// first component
<stop offset="0" stop-color="hsl(20, 100%, 74%)"></stop>
<stop offset="1" stop-color="hsl(20, 100%, 55%)"></stop>
// last component
<stop offset="0" stop-color="hsl(350, 100%, 74%)"></stop>
<stop offset="1" stop-color="hsl(350, 100%, 55%)"></stop>
I think you have to give a unique id to the linear gradient. The problem is that the id is always the same.
import * as React from 'react';
import Svg, { Defs, LinearGradient, Rect, Stop } from "react-native-svg";
export default function Gradient({hue, id}) {
return (
<Svg width={128} height={128} viewBox="0 0 24 24">
<Defs>
<LinearGradient id={`gradient_${id}`} x1="0%" y1="0%" x2="100%" y2="100%">
<Stop offset="0" stopColor={`hsl(${hue}, 100%, 74%)`} />
<Stop offset="1" stopColor={`hsl(${hue}, 100%, 55%)`} />
</LinearGradient>
</Defs>
<Rect width="100%" height="100%" fill={`url(#gradient_${id})`} />
</Svg>
);
}
And then
import * as React from 'react';
import { Text, View, StyleSheet } from 'react-native';
import Gradient from './Gradient';
export default function App() {
return (
<View style={{flexDirection: "row", flexWrap: "wrap"}}>
<Gradient hue={20} id="first" />
<Gradient hue={50} id="second" />
</View>
);
}
The error is: Element type is invalid: expected a string or a class/function but got number.
I did exactly same work two days ago. I got it run. But this time I couldnt.
I run these codes to get the icon run;
npm install react-native-svg --save
npm install react-native-svg-transformer --save
react-native link react-native-svg
Here is my App.js file
import React from 'react';
import { StyleSheet, Text, View, SafeAreaView } from 'react-native';
import Application from "./src/components/icons/application.svg"
const App = () => {
return (
<SafeAreaView style={styles.container}>
<View>
<Application height={30} width={22} fill={"#8c3bff"} style={{ backgroundColor: "#8c3bff" }} />
</View>
</SafeAreaView>
);
};
const styles = StyleSheet.create({
container: {
flex:1,
}
});
export default App;
this is application.svg , I thought this could work, but it doesnt.
<?xml version="1.0" encoding="iso-8859-1"?>
<!-- Generator: Adobe Illustrator 17.1.0, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<svg version="1.1" id="Capa_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 463 463" style="enable-background:new 0 0 463 463;" xml:space="preserve">
<g>
<path d="M175.5,0h-136C17.72,0,0,17.72,0,39.5v136C0,197.28,17.72,215,39.5,215h136c21.78,0,39.5-17.72,39.5-39.5v-136
C215,17.72,197.28,0,175.5,0z M200,175.5c0,13.509-10.991,24.5-24.5,24.5h-136C25.991,200,15,189.009,15,175.5v-136
C15,25.991,25.991,15,39.5,15h136c13.509,0,24.5,10.991,24.5,24.5V175.5z"/>
<path d="M423.5,0h-136C265.72,0,248,17.72,248,39.5v136c0,21.78,17.72,39.5,39.5,39.5h136c21.78,0,39.5-17.72,39.5-39.5v-136
C463,17.72,445.28,0,423.5,0z M448,175.5c0,13.509-10.991,24.5-24.5,24.5h-136c-13.509,0-24.5-10.991-24.5-24.5v-136
c0-13.509,10.991-24.5,24.5-24.5h136c13.509,0,24.5,10.991,24.5,24.5V175.5z"/>
<path d="M175.5,248h-136C17.72,248,0,265.72,0,287.5v136C0,445.28,17.72,463,39.5,463h136c21.78,0,39.5-17.72,39.5-39.5v-136
C215,265.72,197.28,248,175.5,248z M200,423.5c0,13.509-10.991,24.5-24.5,24.5h-136C25.991,448,15,437.009,15,423.5v-136
c0-13.509,10.991-24.5,24.5-24.5h136c13.509,0,24.5,10.991,24.5,24.5V423.5z"/>
<path d="M423.5,248h-136c-21.78,0-39.5,17.72-39.5,39.5v136c0,21.78,17.72,39.5,39.5,39.5h136c21.78,0,39.5-17.72,39.5-39.5v-136
C463,265.72,445.28,248,423.5,248z M448,423.5c0,13.509-10.991,24.5-24.5,24.5h-136c-13.509,0-24.5-10.991-24.5-24.5v-136
c0-13.509,10.991-24.5,24.5-24.5h136c13.509,0,24.5,10.991,24.5,24.5V423.5z"/>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
</svg>
What could I be doing wrong?
Found the solution.
We should add this code in metro.config.js, then it works.
const { getDefaultConfig } = require("metro-config");
module.exports = (async () => {
const {
resolver: { sourceExts, assetExts }
} = await getDefaultConfig();
return {
transformer: {
babelTransformerPath: require.resolve("react-native-svg-transformer")
},
resolver: {
assetExts: assetExts.filter(ext => ext !== "svg"),
sourceExts: [...sourceExts, "svg"]
}
};
})();
I have a requirement to display the polygon on the Map as follows
Can anyone suggest me if there is a way to do that ?
I managed to display using react-native-svg elements inside Marker
import * as React from "react";
import { Marker} from "react-native-maps";
import Svg, { Circle, Rect } from "react-native-svg";
export default function SvgComponent(props) {
const {
coordinate,
} = props;
return (
<Marker coordinate={coordinate} pinColor={pinColor}>
<Svg height="10" width="20" viewBox="0 0 100 100">
<Circle cx="50" cy="50" r="45" stroke="blue" fill="green" />
</Svg>
</Marker>
);
}