Giter Site home page Giter Site logo

benjeau / react-native-draw Goto Github PK

View Code? Open in Web Editor NEW
124.0 124.0 41.0 7.94 MB

SVG based data-driven React Native drawing component 🎨

Home Page: https://www.npmjs.com/package/@benjeau/react-native-draw

License: MIT License

JavaScript 5.90% TypeScript 93.89% Shell 0.21%
drawing react-native react-native-svg

react-native-draw's People

Contributors

asurare avatar benjeau avatar dependabot[bot] avatar gfringeli avatar jimbrocato avatar kdh0324 avatar ping203 avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar

react-native-draw's Issues

Move to Gesture API introduced with react-native-gesture-handler 2

Currently, the gestures are handled using an older react-native-gesture-handler (RNGH) API, i.e. PanGestureHandler. Moving to the new Gesture API introduced with react-native-gesture-handler 2 would remove a warning notification popping up in the React Native app during development.
In addition, in order to be able to use the old API when having installed version 2 of RNGH in some cases requires to add the line

import 'react-native-gesture-handler';

at very beginning of index.js of a React Native project. There does not seem agreement in the community about the extent and the source of this issue. But using the new API resolved the issue in my case.

More ref methods (replacePaths, addPaths)

Is your feature request related to a problem?

No response

Desired solution (feature)

Should have all the necessary ref methods to properly control the canvas

Alternatives considered

No response

Anything else?

No response

Able to draw out of height and width

On what kind of device are you using this library?

  • Android
  • iOS
  • Web

Environment

- OS: macOS Ventura
- react-native: 0.70.4
- @benjeau/react-native-draw: 0.8.3
- @benjeau/react-native-draw-extras: 0.2.2

Current Behavior

I'm developing an app for drawing above an image, I have restricted the canvas height and width but I can draw more than the specified height and width.

Code:

<View style={{ height: '60%, width: '100%', paddingHorizontal: 16 }}>
            <FastImage
                style={{ height: '100%', width: '100%' }}
                source={{ uri: image.uri }}
                resizeMode={FastImage.resizeMode.contain}
            />

            <Canvas
                enabled={isEditing}
                ref={canvasRef}
                style={{ position: 'absolute', top: 0, bottom: 0, left: 0, right: 0, backgroundColor: 'transparent' }}
                color={color}
                thickness={thickness}
                opacity={opacity}
                tool={DrawingTool.Brush}
                onPathsChange={setPaths}
            />
</View>

Sample Video:

Screen.Recording.2023-03-22.at.6.09.55.PM.mov

Expected Behavior

I should be able to restrict drawing height to the view's height and width. I need something like this UI part I can take care. Just that drawing part alone I'm facing issues.

RPReplay_Final1679923703.MP4

Steps To Reproduce

You can check my above code in the current behavior section.

Anything else?

No response

Slow performance when holding stroke for a long time

On what kind of device are you using this library?

  • Android
  • iOS
  • Web

Environment

- OS: archlinux 5.17.4
- react-native: 0.64.3
- expo: 44.0.0
- @benjeau/react-native-draw: 0.8.1
- react-native-gesture-handler: 2.1.0
- react-native-svg: 12.1.1

Current Behavior

When holding more than 2 seconds a stroke, it's drawing with delay and slow performance

demo

Expected Behavior

No delay when holding for a longtime a stroke

Steps To Reproduce

Problem appear with the minimal example:

return (
  <View style={{flex: 1, height: "100%", width: "100%"}}>
    <Canvas style={{backgroundColor: "green"}}/>
  </View>
)

Anything else?

No response

VSCode is unable to find types

On what kind of device are you using this library?

  • Android
  • iOS
  • Web

Environment

- OS:Window 10
- react-native: 0.68.2
- @benjeau/react-native-draw: 0.8.1
- react: 17.0.2
- @types/react-native: 0.67.3
- typescript: 4.4.4
- @babel/core: 7.12.9

Current Behavior

image

Expected Behavior

should be able to find a declaration file for module.

Steps To Reproduce

import CanvasRef in Typescript React Native Project with environment given above.

Anything else?

Seems Typescript can't find declaration file in the module.
Is't this project meant to be used in typescripts based projects?
(I've solved my issue by declaring the interfaces that I need. But definitely there's a better way to solve it)

Opacity overlay does not respect border radius of canvas

When passing custom styling to the canvas, the overlay used when selecting a color or changing the properties of the brush does not behave correctly.

E.g. here with borderRadius set, the overlay should respect that borderRadius too
image

Bezier curves

Is your feature request related to a problem?

No response

Desired solution (feature)

I'm not sure if the program already does this, but it would be nice to have bezier curve conversion.

Alternatives considered

No response

Anything else?

No response

Canvas Prop for shouldCancelWhenOutside

Is your feature request related to a problem?

First of all, thanks for making this nice library!

I noticed that when your finger moves outside the canvas while drawing, the drawing stops. For some use cases that is quite annoying, especially when the user wants to draw near the edges.

Desired solution (feature)

The Canvas component should have a prop to tell whether the touch should be persisted when moving outside the Canvas or not. Something like:

<Canvas
   color={"#000"}
   thickness={20}
   opacity={1}
   shouldCancelWhenOutside={false}
/>

In Canvas.tsx i noticed a property ".shouldCancelWhenOutside(true)" which is hardcoded to true. Changing this to false seems to solve the problem. Would be nice to have this property controllable via the Canvas prop.

Alternatives considered

No response

Anything else?

No response

Unable to draw anything on Canvas.

On what kind of device are you using this library?

  • Android
  • iOS
  • Web

Environment

- OS:macOS (Monterey)
- react-native:0.66.0
- @benjeau/react-native-draw:0.7.0

Current Behavior

I have followed every installation steps mentioned in the docs, still not been able to draw anything on the canvas.
Everytime i start dragging to draw a shape or line it shows me a dot where i start to drag from and then the dot vanishes.

I have also put gesture handler import on top or app.js and index.js.

@BenJeau can you help me out ?

screen-20220726-064108.mp4

Expected Behavior

I need to be able to draw on Canvas.

Steps To Reproduce

I just simple installed the package following the documentation and sarted the project from the example project.
That's all.

Anything else?

Here is my Component :

import React, {useRef, useState} from 'react';
import {Animated, StyleSheet, View} from 'react-native';
import {Canvas, CanvasRef, DrawingTool} from '@benjeau/react-native-draw';

import {
BrushProperties,
CanvasControls,
DEFAULT_COLORS,
} from '@benjeau/react-native-draw-extras';
import {height, SIZES, width} from '../constants';

export default React.forwardRef((props, ref) => {
// const canvasRef = useRef(null);
console.log('props ======= >>>>>> ', props);
const [color, setColor] = useState(DEFAULT_COLORS[0][0][0]);
const [thickness, setThickness] = useState(5);
const [opacity, setOpacity] = useState(1);
const [tool, setTool] = useState(DrawingTool.Brush);
const [visibleBrushProperties, setVisibleBrushProperties] = useState(false);

const handleUndo = () => {
ref.current?.undo();
};

const handleClear = () => {
ref.current?.clear();
};

const handleToggleEraser = () => {
setTool(prev =>
prev === DrawingTool.Brush ? DrawingTool.Eraser : DrawingTool.Brush,
);
};

const [overlayOpacity] = useState(new Animated.Value(0));

const handleToggleBrushProperties = () => {
if (!visibleBrushProperties) {
setVisibleBrushProperties(true);

  Animated.timing(overlayOpacity, {
    toValue: 1,
    duration: 350,
    useNativeDriver: true,
  }).start();
} else {
  Animated.timing(overlayOpacity, {
    toValue: 0,
    duration: 350,
    useNativeDriver: true,
  }).start(() => {
    setVisibleBrushProperties(false);
  });
}

};

return (
<>
<Canvas
ref={ref}
height={height * 0.8}
width={width * 0.97}
color={color}
thickness={thickness}
opacity={opacity}
tool={tool}
style={{
borderBottomWidth: StyleSheet.hairlineWidth,
borderColor: '#ccc',
alignSelf: 'center',
}}
/>

{!props.toolsVisible && (
<CanvasControls
onUndo={handleUndo}
onClear={handleClear}
onToggleEraser={handleToggleEraser}
onToggleBrushProperties={handleToggleBrushProperties}
tool={tool}
color={color}
opacity={opacity}
thickness={thickness}
buttonStyle={{elevation: 0}}
/>
)}
{!props.toolsVisible && visibleBrushProperties && (
<BrushProperties
color={color}
thickness={thickness}
opacity={opacity}
onColorChange={setColor}
onThicknessChange={setThickness}
onOpacityChange={setOpacity}
style={{
position: 'absolute',
bottom: 80,
left: 0,
right: 0,
padding: SIZES.fifteen,
backgroundColor: '#15',
borderTopEndRadius: SIZES.fifteen,
borderTopStartRadius: SIZES.fifteen,
paddingTop: SIZES.twenty,
borderWidth: StyleSheet.hairlineWidth,
borderBottomWidth: 0,
borderTopColor: '#ccc',
opacity: overlayOpacity,
}}
/>
)}

</>
);
});

Be able to draw single dots

Is your feature request related to a problem?

Right now when drawing dots (so just tapping the canvas), it will create a simplified line between those dots, and continue drawing this path with every new tap on the canvas.

Desired solution (feature)

It should be possible to draw dots, so every tap on the canvas should create a dot.

Alternatives considered

There is this closed issue #5 but it seems like it is not solved yet. I also tried screwing around in react-natuve-draw/src/utils.ts , but i was not able to get it working. Would appreciate any help! :)

Anything else?

No response

Add rudimentary layering support

It would be nice to have a layer system built into the Canvas which would allow the following examples to work:

  • Have a "highlighter" on top on every other strokes
  • Creating a sophisticated drawing app
  • Integrating drawing in a game (multi-user drawing, ...)

Implementation

This should be rather simple.

  1. The Canvas should have a prop specifying the layer, for simplicity, it would be a number, similar to how z-index works. The default would be 0.
  2. In the renderer, we would concatenate all the paths and the depth will simply come from the inherent order of the paths and nothing else needs to be done (the only
  3. PathType would have a layer attribute OR the paths should be grouped together in the same array (the first may be better for the end user, but the second one would make it simpler for the renderer and possibly more performant - worst case, there could be a conversion made from the second to the first one)
[paths]

OR

{
  0: [pathsOfLayer0],
  1: [pathsOfLayer1]
}

Webview as a possible Canvas

Is your feature request related to a problem?

No response

Desired solution (feature)

Add WebView as a possible Canvas implementation, this should be better than drawing SVGs for the web and would maybe be better for some type of mobile devices

Alternatives considered

No response

Anything else?

No response

Combine paths if strokes have same properties (except for the d attribute)

getSvg() function returns multiple path with d attrtibute. @BenJeau Is there any functionality to make only one path with d attribute ??
example
Right Now
<svg xmlns="http://www.w3.org/2000/svg" width="200" height="200" viewBox="0 0 200 200"><path d="M39,176c0,-21 11,-40 19,-59c8,-20 18,-39 27,-59c3,-7 20,-56 24,-42c8,26 11,51 16,77c3,15 15,45 15,63" stroke="#457429" stroke-width="3" opacity="1" stroke-linecap="round" stroke-linejoin="round" fill="none"/><path d="M67,91c-1,2 4,3 7,3c17,3 33,4 50,4" stroke="#457429" stroke-width="3" opacity="1" stroke-linecap="round" stroke-linejoin="round" fill="none"/></svg>

Expected
<svg xmlns="http://www.w3.org/2000/svg" width="200" height="200" viewBox="0 0 200 200"><path d="M39,176c0,-21 11,-40 19,-59c8,-20 18,-39 27,-59c3,-7 20,-56 24,-42c8,26 11,51 16,77c3,15 15,45 15,63 M67,91c-1,2 4,3 7,3c17,3 33,4 50,4" stroke="#457429" stroke-width="3" opacity="1" stroke-linecap="round" stroke-linejoin="round" fill="none"/></svg>

Create an eraser

Since this component is based on data/paths, the conventional eraser would not work (in the sense to erase a certain part of a "path"), but could remove the paths that intercept the touch of the eraser.

Features

Hi,

looks great so far. Some ideas:

  • Be able to add stickers (or images).
    Make them scalable (pinch, rotate etc)

  • be able to add multiple Text fields (maybe with color, scaling, rotating etc).

I’ve tried something similar like this before in the past but wasn’t really happy with my feature set and results , but your current development looks pretty neat

Modify lines

Is your feature request related to a problem?

No response

Desired solution (feature)

Hello!
Currently, I'm using your library and really appreciate making such a nice library.
This library is almost useful, but I think it would be better if I could adjust handwritten lines to straight lines like the iOS memo App.
I'm sorry for my poor English.
Thanks.

Alternatives considered

No response

Anything else?

No response

Be able to draw dots

I think this is related to my implementation of creating the SVG path strings, in the following function

export const createSVGPath = (path: PathDataType) => {
return path.reduce((acc, point, index) => {
let letter = 'L';
if (index === 0) letter = 'M';
return `${acc}${letter} ${point[0]},${point[1]} `;
}, '');

I could either

  • modify this function to cover edge cases
  • implement #2 with a way that takes this in mind

Lock the canvas

Is your feature request related to a problem?

No response

Desired solution (feature)

Hello!
I very much appreciate you publishing such a useful library.
This library is almost perfect. But I think it would be better if I could lock the canvas and forbid editing.
Thanks.

Alternatives considered

No response

Anything else?

No response

Refactor code in Draw component

Create a separation in the Draw component where users can

  • Create a canvas component that has no color picker / brush properties

Support more customization

Allows customization such as:

  • custom canvas size
  • option to remove bottom part
  • disable features
    • opacity
    • width
    • color picker
    • undo
    • delete

Remove @react-native-community/slider dependency

Remove @react-native-community/slider dependency by allowing users to provide their own "slider" or way to change opacity and thickness, via a component passed as a prop or with callbacks. This would make the library more lightweight

Support reanimated

Is your feature request related to a problem?

This library currently conflicts with react-native-reanimated@2 or [email protected] showing the error tried to synchronously call function from a different thread

Desired solution (feature)

Mark functions like addPointToPath as a worklet or wrap it using runOnJS

Alternatives considered

No response

Anything else?

https://docs.swmansion.com/react-native-gesture-handler/docs/2.3.0/api/gestures/base-gesture-config/#runonjsvalue-boolean

Generate IDs for paths for better performance

This is not currently a problem, but with #46, if this is not implemented, it will become a problem since the keys for SVG paths is simply the index, and it will not be linear like it is right now once layering is implemented.

Implementation

Generate a random ID and add it to the path:

  • UUID, but this would required extra dependencies (probable what should be done (would require uuid and react-native-get-random-values
  • Current time (most simple), but if multiple people "draw" on the same Canvas, there would be collisions
  • The path itself, but there may a problem if it happens that the user draw the exactly same path

Support multiple brushes

Allow for different predefined pens/brushes. They would have a static values for its properties, such as opacity, size... And they should be in different "layers" (e.g. make the brush strokes of a brush be on top or on the bottom of the others)

Unable to draw on iOS build, works locally on Expo

On what kind of device are you using this library?

  • Android
  • iOS
  • Web

Environment

- OS: iOS 17.0.3
- react-native: 0.71.13
- expo: 48.0.18
- @benjeau/react-native-draw: 0.8.3
- @luncheon/simplify-svg-path: 0.2.0
- react-native-gesture-handler: 2.9.0

Current Behavior

Drawing works when my app is tested using Expo Go, but once it is built to iOS, nothing seems to happen. It's not an issue with react-native-svg, as svgs are still rendering.

Expected Behavior

I should be able to draw.

Steps To Reproduce

  1. If you're using React Native Navigation, set up a new Stack.Screen with the following code (if not, just put it into App):
const WelcomeScreen = ({ navigation }) => {
  const canvasRef = useRef()
  return (
    <Canvas
      style={{ flex: 1 }}
      ref={canvasRef}
      thickness={8}
      tool={'brush'}
    />
  )
}
  1. eas build -p ios then test with TestFlight

Anything else?

No response

Reexport `createSVGPath` from utils

I am saving just coordinates of draw. When I want to show original drawing(pass initialValues.paths), it is not possible just passing there coordinates(and color, thickness,...), it is required pass also path as SVG string. This SVG string is internally generated when drawing by function in utils createSVGPath.

It would be good to reexport this function so it can be used for generating SVG path, or add method for generate drawing just from coordinates without SVG path variable(call createSVGPath internally).

Now I am importing this function directly with import { createSVGPath } from "../node_modules/@benjeau/react-native-draw/src/utils"; which is not ideal

Function which return bitmap image in base64 format.

Is your feature request related to a problem?

No response

Desired solution (feature)

I am able to convert the svg into base64 but I need a bitmap image as a base64 format.

Alternatives considered

No response

Anything else?

No response

Cannot draw even following every instruction

On what kind of device are you using this library?

  • Android
  • iOS
  • Web

Environment

- OS: IOS 15.5
- react-native: 0.66.3
- @benjeau/react-native-draw: 0.8.3

Current Behavior

Cannot draw on the Canvas and keep on getting the error: [ReferenceError: Can't find variable: t] for each touch events.

Screenshot 2022-05-24 at 2 15 27 PM

Expected Behavior

be able to draw

Steps To Reproduce

  1. set up new typescript RN template
    npx react-native init draw --template [email protected]

  2. install all the dependences
    npm i react-native-gesture-handler react-native-svg @benjeau/react-native-draw

  3. install pod
    cd ios && pod install && cd ..

  4. add <GestureHandlerRootView> wrapper at App.tsx

  5. import "react-native-gesture-handler" in both App.tsx and index.js

  6. modifiy App.tsx so that it matches the example

  7. npm run ios

Anything else?

I have been reading all the documents again and again and I believe I followed every instructions.
I even tried going to the example package.json to copy all the dependencies and versions but that error still occurs.

Please help

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.