Giter VIP home page Giter VIP logo

scarlet's Introduction

Scarlet

Colors and color spaces made simple, for Rustaceans.

Build Status Crates.io dependency status Documentation

Humans and computers don't view color the same way, and so color descriptions like RGB don't effectively describe colors in the way that humans perceive them and vice versa. Image processing and other disciplines require the ability to interconvert and work with colors in a way that respects both how colors are displayed and how they are perceived by the human eye. Scarlet makes this not only possible, but simple and convenient. With Scarlet, you can:

  • Interconvert between different color representations
  • Work with colors in one representation using the concepts of a different one: for example, you can use a model of color luminance that accurately models human vision without leaving RGB, or modify a color's hue in CIELAB
  • Mix and average colors accurately, without kludges or results that look wrong to humans
  • Create perceptually-uniform color scales, colormaps, and gradients suitable for publication-quality visuals that don't mislead viewers
  • Convert a color to grayscale accurately and precisely
  • Accurately determine how far apart colors are perceptually.
  • And more!

Installation

Add this to your Cargo.toml:

[dependencies]
scarlet = "1.1.0"

and this to your crate root:

extern crate scarlet;

Documentation

Consult the documentation at docs.rs.

Contributing Guidelines

Before making a pull request, please consult the contributing guidelines.

The gist of it is:

  • Running cargo test should result in all tests passing. If tests themselves are wrong, change those in the pull request and explain the errors. Don't disable tests to make cargo test pass unless you have a really good reason!
  • If you make changes to the public-facing API, you should make sure that those changes are consistent with best practices and explain why you feel the API should change.
  • If you make performance improvements to code that already works, benchmark the change with test code that does things users would want to do and publish the results showing that your improvement actually improved something.
  • If you add new functionality, you should have test cases that thoroughly test that functionality.

General Philosophy

To look at the general philosophy and API design of Scarlet, please look at api.org. This is more intended for developers.

scarlet's People

Contributors

joseluis avatar milesmcc avatar nicholas-miklaucic avatar twitzelbos 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

Watchers

 avatar  avatar  avatar  avatar

scarlet's Issues

Constants are a mess

The consts.rs file runs into the problem that, as of now, Rust doesn't allow constants or statics to use functions to initialize. This means that every time we do any conversion, we generate the matrix from scratch, or do that and take its inverse. This is ridiculous, but it's hard to think of ways to fix it. We could add const fn, which is a nightly feature, but I'm unsure if that will even apply. We could store the inverses, but unless we do it to something like 15 decimal places we'll lose the preciison that made me use this library in the first place.

High level documentation: add section on the various definitions of colors being close

We need a guide, with worked examples, on how to compare colors and what that means. Embedding colors as points can be really confusing: CIELAB with L = 0, a = -123, and b = 125 is the exact same color as L = 0, a = 100, and b = -124. Ditto for HSV and any chrominance-value system. We need a guide that clearly explains how to get color distances and why other methods aren't good enough.

Form of perceptual equality or approximate equality

Color::distance is already implemented, which gives a perceptual analog for color distance. It'd be helpful to have some sort of equality metric that uses this, perhaps both for exact equality and approximate equality.

The reason for this is because for chrominance-value spaces, like HSL and CIELCH, hue doesn't matter if the lightness is either black or white, so the hue value doesn't matter for equality metrics. Floating-point means that direct equality isn't super useful, though: perhaps it'd be best to do approximate equality using the XYZ method?

Clarify public/private: create prelude

I need to clarify what's public and what's private: I think pretty much everything should be public, but that might create problems down the line. What, if anything, should be private?

We also need a "prelude" of sorts. This allows people to import things without having to dig through a bunch of files. I'm thinking Color, RGBColor, CIELABColor, CIELCHColor, XYZColor, Mix, and ColorPoint.

Automatic rainbow-mode colorization?

In my Emacs setup, strings such as #f0f that can be hex codes are automatically colored with that color. This makes it easy to see what colors look like. Adding this to our documentation would be lovely.

High-level tutorial guide with examples

I'll probably take care of this one myself, just so you know.

Rustdoc is nice and all, but a lot of crates lack the really crucial last step: a high-level guide that goes through common use cases. Giving people documentation on everything in the library isn't useful if people need to search all of that just to figure out how to do the thing they want to do.

I'm thinking worked code examples, that compile and do useful things, for things that people might want to do:

  • Generate a triadic color scheme
  • Equalize colors by luminance
  • Compare the difference in various methods of getting grayscale versions of a color
  • Replicate the famous Wright-Guild experiment (ok, probably better as a demo)

With something like this, where it's hard to explain what it does clearly to anyone who isn't a color scientist, it's especially important to have some cool demo or something that people can look at and then see parts of that functionality that they wanna use.

Link to API.org Seems Wrong

In the README you state:

To look at the general philosophy and API design of Scarlet, please look at api.org. This is more intended for developers.

The domain www.api.org points to the American Petroleum Institute, a website dedicated to natural gas and oil.

Which was the originally intended reference for API guidelines?

Different kinds of gradients

We currently just have linear gradients. It's sometimes nice to have other kinds, such as:

  • Logarithmic
  • Square root/cube root
  • Padding the scale on either end (e.g., end 80% of the way there)

These should be easy to implement and are a good way to get started!

Clamp color to the closest one representable in another color space

Every color space has a range of colors it can represent: for some, like CIELAB, this is simply the entire gamut of human vision, for others (like sRGB) it is much smaller. It is often desirable to get the closest color in one space that is representable in another one. This is pretty difficult to do and might require some pretty significant implementation: definitely one to tackle if you're feeling ambitious.

Colorizing isn't robust

The docs.rs link to the colorized HTML file wasn't working, so I had to remove it. Now, without externally hosting it, there's no good way of getting colorized RGB output without user plugins, sadly enough. Not sure this is really fixable in this library.

Switch linear algebra library

I think nalgebra was perhaps not the best choice. I literally only want a couple of functions, but it's a really big library. I think something like rulinalg might be better suited.

Clarify external dependencies

I'm not sure if I need to import all the things I do. Even nonwithstanding that, I need to make sure there's only extern crates in lib.rs. We also might wanna use deps.rs.

Unify precision requirements for test cases

For comparing XYZ colors, we have the approx_visually_equal method, which compares to a set constant that I can change. The problem is that in many other places in the code, I instead use one-off constants. That should change: either put them all using one method or make it a constant. That way, I can iteratively increase the precision of tests and fix the things that don't have that level of precision, like I did with XYZ colors.

Add CMYK

CMYK is... very different from other spaces. It's subtractive, for one thing. Also, different printers are different. It's gamut is also a pentagon on the UCS diagram: bet you didn't see that coming!

rulinalg is obsolete

Seems like rulinalg is no longer developed, and its also being flagged as having data race condition. I suggest replacing it with nalgebra.

sHSL string conversion functionality

In the goal to have Scarlet accept all forms of color input that CSS does, at some point functionality for accepting strings such as hsl(75%, 20%, 14%) for the HSLColor class.

Implement common colormaps

There are some standard colormaps in data visualization that it's worth implementing. These include:

  • The MATLAB and matplotlib ones
  • A standard hue-based rainbow (this one is really bad for most things, though)
  • Cubehelix and other ones that vary lightness evenly

Care has to be taken: some of these really don't have any uses, and so in line with Scarlet's philosophy we should probably only implement colormaps that people should actually use.

Implement standard traits

Lots of common traits need to be implemented or derived. These include:

  • Serde's Deserialize and Serialize
  • Hash
  • IntoIterator for conveniently getting the components from the color
  • ToString where feasible
  • Display if possible
  • Anything else I'm missing

Clean up tests

Tests currently print all sorts of debugging nonsense. It's better to just stick to the demonstrations of color printing.

Add examples to documentation

Part of the Rust API guidelines is that every public-facing feature should have a documentation comment with an example. We're currently 0 for hundreds on this score.

File organization is a bit of a mess

The colors.rs file has two types and two traits, totalling over 1000 lines of code. When I first made it, I didn't realize that Rust is much more generous with import cycles than Python, so it is possible to move some of that into its own place.

Intra-crate links break in docs.rs

Docs.rs is breaking the intradoc links in many places. They work fine in local docs, though. Something to look into further. Hopefully soon the RFC on this will be stabilized so I can avoid this mess.

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.