Huge News!Announcing our $40M Series B led by Abstract Ventures.Learn More
Socket
Sign inDemoInstall
Socket

perfect-arrows

Package Overview
Dependencies
Maintainers
1
Versions
12
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

perfect-arrows

Draw perfect arrows between points or shapes

  • 0.3.7
  • latest
  • Source
  • npm
  • Socket score

Version published
Weekly downloads
6.1K
increased by15.77%
Maintainers
1
Weekly downloads
 
Created
Source

Perfect Arrows

A set of functions for drawing perfect arrows between points and shapes.

Example

👉 Demo

Edit example

Other languages

Português (pt-BR)

Installation

npm i perfect-arrows

or

yarn add perfect-arrows

Usage

The functions in this library provide only the information needed to draw an arrow. You'll need to draw the arrow yourself using your technology of choice. See below for an example React component with SVG.

getArrow(x0, y0, x1, y1, options)

The getArrow function accepts the position of two points and returns an array containing information for:

  • three points: a start, end, and control point
  • three angles: an end, start, and center

You can use this information to draw an arc and arrow-heads. You can use the options object to tweak the return values.

const arrow = getArrow(0, 0, 100, 200, {
  bow: 0,
  stretch: 0.5,
  stretchMin: 0,
  stretchMax: 420,
  padStart: 0,
  padEnd: 0,
  flip: false,
  straights: true,
})

const [sx, sy, cx, cy, ex, ey, ae, as, sc] = arrow
Arguments
ArgumentTypeDescription
x0numberThe x position of the starting point.
y0numberThe y position of the starting point.
x1numberThe x position of the ending point.
y1numberThe y position of the ending point.
optionsobjectAn (optional) object containing one or more of the options described below.
Options
OptionTypeDefaultDescription
bownumber0A value representing the natural bow of the arrow. At 0, all lines will be straight.
stretchnumber.5The effect that the arrow's length will have, relative to its minStretch and maxStretch, on the bow of the arrow. At 0, the stretch will have no effect.
minStretchnumber0The length of the arrow where the line should be most stretched. Shorter distances than this will have no additional effect on the bow of the arrow.
maxStretchnumber420The length of the arrow at which the stretch should have no effect.
padStartnumber0How far the arrow's starting point should be from the provided start point.
padEndnumber0How far the arrow's ending point should be from the provided end point.
flipbooleanfalseWhether to reflect the arrow's bow angle.
straightsbooleantrueWhether to use straight lines at 45 degree angles.
Returns
ArgumentTypeDescription
x0numberThe x position of the (padded) starting point.
y0numberThe y position of the (padded) starting point.
x1numberThe x position of the (padded) ending point.
y1numberThe y position of the (padded) ending point.
aenumberThe angle (in radians) for an ending arrowhead.
asnumberThe angle (in radians) for a starting arrowhead.
acnumberThe angle (in radians) for a center arrowhead.

Example: A React Arrow Component

import * as React from "react"
import { getArrow } from "perfect-arrows"

export function PerfectArrow() {
  const p1 = { x: 64, y: 64 }
  const p2 = { x: 128, y: 96 }

  const arrow = getArrow(p1.x, p1.y, p2.x, p2.y, {
    padEnd: 20,
  })

  const [sx, sy, cx, cy, ex, ey, ae, as, ec] = arrow

  const endAngleAsDegrees = ae * (180 / Math.PI)

  return (
    <svg
      viewBox="0 0 720 480"
      style={{ width: 720, height: 480 }}
      stroke="#000"
      fill="#000"
      strokeWidth={3}
    >
      <circle cx={sx} cy={sy} r={4} />
      <path d={`M${sx},${sy} Q${cx},${cy} ${ex},${ey}`} fill="none" />
      <polygon
        points="0,-6 12,0, 0,6"
        transform={`translate(${ex},${ey}) rotate(${endAngleAsDegrees})`}
      />
    </svg>
  )
}

getBoxToBoxArrow(x0, y0, w0, h0, x1, y1, w1, h1, options)

The getBoxToBoxArrow function accepts the position and dimensions of two boxes (or rectangles) and returns an array containing information for:

  • three points: a start, end, and control point
  • three angles: an end, start, and center

You can use this information to draw an arc and arrow-heads. You can use the options object to tweak the return values.

Note: The options and values returned by getBoxToBoxArrow are in the same format as the options and values for getArrow.

const arrow = getBoxToBoxArrow(0, 0, 96, 128, 400, 200, 128, 96, {
  bow: 0,
  stretch: 0.5,
  stretchMin: 0,
  stretchMax: 420,
  padStart: 0,
  padEnd: 0,
  flip: false,
  straights: true,
})

const [sx, sy, cx, cy, ex, ey, ae, as, sc] = arrow
Arguments
ArgumentTypeDescription
x0numberThe x position of the first rectangle.
y0numberThe y position of the first rectangle.
w0numberThe width of the first rectangle.
h0numberThe height of the first rectangle.
x1numberThe x position of the second rectangle.
y1numberThe y position of the second rectangle.
w1numberThe width of the second rectangle.
h1numberThe height of the second rectangle.
optionsobjectAn (optional) object containing one or more of the options described below.
Options

See options in getArrow above. (Both functions use the same options object.)

Returns

See returns in getArrow above. (Both functions return the same set of values.)

Example: A React Box-to-box Arrow Component

import * as React from "react"
import { getBoxToBoxArrow } from "perfect-arrows"

export function PerfectArrow() {
  const p1 = { x: 64, y: 64, w: 64, h: 64 }
  const p2 = { x: 128, y: 96, w: 64, h: 64 }

  const arrow = getBoxToBoxArrow(
    p1.x,
    p1.y,
    p1.w,
    p1.h,
    p2.x,
    p2.y,
    p2.w,
    p2.h,
    {
      bow: 0.2,
      stretch: 0.5,
      stretchMin: 40,
      stretchMax: 420,
      padStart: 0,
      padEnd: 20,
      flip: false,
      straights: true,
    }
  )

  const [sx, sy, cx, cy, ex, ey, ae, as, ec] = arrow

  const endAngleAsDegrees = ae * (180 / Math.PI)

  return (
    <svg
      viewBox="0 0 1280 720"
      style={{ width: 1280, height: 720 }}
      stroke="#000"
      fill="#000"
      strokeWidth={3}
    >
      <circle cx={sx} cy={sy} r={4} />
      <path d={`M${sx},${sy} Q${cx},${cy} ${ex},${ey}`} fill="none" />
      <polygon
        points="0,-6 12,0, 0,6"
        transform={`translate(${ex},${ey}) rotate(${endAngleAsDegrees})`}
      />
    </svg>
  )
}

Author

@steveruizok

Keywords

FAQs

Package last updated on 28 Sep 2021

Did you know?

Socket

Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.

Install

Related posts

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc