png2svg

package module
v0.0.0-...-75d5f75 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Dec 8, 2022 License: BSD-3-Clause Imports: 11 Imported by: 0

README

png2svg Build GoDoc Go Report Card

Go module and command line utility for converting small PNG images to SVG Tiny 1.2.

Features and limitations

  • Draws rectangles for each region in the PNG image that can be covered by a rectangle.
  • The remaining pixels are drawn with a rectangle for each pixel.
  • This is not an efficient representation of PNG images!
  • The conversion may be useful if you have a small PNG image or icons at sizes around 32x32, and wish to scale them up and print them out without artifacts.
  • The utility is fast for small images, but larger images will take an unreasonable amount of time to convert, creating SVG files many megabytes in size. This could potentially also be used for benchmarking the single-core performance of a CPU.
  • The resulting SVG images can be opened directly in a browser like Firefox or Chromium, and may look sharper and crisper than small PNG or JPEG images that are smoothed/blurred by the browser, by default (this can be configured with CSS, though).
  • The default crispiness of how SVG images are displayed may be useful for displaying "pixel art" style graphics in the browser.
  • Written in pure Go, with no runtime dependencies on any external library or utility.
  • Handles transparent PNG images by not drawing SVG elements for the transparent regions.
  • For creating SVG images that draws a rectangle for each and every pixel, instead of also using larger rectangles, use the -p flag.

Image Comparison

192x192 PNG image (16 colors) 192x192 SVG image (16 colors) 192x192 SVG image (optimized with svgo)
5.7 KiB 187 KiB 61 KiB
png svg svgopt

The spaceships are drawn by wuhu (CC-BY 3.0).

Try zooming in on the images. Most browsers will keep the SVG image crisp when zooming in, but blur the PNG image.

For keeping PNG images crisp, this CSS can be used, but this is not normally needed for SVG images:

image-rendering: -moz-crisp-edges; /* Firefox */
image-rendering: -o-crisp-edges; /* Opera */
image-rendering: -webkit-optimize-contrast; /* Webkit (non-standard naming) */
image-rendering: crisp-edges;
-ms-interpolation-mode: nearest-neighbor; /* IE (non-standard property) */

Right now, Chrome does not support image-rendering: crisp-edges, while Firefox does not support image-rendering: pixelated. This may change over time, check out the excellent caniuse.com page.

Using SVG to get crisp images has the advantage of not relying on CSS that may differ from browser to browser.

Other comparisons:

302x240 PNG image 302x240 SVG image (limited to 4096 colors) 302x240 SVG (optimized with svgo)
171 KiB 3.0 MiB 911 KiB
png svg svgopt

The rainforest image is from Wikipedia.

64x64 PNG image 64x64 SVG image (one rectangle per pixel) 64x64 SVG image (4096 colors) 64x64 SVG image (rectangles >1px are colored pink) 64x64 SVG image (optimized with svgo)
2.3 KiB 167 KiB 69 KiB 22 KiB
png svgpixel svg4096 svgpink svgopt

The Glenda bunny is from 9p.io.

Q&A

Q: Why 4096 colors?
A: Because representing colors on the short form (#000 as opposed to #000000) makes it possible to express 4096 unique colors.

Q: Does this mean that I can make an entire web page in SVG, with photos and everything?
A: Yes! This is not the intended use of png2svg, but it might work out if the images are kept small.

Q: Can I use this for QR codes?
A: Yes!

Q: Can I use png2svg together with svgo to create assets for a game that only uses vector graphics?
A: Yes! If the images are kept small.

Q: Are these questions just made up, or did someone actually ask this?
A: Look behind you, a three headed monkey!

Installation

For Go 1.17 or later:

go install github.com/0daryo/png2svg/cmd/png2svg@latest

Example usage

Generate an SVG image with as few rectangles as possible (-o for "output"):

png2svg -o output.svg input.png

Generate an SVG image with one rectangle per pixel:

png2svg -p -o output.svg input.png

Generate an SVG image where the output is limited to 4096 unique colors (-l for "limit"):

png2svg -l -o output.svg input.png

Like above, but with progress information while the image is being generated:

png2svg -v -l -o output.svg input.png

General information

Documentation

Index

Constants

View Source
const VersionString = "png2svg 1.5.2"

VersionString contains the package name and the current version

Variables

This section is empty.

Functions

func Erase

func Erase(n int)

Erase characters on the terminal

func ReadPNG

func ReadPNG(filename string, verbose bool) (image.Image, error)

ReadPNG tries to read the given PNG image filename and returns and image.Image and an error. If verbose is true, some basic information is printed to stdout.

Types

type Box

type Box struct {
	// contains filtered or unexported fields
}

Box represents a box with the following properties: * position (x, y) * size (w, h) * color (r, g, b, a)

type Pixel

type Pixel struct {
	// contains filtered or unexported fields
}

Pixel represents a pixel at position (x,y) with color (r,g,b,a) and a bool for if this pixel has been covered by an SVG shape yet

type PixelImage

type PixelImage struct {
	// contains filtered or unexported fields
}

PixelImage contains the data needed to convert a PNG to an SVG: pixels (with an overview of which pixels are covered) and an SVG document, starting with the document and root tag + colorOptimize, for if only 4096 colors should be used (short hex color strings, like #fff).

func NewPixelImage

func NewPixelImage(img image.Image, verbose bool) *PixelImage

NewPixelImage initializes a new PixelImage struct, given an image.Image.

func (*PixelImage) At

func (pi *PixelImage) At(x, y int) (r, g, b int)

At returns the RGB color at the given coordinate

func (*PixelImage) At2

func (pi *PixelImage) At2(x, y int) (r, g, b, a int)

At2 returns the RGBA color at the given coordinate

func (*PixelImage) Bytes

func (pi *PixelImage) Bytes() []byte

Bytes returns the rendered SVG document as bytes

func (*PixelImage) CoverAllPixels

func (pi *PixelImage) CoverAllPixels()

CoverAllPixels will cover all pixels that are not yet covered by an SVG element , by creating a rectangle per pixel.

func (*PixelImage) CoverBox

func (pi *PixelImage) CoverBox(bo *Box, pink bool, optimizeColors bool)

CoverBox creates rectangles in the SVG image, and also marks the pixels as covered if pink is true, the rectangles will be pink if optimizeColors is true, the color strings will be shortened (and quantized)

func (*PixelImage) CoverEmptyBox

func (pi *PixelImage) CoverEmptyBox(bo *Box)

func (*PixelImage) Covered

func (pi *PixelImage) Covered(x, y int) bool

Covered returns true if the pixel at the given coordinate is already covered by SVG elements

func (*PixelImage) CreateBox

func (pi *PixelImage) CreateBox(x, y int) *Box

CreateBox creates a 1x1 box at the given location, if it's not already covered

func (*PixelImage) CreateRandomBox

func (pi *PixelImage) CreateRandomBox(checkIfPossible bool) *Box

CreateRandomBox randomly searches for a place for a 1x1 size box. Note: If checkIfPossible is true, the function continue running until it either finds a free spot or no spots are available.

func (*PixelImage) Done

func (pi *PixelImage) Done(startx, starty int) bool

Done checks if all pixels are covered, in terms of being represented by an SVG element searches from the given x and y coordinate

func (*PixelImage) Expand

func (pi *PixelImage) Expand(bo *Box) (expanded bool)

Expand tries to expand the box to the right and downwards, until it can't expand any more. Returns true if the box was expanded at least once.

func (*PixelImage) ExpandDown

func (pi *PixelImage) ExpandDown(bo *Box) bool

ExpandDown will expand a box 1 pixel downwards, if all new pixels have the same color

func (*PixelImage) ExpandLeft

func (pi *PixelImage) ExpandLeft(bo *Box) bool

ExpandLeft will expand a box 1 pixel to the left, if all new pixels have the same color

func (*PixelImage) ExpandOnce

func (pi *PixelImage) ExpandOnce(bo *Box) bool

ExpandOnce tries to expand the box to the right and downwards, once

func (*PixelImage) ExpandRight

func (pi *PixelImage) ExpandRight(bo *Box) bool

ExpandRight will expand a box 1 pixel to the right, if all new pixels have the same color

func (*PixelImage) ExpandUp

func (pi *PixelImage) ExpandUp(bo *Box) bool

ExpandUp will expand a box 1 pixel upwards, if all new pixels have the same color

func (*PixelImage) FirstUncovered

func (pi *PixelImage) FirstUncovered(startx, starty int) (int, int)

FirstUncovered will find the first pixel that is not covered by an SVG element, starting from (startx,starty), searching row-wise, downwards.

func (*PixelImage) SetColorOptimize

func (pi *PixelImage) SetColorOptimize(enabled bool)

SetColorOptimize can be used to set the colorOptimize flag, for using only 4096 colors.

func (*PixelImage) WriteSVG

func (pi *PixelImage) WriteSVG(filename string) error

WriteSVG will save the current SVG document to a file

type Pixels

type Pixels []*Pixel

Pixels is a slice of pointers to Pixel

Directories

Path Synopsis
cmd

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL