Giter VIP home page Giter VIP logo

rio-color's Introduction

rio-color

Build Status Coverage Status

A rasterio plugin for applying basic color-oriented image operations to geospatial rasters.

Goals

  • No heavy dependencies: rio-color is purposefully limited in scope to remain lightweight
  • Use the image structure: By iterating over the internal blocks of the input image, we keep memory usage low and predictable while gaining the ability to
  • Use multiple cores: thanks to rio-mucho
  • Retain all the GeoTIFF info and TIFF structure: nothing is lost. A GeoTIFF input → GeoTIFF output with the same georeferencing, internal tiling, compression, nodata values, etc.
  • Efficient colorspace conversions: the intensive math is written in highly optimized C functions and for use with scalars and numpy arrays.
  • CLI and Python module: accessing the functionality as a python module that can act on in-memory numpy arrays opens up new opportunities for composing this with other array operations without using intermediate files.

Operations

Gamma adjustment adjusts RGB values according to a power law, effectively brightening or darkening the midtones. It can be very effective in satellite imagery for reducing atmospheric haze in the blue and green bands.

Sigmoidal contrast adjustment can alter the contrast and brightness of an image in a way that matches human's non-linear visual perception. It works well to increase contrast without blowing out the very dark shadows or already-bright parts of the image.

Saturation can be thought of as the "colorfulness" of a pixel. Highly saturated colors are intense and almost cartoon-like, low saturation is more muted, closer to black and white. You can adjust saturation independently of brightness and hue but the data must be transformed into a different color space.

animated

Examples

Sigmoidal

Contrast

sigmoidal_contrast

Bias

sigmoidal_bias

Gamma

Red

gamma_red

Green

gamma_green

Blue

gamma_blue

Saturation

saturation

Combinations of operations

combos

Install

We highly recommend installing in a virtualenv. Once activated,

pip install -U pip
pip install rio-color

Or if you want to install from source

git checkout https://github.com/mapbox/rio-color.git
cd rio-color
pip install -U pip
pip install -r requirements-dev.txt
pip install -e .

Python API

rio_color.operations

The following functions accept and return numpy ndarrays. The arrays are assumed to be scaled 0 to 1. In some cases, the input array is assumed to be in the RGB colorspace.

All arrays use rasterio ordering with the shape as (bands, columns, rows). Be aware that other image processing software may use the (columns, rows, bands) axis order.

  • sigmoidal(arr, contrast, bias)
  • gamma(arr, g)
  • saturation(rgb, proportion)
  • simple_atmo(rgb, haze, contrast, bias)

The rio_color.operations.parse_operations function takes an operations string and returns a list of python functions which can be applied to an array.

ops = "gamma b 1.85, gamma rg 1.95, sigmoidal rgb 35 0.13, saturation 1.15"

assert arr.shape[0] == 3
assert arr.min() >= 0
assert arr.max() <= 1

for func in parse_operations(ops):
    arr = func(arr)

This provides a tiny domain specific language (DSL) to allow you to compose ordered chains of image manipulations using the above operations. For more information on operation strings, see the rio color command line help.

rio_color.colorspace

The colorspace module provides functions for converting scalars and numpy arrays between different colorspaces.

>>> from rio_color.colorspace import ColorSpace as cs  # enum defining available color spaces
>>> from rio_color.colorspace import convert, convert_arr
>>> convert_arr(array, src=cs.rgb, dst=cs.lch) # for arrays
...
>>> convert(r, g, b, src=cs.rgb, dst=cs.lch)  # for scalars
...
>>> dict(cs.__members__)  # can convert to/from any of these color spaces
{
 'rgb': <ColorSpace.rgb: 0>,
 'xyz': <ColorSpace.xyz: 1>,
 'lab': <ColorSpace.lab: 2>,
 'lch': <ColorSpace.lch: 3>,
 'luv': <ColorSpace.luv: 4>
 }

Command Line Interface

Rio color provides two command line interfaces:

rio color

A general-purpose color correction tool to perform gamma, contrast and saturation adjustments.

The advantages over Imagemagick convert: rio color is geo-aware, retains the profile of the source image, iterates efficiently over interal tiles and can use multiple cores.

Usage: rio color [OPTIONS] SRC_PATH DST_PATH OPERATIONS...

  Color correction

  Operations will be applied to the src image in the specified order.

  Available OPERATIONS include:

      "gamma BANDS VALUE"
          Applies a gamma curve, brightening or darkening midtones.
          VALUE > 1 brightens the image.

      "sigmoidal BANDS CONTRAST BIAS"
          Adjusts the contrast and brightness of midtones.
          BIAS > 0.5 darkens the image.

      "saturation PROPORTION"
          Controls the saturation in LCH color space.
          PROPORTION = 0 results in a grayscale image
          PROPORTION = 1 results in an identical image
          PROPORTION = 2 is likely way too saturated

  BANDS are specified as a single arg, no delimiters

      `123` or `RGB` or `rgb` are all equivalent

  Example:

      rio color -d uint8 -j 4 input.tif output.tif \
          gamma 3 0.95, sigmoidal rgb 35 0.13


Options:
  -j, --jobs INTEGER              Number of jobs to run simultaneously, Use -1
                                  for all cores, default: 1
  -d, --out-dtype [uint8|uint16]  Integer data type for output data, default:
                                  same as input
  --co NAME=VALUE                 Driver specific creation options.See the
                                  documentation for the selected output driver
                                  for more information.
  --help                          Show this message and exit.

Example:

$ rio color -d uint8 -j 4 rgb.tif test.tif \
    gamma G 1.85 gamma B 1.95 sigmoidal RGB 35 0.13 saturation 1.15

screen shot 2016-02-17 at 12 18 47 pm

rio atmos

Provides a higher-level tool for general atmospheric correction of satellite imagery using a proven set of operations to adjust for haze.

Usage: rio atmos [OPTIONS] SRC_PATH DST_PATH

  Atmospheric correction

Options:
  -a, --atmo FLOAT                How much to dampen cool colors, thus cutting
                                  through haze. 0..1 (0 is none), default:
                                  0.03.
  -c, --contrast FLOAT            Contrast factor to apply to the scene.
                                  -infinity..infinity(0 is none), default: 10.
  -b, --bias FLOAT                Skew (brighten/darken) the output. Lower
                                  values make it brighter. 0..1 (0.5 is none),
                                  default: 0.15
  -d, --out-dtype [uint8|uint16]  Integer data type for output data, default:
                                  same as input
  --as-color                      Prints the equivalent rio color command to
                                  stdout.Does NOT run either command, SRC_PATH
                                  will not be created
  -j, --jobs INTEGER              Number of jobs to run simultaneously, Use -1
                                  for all cores, default: 1
  --co NAME=VALUE                 Driver specific creation options.See the
                                  documentation for the selected output driver
                                  for more information.
  --help                          Show this message and exit.

rio-color's People

Contributors

0xflotus avatar celoyd avatar dnomadb avatar firefishy avatar jqtrde avatar perrygeo avatar pratikyadav avatar sgillies avatar vincentsarago avatar virginiayung 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  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

rio-color's Issues

Saturation can't precede other operations

works w/saturation as last op

rio color test/fixtures/wellformed-tiny.tif /tmp/out gamma g 0.99 gamma R 0.95  saturation 1.25

putting gamma last gives an error

$ rio color test/fixtures/wellformed-tiny.tif /tmp/out gamma g 0.99 saturation 1.25 gamma R 0.95
Traceback (most recent call last):
  File "/Users/mperry/env/mapbox34/bin/rio", line 9, in <module>
    load_entry_point('rasterio', 'console_scripts', 'rio')()
  File "/Users/mperry/env/mapbox34/lib/python3.4/site-packages/click/core.py", line 716, in __call__
    return self.main(*args, **kwargs)
  File "/Users/mperry/env/mapbox34/lib/python3.4/site-packages/click/core.py", line 696, in main
    rv = self.invoke(ctx)
  File "/Users/mperry/env/mapbox34/lib/python3.4/site-packages/click/core.py", line 1060, in invoke
    return _process_result(sub_ctx.command.invoke(sub_ctx))
  File "/Users/mperry/env/mapbox34/lib/python3.4/site-packages/click/core.py", line 889, in invoke
    return ctx.invoke(self.callback, **ctx.params)
  File "/Users/mperry/env/mapbox34/lib/python3.4/site-packages/click/core.py", line 534, in invoke
    return callback(*args, **kwargs)
  File "/Users/mperry/env/mapbox34/lib/python3.4/site-packages/click/decorators.py", line 17, in new_func
    return f(get_current_context(), *args, **kwargs)
  File "/Users/mperry/work/rio-color/rio_color/scripts/cli.py", line 110, in color
    arr = color_worker(rasters, window, ij, args)
  File "/Users/mperry/work/rio-color/rio_color/workers.py", line 27, in color_worker
    arr = func(arr)
  File "/Users/mperry/work/rio-color/rio_color/operations.py", line 250, in f
    newarr[b - 1] = func(arr[b - 1], **kwargs)
  File "/Users/mperry/work/rio-color/rio_color/operations.py", line 132, in saturation
    raise ValueError("saturation requires a 3-band array")
ValueError: saturation requires a 3-band array

Saturation operator

One of the convert flags we want to replace is the second argument to -modulate, which adjusts saturation. (Pulled out of #5.) Braindumping some options, in order of increasing hackiness:

  1. The conceptually straightest path here is to convert RGB to a radial colorspace that has a dedicated saturation channel, multiply that channel, and convert it back. Our default radial colorspace is LCH, because it combines a nicely grounded definition with a good approximation of perceptual uniformity. Unfortunately, the conversion is relatively complex and resource-hungry: skimage, for example, goes RGB → Lab → LCH and back.
  2. We could use HSV, which has a simpler definition.* The 👎 I see is setting a precedent of using HSV, which isn’t our best practice. I think it’s wiser to keep rio color in a “gold standard” role instead of a “workable approximation” role – for that, you might as well write your own functions. *Though possibly not faster, given that it has a 6-part case, as opposed to the trig functions of the LCH route. I don’t have good intuition about numpy optimization.
  3. We could work out an equivalent (ish) saturation operator that works directly on RGB pixels. I see this as even more of a hack: by the time it was well defined, it’d be doing 80% of the work of converting to and from a radial colorspace anyway. On the 👍, it would probably be very fast and do a fairly good job of matching any other saturation operator.

How do you see this, @perrygeo?

Handle dataset with negative values

Input bands are presumed to correspond to digital numbers for a certain spectral range, most often Red, Green and Blue.

What do we do with negative values and negative nodata values?

My current thought is that scaling these values to positive should be the responsibility of the user (otherwise need to make many assumptions on their behalf).

Let's do this

  • get a test case with negative values
  • assert that negative values or negative nodata values raise an exception

The future of the colorspaces module

a fast all-around colorspace converter for numpy arrays (that doesn't require skimage)

might be a good eventual goal for rio-color. It's something we can works towards incrementally...

  • refactor scalar conversions into smaller cdef funcs (rgb2xyz, xyz2lab, lab2lch)
  • general purpose array conversion function, instead of arr_rgb_to_lch, we'd have something like arr_colorspace(arr, 'rgb', 'lch')
  • a generic c struct for 3 element color coordinates rather than a separate struct for each
  • ???

still planning and thinking on this one. /cc @celoyd

Color interpretation test failure with Rasterio 1.0 and GDAL 2.2

This test fails, and seems to fail because the source file has no photometric interpretation explicitly set, and thus none is transferred via profile to the output file.

tmpdir = local('/private/var/folders/zq/fv6jds3j4wb_0z0zh35xky_c0000gn/T/pytest-of-sean/pytest-671/test_color_cli_16bit_photointe0')

    def test_color_cli_16bit_photointerp(tmpdir):
        output = str(tmpdir.join('color16color.tif'))
        runner = CliRunner()
        result = runner.invoke(
            color,
            ['-d', 'uint16',
             '-j', '1',
             'tests/rgb16.tif',
             output,
             "gamma 3 1.85",
             "gamma 1,2 1.95"])
        assert result.exit_code == 0

        with rasterio.open('tests/rgb16.tif') as src:
            with rasterio.open(output) as out:
                for b in src.indexes:
>                   assert out.colorinterp == src.colorinterp
E                   assert (<ColorInterp...undefined: 0>) == (<ColorInterp....terp.blue: 5>)
E                     At index 0 diff: <ColorInterp.grey: 1> != <ColorInterp.red: 3>
E                     Use -v to get the full diff

Otherwise, everything checks out with Rasterio 1.0rc5 and rio-mucho 1.0dev1.

1.0 release

Let's go! Target date: Thursday, July 26.

  • tag 1.0dev1
  • close issues
  • tag 1.0rc1
  • 1.0.0

AttributeError: module 'enum' has no attribute 'IntFlag' when install from source

(v) G:\_temp\!test\rio-color>pip install -e .
Obtaining file:///G:/_temp/%21test/rio-color
Requirement already satisfied: click in g:\_temp\!test\v\lib\site-packages (from rio-color==1.0.0) (7.1.2)
Collecting rasterio>=1.0a11
  Downloading rasterio-1.1.5.tar.gz (2.2 MB)
     |████████████████████████████████| 2.2 MB 6.4 MB/s
  Installing build dependencies ... error
  ERROR: Command errored out with exit status 1:
   command: 'g:\_temp\!test\v\scripts\python.exe' 'g:\_temp\!test\v\lib\site-packages\pip' install --ignore-installed --no-user --prefix 'C:\Users\Administrator\AppData\Local\Temp\pip-build-env-o8wr7vzf\overlay' --no-warn-script-location --no-binary :none: --only-binary :none: -i https://pypi.org/simple -- setuptools wheel cython numpy
       cwd: None
  Complete output (14 lines):
  Traceback (most recent call last):
    File "C:\Program Files\Python37\lib\runpy.py", line 193, in _run_module_as_main
      return _run_code(code, main_globals, None,
    File "C:\Program Files\Python37\lib\runpy.py", line 86, in _run_code
      exec(code, run_globals)
    File "g:\_temp\!test\v\lib\site-packages\pip\__main__.py", line 23, in <module>
      from pip._internal.cli.main import main as _main  # isort:skip # noqa
    File "g:\_temp\!test\v\lib\site-packages\pip\_internal\cli\main.py", line 5, in <module>
      import locale
    File "C:\Program Files\Python37\lib\locale.py", line 16, in <module>
      import re
    File "C:\Program Files\Python37\lib\re.py", line 143, in <module>
      class RegexFlag(enum.IntFlag):
  AttributeError: module 'enum' has no attribute 'IntFlag'
  ----------------------------------------
ERROR: Command errored out with exit status 1: 'g:\_temp\!test\v\scripts\python.exe' 'g:\_temp\!test\v\lib\site-packages\pip' install --ignore-installed --no-user --prefix 'C:\Users\Administrator\AppData\Local\Temp\pip-build-env-o8wr7vzf\overlay' --no-warn-script-location --no-binary :none: --only-binary :none: -i https://pypi.org/simple -- setuptools wheel cython numpy Check the logs for full command output.

(v) G:\_temp\!test\rio-color>

use all cores with -j -1

Modify max_procs so that a negative value means "use the number of cores available on this machine"

Performance of saturation

Saturation operator needs to be faster. It's really slow compared to imagemagick's modulate.

$ rio info $orig | jq .shape
[
  8192,
  8192
]
$ time rio color $orig f416_rio_lch.tif "saturation 130"

real    1m10.490s
$ time convert $orig -modulate 100,130 f416_magick.tif

real    0m6.954s

Investigating...

Manylinux wheels

As part of the release process, we might consider building manylinux wheels to allow easy installation on linux without a build toolchain. I think that, because colorspace.so does not link to any external shared objects, that this should be fairly lightweight and rely on the libgdal that is linked to Rasterio.

@sgillies do we want to include this in frs-wheel-builds?

cc @vincentsarago

Error in rio color command line

Hi,
I use Mac and installed rio color as explained.
I could not execute rio color command as in the example.

Error: no such option: -d

new cli syntax

As discussed in #5, We ditched the idea of click command options (--saturation, etc) because they are unordered. As an alternative, we developed a little domain specific language where each additional argument was an operation to applied in order.

e.g. this would apply gamma to red and green then a saturation to the whole image

rio color in.tif out.tif "gamma r,g 1.05" "saturation 125"

This works until you start passing around the the operations as shell variables. You quickly get into quote escape and delimeter hell. Consider this

$ color_formula="\"gamma r,g 1.05\" \"saturation 125\""
$ set -x
$ echo $color_formula
+ echo '"gamma' r,g '1.05"' '"saturation' '125"'

Ugh. broken by spaces. It gets even nastier when you try to read operations from files or sed streams.

In short, our DSL has issues.

❓ Potential Solutions:

  • Use a different delimiter: gamma_r,g_1.05 saturation_125 a bit yicky but functional. By using _ and avoiding the space, we avoid the need to use quotes. And we could make it compatible with the existing language.
  • Use something that would be an entire departure
    • a single quoted series of S-expressions: "(gamma r,g 1.05) (saturation 125)"
    • override click.Command.parse_args to keep ordered options: --gamma r,g 1.05 --saturation 125
    • unquoted DSL: gamma r,g 1.05 saturation 125

/cc @sgillies @celoyd

Spurious sigmoidal contrast output error

I'm getting a confusing error the file at https://www.dropbox.com/s/e86y9xl1u49vjxa/moab8_crop.tif?dl=0.

$ rio atmos moab8_crop.tif moab8_cor.tif
/Users/sean/code/rasterio/rasterio/__init__.py:193: UserWarning: Dataset has no geotransform set.  Default transform will be applied (Affine.identity())
  s.start()
/Users/sean/code/rasterio/rasterio/__init__.py:193: UserWarning: Dataset uses default geotransform (Affine.identity). No transform will be written to the output by GDAL.
  s.start()
Traceback (most recent call last):
  File "/Users/sean/envs/pydotorg35/bin/rio", line 9, in <module>
    load_entry_point('rasterio==0.35.1', 'console_scripts', 'rio')()
  File "/Users/sean/envs/pydotorg35/lib/python3.5/site-packages/click/core.py", line 716, in __call__
    return self.main(*args, **kwargs)
  File "/Users/sean/envs/pydotorg35/lib/python3.5/site-packages/click/core.py", line 696, in main
    rv = self.invoke(ctx)
  File "/Users/sean/envs/pydotorg35/lib/python3.5/site-packages/click/core.py", line 1060, in invoke
    return _process_result(sub_ctx.command.invoke(sub_ctx))
  File "/Users/sean/envs/pydotorg35/lib/python3.5/site-packages/click/core.py", line 889, in invoke
    return ctx.invoke(self.callback, **ctx.params)
  File "/Users/sean/envs/pydotorg35/lib/python3.5/site-packages/click/core.py", line 534, in invoke
    return callback(*args, **kwargs)
  File "/Users/sean/envs/pydotorg35/lib/python3.5/site-packages/click/decorators.py", line 17, in new_func
    return f(get_current_context(), *args, **kwargs)
  File "/Users/sean/envs/pydotorg35/lib/python3.5/site-packages/rio_color/scripts/cli.py", line 178, in atmos
    arr = atmos_worker(rasters, window, ij, args)
  File "/Users/sean/envs/pydotorg35/lib/python3.5/site-packages/rio_color/workers.py", line 15, in atmos_worker
    args['bias'])
  File "/Users/sean/envs/pydotorg35/lib/python3.5/site-packages/rio_color/operations.py", line 170, in simple_atmo
    output = sigmoidal(arr, contrast, bias)
  File "/Users/sean/envs/pydotorg35/lib/python3.5/site-packages/rio_color/operations.py", line 82, in sigmoidal
    raise ValueError("Sigmoidal contrast output is not within the range of [0,1]")
ValueError: Sigmoidal contrast output is not within the range of [0,1]

To see what the equivalent rio-color is, I used the --as-color option.

$ rio atmos --as-color moab8_crop.tif moab8_cor.tif
rio color moab8_crop.tiff moab8_cor.tif gamma g 0.99, gamma b 0.97, sigmoidal rgb 10.0 0.15

And then this rio-color command worked, no error.

review maths

We need a quick review of the formulas. Everything looks good, outputs are almost exactly what imagemagick gives us but just to be safe...

  • add detailed docstrings explaining the parameters, their domains, references to literature, etc
  • write some validation logic in the functions to catch parameters that are outside the expected domains (e.g. arrays not scaled 0 to 1)
  • review unit tests, test_operations.py and see if the current tests make sense and if there are additional edge cases we should be testing for.

/cc @virginiayung

How to rescale the image after rio-color operations?

According to documentation, rio-color operations only take rasters of dimensions (3, x, y) for processing, in 0 to 1 range for pixel values.

I'm facing some issues getting the image into the same state as doing rio color --co photometric=rgb stack.tiff landsat8_color.tiff sigmoidal RGB 20 0.2 -j 1

The code I've used is as follows.

# initializing and reading the bands

import rasterio as rio
import numpy as np
from rio_color import operations, utils

R10 = '/Users/shivashis.ext/felicette-data/LC81390462020136'
b4 = rio.open(R10+'/LC81390462020136-b4.tiff')
b3 = rio.open(R10+'/LC81390462020136-b3.tiff')
b2 = rio.open(R10+'/LC81390462020136-b2.tiff')
# getting the bands in the range of [0..1]
r = b4.read(1)
g = b3.read(1)
b = b2.read(1)
norm_r = np.linalg.norm(r)
norm_g = np.linalg.norm(g)
norm_b = np.linalg.norm(b)
r = r / norm_r
g = g / norm_g
b = b / norm_b

# making and processing image
img = np.array([r,g,b])

img = operations.sigmoidal(img, 20, 0.2)

# from matplotlib import pyplot as plt
norm_r = img[0]
norm_r = utils.scale_dtype(img[0], np.uint16)# np.interp(norm_r, (norm_r.min(), norm_r.max()), (0, 65535))
norm_g = img[1]
norm_g = utils.scale_dtype(img[1], np.uint16)#np.interp(norm_g, (norm_g.min(), norm_g.max()), (0, 65535))
norm_b = img[2]
norm_b = utils.scale_dtype(img[2], np.uint16)#np.interp(norm_b, (norm_b.min(), norm_b.max()), (0, 65535))

# writing back to file

out_tiff = R10 + '/stack_prog_color_2.tiff'
with rio.open(out_tiff,'w',driver='Gtiff', width=b4.width, height=b4.height, 
              count=3,crs=b4.crs,transform=b4.transform, dtype=np.uint16, photometric="RGB") as rgb:
    rgb.write(norm_r.astype(np.uint16),1) 
    rgb.write(norm_g.astype(np.uint16),2) 
    rgb.write(norm_b.astype(np.uint16),3) 
    rgb.close()

As one can see, I've used both in-house scale_dtype and Numpy's linear interpolation to scale the array back, without success.

Also, I planned to save the numpy response of sigmoid function as a pickle file, and debug keeping it as reference, but since the job is parallel by rio-mucho, it got too complex in very short time.

I am almost sure that I'm scaling the image back wrong, because size of the the output tiffs with a) command line and b) Python API are same. (Both use np.uint16 to store data)

Please let me also know, if any other detail is required to understand/debug/help this issue.

Thank you for your time in advance!

Exclude *.pyx and *.c files from wheels

The bulk of a wheel's contents is the colorspace.c file and it isn't needed in the wheels.

$ tar tzvf ~/Downloads/rio_color-1.0rc1-cp37-cp37m-manylinux1_x86_64.whl
-rwxrwxrwx  0 0      0      334703 Jul 19 16:50 rio_color/colorspace.cpython-37m-x86_64-linux-gnu.so
-rwxrwxrwx  0 0      0          40 Jul 19 16:43 rio_color/__init__.py
-rwxrwxrwx  0 0      0         836 Jul 19 16:43 rio_color/workers.py
-rwxrwxrwx  0 0      0       11034 Jul 19 16:43 rio_color/colorspace.pyx
-rwxrwxrwx  0 0      0      463022 Jul 19 16:44 rio_color/colorspace.c
-rwxrwxrwx  0 0      0        8519 Jul 19 16:43 rio_color/operations.py
-rwxrwxrwx  0 0      0        2285 Jul 19 16:43 rio_color/utils.py
-rwxrwxrwx  0 0      0          21 Jul 19 16:43 rio_color/scripts/__init__.py
-rwxrwxrwx  0 0      0        5925 Jul 19 16:43 rio_color/scripts/cli.py
-rwxrwxrwx  0 0      0        1170 Jul 19 16:51 rio_color-1.0rc1.dist-info/RECORD
-rwxrwxrwx  0 0      0          10 Jul 19 16:50 rio_color-1.0rc1.dist-info/top_level.txt
-rwxrwxrwx  0 0      0         108 Jul 19 16:50 rio_color-1.0rc1.dist-info/entry_points.txt
-rwxrwxrwx  0 0      0         109 Jul 19 16:51 rio_color-1.0rc1.dist-info/WHEEL
-rwxrwxrwx  0 0      0        1178 Jul 19 16:50 rio_color-1.0rc1.dist-info/METADATA

I'm not sure how to accomplish this without some conditional MANIFEST.in hacks, but there are probably some examples out there.

Sigmoidal switch: no change

I am having an issue with the sigmoidal switch when using the rio color commandline interface.

No matter what settings I use for the brightness swtich, the visuals on the output file do not change.

The following all produce the exact same result, with no visual change from the test file:

/usr/local/bin/rio color -d uint8 -j 4 ~/BG43_2016-12-06_2017-12-01.tif ~/BG43_2016-12-06_2017-12-01_SIGMOIDAL_brightness.tif sigmoidal rgb 1.0 0.4

/usr/local/bin/rio color -d uint8 -j 4 ~/BG43_2016-12-06_2017-12-01.tif ~/BG43_2016-12-06_2017-12-01_SIGMOIDAL_brightness.tif sigmoidal rgb 1.0 0.01

/usr/local/bin/rio color -d uint8 -j 4 ~/BG43_2016-12-06_2017-12-01.tif ~/BG43_2016-12-06_2017-12-01_SIGMOIDAL_brightness.tif sigmoidal rgb 1.0 1.001

The test file can be accessed here: https://linz-test-data.s3-ap-southeast-2.amazonaws.com/BG43_2016-12-06_2017-12-01.tif

I am running Ubuntu 18.04 and did the standard install for rio color:
pip install rio-color

The gamma and saturation switches both work normally. For me, sigmoidal seems to be the only issue.

Is this a bug or am I missing something in my command structure?

dark object subtraction

We have rio atmos which provides a basic mechanism for de-hazing. Let's implement dark object subtraction - a scene-wide atmospheric correction technique that requires no auxillary atmospheric data.

The core concept is that we can identify a pixel that should be zero reflectance - the "dark object". If it's reflectance is higher than zero, the resulting offset is assumed to be due to atmospheric scattering. We can subtract that offset from each band, effectively shifting the histograms left and correcting the haze. (the amount of shift differs based on the wavelength of each band, more details in below)

This is ostensibly color related because atmospheric scatter is greatest in the visible bands though it does affect other bands as well. So I'm 50/50 on whether this operation belongs here or in a separate repo.

cc @celoyd @virginiayung

Can't pip install in py 3.11

Running pip install rio-color fails in Python 3.11.4 and pip 23.1.2

The error message is:

Building wheels for collected packages: rio-color
  Building wheel for rio-color (pyproject.toml) ... error
  error: subprocess-exited-with-error
  
  × Building wheel for rio-color (pyproject.toml) did not run successfully.
  │ exit code: 1
  ╰─> [35 lines of output]
      running bdist_wheel
      running build
      running build_py
      creating build
      creating build/lib.linux-x86_64-cpython-311
      creating build/lib.linux-x86_64-cpython-311/rio_color
      copying rio_color/workers.py -> build/lib.linux-x86_64-cpython-311/rio_color
      copying rio_color/operations.py -> build/lib.linux-x86_64-cpython-311/rio_color
      copying rio_color/__init__.py -> build/lib.linux-x86_64-cpython-311/rio_color
      copying rio_color/utils.py -> build/lib.linux-x86_64-cpython-311/rio_color
      creating build/lib.linux-x86_64-cpython-311/rio_color/scripts
      copying rio_color/scripts/__init__.py -> build/lib.linux-x86_64-cpython-311/rio_color/scripts
      copying rio_color/scripts/cli.py -> build/lib.linux-x86_64-cpython-311/rio_color/scripts
      running egg_info
      writing rio_color.egg-info/PKG-INFO
      writing dependency_links to rio_color.egg-info/dependency_links.txt
      writing entry points to rio_color.egg-info/entry_points.txt
      writing requirements to rio_color.egg-info/requires.txt
      writing top-level names to rio_color.egg-info/top_level.txt
      reading manifest file 'rio_color.egg-info/SOURCES.txt'
      reading manifest template 'MANIFEST.in'
      adding license file 'LICENSE'
      writing manifest file 'rio_color.egg-info/SOURCES.txt'
      copying rio_color/colorspace.c -> build/lib.linux-x86_64-cpython-311/rio_color
      copying rio_color/colorspace.pyx -> build/lib.linux-x86_64-cpython-311/rio_color
      running build_ext
      building 'rio_color.colorspace' extension
      creating build/temp.linux-x86_64-cpython-311
      creating build/temp.linux-x86_64-cpython-311/rio_color
      gcc -pthread -B /home/mambaforge/envs/gis2/compiler_compat -DNDEBUG -fwrapv -O2 -Wall -fPIC -O2 -isystem /home/mambaforge/envs/gis2/include -fPIC -O2 -isystem /home/mambaforge/envs/gis2/include -fPIC -I/tmp/pip-build-env-gk4m9_aa/overlay/lib/python3.11/site-packages/numpy/core/include -I/home/mambaforge/envs/gis2/include/python3.11 -c rio_color/colorspace.c -o build/temp.linux-x86_64-cpython-311/rio_color/colorspace.o -O2
      rio_color/colorspace.c:212:12: fatal error: longintrepr.h: No such file or directory
        212 |   #include "longintrepr.h"
            |            ^~~~~~~~~~~~~~~
      compilation terminated.
      error: command '/usr/bin/gcc' failed with exit code 1
      [end of output]
  
  note: This error originates from a subprocess, and is likely not a problem with pip.
  ERROR: Failed building wheel for rio-color
Failed to build rio-color
ERROR: Could not build wheels for rio-color, which is required to install pyproject.toml-based projects

Color Interp for uint16 outputs

A 16bit input:

$ gdalinfo -stats rgb_16bit_test.tif
...
Band 1 Block=1230x1 Type=UInt16, ColorInterp=Red
  Minimum=0.000, Maximum=65535.000, Mean=31678.789, StdDev=18936.088
Band 2 Block=1230x1 Type=UInt16, ColorInterp=Green
  Minimum=0.000, Maximum=65535.000, Mean=37789.235, StdDev=18526.473
Band 3 Block=1230x1 Type=UInt16, ColorInterp=Blue
  Minimum=0.000, Maximum=65535.000, Mean=32110.620, StdDev=21438.856

Running it through rio color to effectively make a copy

$ rio color -d uint16 rgb_16bit_test.tif channeltest.tif "gamma r,g,b 1"

And the output loses color interpretation (ColorInterp=Gray or Undefined)

$ gdalinfo -stats channeltest.tif
...
Band 1 Block=1230x1 Type=UInt16, ColorInterp=Gray
  Minimum=0.000, Maximum=65535.000, Mean=31678.789, StdDev=18936.088
Band 2 Block=1230x1 Type=UInt16, ColorInterp=Undefined
  Minimum=0.000, Maximum=65535.000, Mean=37789.235, StdDev=18526.473
Band 3 Block=1230x1 Type=UInt16, ColorInterp=Undefined
  Minimum=0.000, Maximum=65535.000, Mean=32110.620, StdDev=21438.856

We should retain the color interp from the original image if provided.

ping @celoyd

release 0.2

When the 0.2 milestone is wrapped up, it's time to publish 0.2.

This time, I need to straighten out a few issues

  • check on best practices for distributing cython
  • How to efficiently build binary wheels for as many platforms/py versions as reasonable
  • Upload with twine
  • Build linux wheels & publish to private package indexes (possibly digging into manylinux binaries depending on rasterio/rasterio#693)

In short, I just need to get a good release workflow down and documented.

@sgillies can we chat a bit about this next week?

Channel selectors

@virginiayung and I want a syntax and mechanism for rio color to apply given operations only to selected channels. For comparison, ImageMagick’s convert works like this:

convert input.tif -channel G -gamma 1.5 -channel B -gamma 0.5 -sigmoidal-contrast 3,50% -channel RGB output.tif

Which is something like this in pseudocode:

G = gamma(G, 1.5);
B = gamma(B, 0.5);
B = sigmoid(B, 3, 50);
write([R, G, B], output.tif);

Implicitly, R is passed through. It amounts to a simple system for creating blocks of operations.

I don’t love the convert syntax (for example, it’s easy to forget to switch back to RGB at the end) but it seems to mostly work. I wonder about something maybe more like this:

rio color 'G(gamma 1.6) B(gamma 0.5, sigmoid 3 50)' input.tif output.tif

Or maybe full s-expressions, or…?

Compatibility with existing color forumulas

The color formulas for each source are defined in a color file containing the command line arguments to imagemagick convert

We need to translate these to rio color arguments. Two main options

  1. Have a rio color --compatability option that will read convert args and interpret them on the fly
  2. Script/manually adjust all the color formulas in pxm-sources. Create an alternate color.rio file that mirrors the intent of color but with rio color syntax

Questions:

  • what do we do with convert options that don't translate well to rio color?
  • how are we going to visually test to make sure rio color output matches convert's?

Handling RGBA data

We want to make sure we adjust colors but don't tweak values in the alpha band.

Unable to install rio-color using pip in Windows 10

Hey,

I am having trouble installing rio-color using the command 'pip install rio-color'. I appreciate any support you can provide.

Here is my setup:
Windows 10 64-bit
pip 10.0.1
conda 4.5.8
python 3.6

When I run 'conda list' I see that I have:
twisted 17.5.0
automat 0.7.0

I have installed the following 'Included' tools from Visual Studio Build Tools 2017 15.7.5:
Visual C++ Build Tools core features
VC++ 2017 version 15.7 v14.14 latest v141 tools
Visual C++ 2017 Redistributable Update

I have also installed the following 'Optional' tools from Visual Studio Build Tools 2017 15.7.5:
Windows 10 SDK (10.0.17134.0)
Testing tools core features - Build Tools
C++/CLI support
Windows 10 SDK (10.0.15063.0) for Desktop C++
VC++ 2015.3 v14.00 (v140) toolset for desktop
Visual C++ compilers and libraries for ARM

Here is the error I am getting:

Collecting rio-color
Using cached https://files.pythonhosted.org/packages/66/41/8f4203efe15d2d679f59095611089b7a2f64cf1944d88954ef4e3819065c/rio-color-0.4.1.tar.gz
Requirement already satisfied: click in c:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\lib\site-packages (from rio-color) (6.7)
Requirement already satisfied: rasterio>=1.0a11 in c:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\lib\site-packages (from rio-color) (1.0.0)
Requirement already satisfied: rio-mucho in c:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\lib\site-packages (from rio-color) (0.2.2)
Requirement already satisfied: affine in c:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\lib\site-packages (from rasterio>=1.0a11->rio-color) (2.2.1)
Requirement already satisfied: attrs in c:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\lib\site-packages (from rasterio>=1.0a11->rio-color) (18.1.0)
Requirement already satisfied: cligj in c:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\lib\site-packages (from rasterio>=1.0a11->rio-color) (0.4.0)
Requirement already satisfied: numpy in c:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\lib\site-packages (from rasterio>=1.0a11->rio-color) (1.14.3)
Requirement already satisfied: snuggs>=1.4.1 in c:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\lib\site-packages (from rasterio>=1.0a11->rio-color) (1.4.1)
Requirement already satisfied: click-plugins in c:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\lib\site-packages (from rasterio>=1.0a11->rio-color) (1.0.3)
Requirement already satisfied: pyparsing in c:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\lib\site-packages (from snuggs>=1.4.1->rasterio>=1.0a11->rio-color) (2.2.0)
Building wheels for collected packages: rio-color
Running setup.py bdist_wheel for rio-color ... error
Complete output from command c:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\python.exe -u -c "import setuptools, tokenize;file='C:\Users\ROSS1.WIN\AppData\Local\Temp\1\pip-install-nxcvpadu\rio-color\setup.py';f=getattr(tokenize, 'open', open)(file);code=f.read().replace('\r\n', '\n');f.close();exec(compile(code, file, 'exec'))" bdist_wheel -d C:\Users\ROSS1.WIN\AppData\Local\Temp\1\pip-wheel-evap6m7s --python-tag cp36:
running bdist_wheel
running build
running build_py
creating build
creating build\lib.win-amd64-3.6
creating build\lib.win-amd64-3.6\rio_color
copying rio_color\operations.py -> build\lib.win-amd64-3.6\rio_color
copying rio_color\utils.py -> build\lib.win-amd64-3.6\rio_color
copying rio_color\workers.py -> build\lib.win-amd64-3.6\rio_color
copying rio_color_init_.py -> build\lib.win-amd64-3.6\rio_color
creating build\lib.win-amd64-3.6\rio_color\scripts
copying rio_color\scripts\cli.py -> build\lib.win-amd64-3.6\rio_color\scripts
copying rio_color\scripts_init_.py -> build\lib.win-amd64-3.6\rio_color\scripts
running egg_info
writing rio_color.egg-info\PKG-INFO
writing dependency_links to rio_color.egg-info\dependency_links.txt
writing entry points to rio_color.egg-info\entry_points.txt
writing requirements to rio_color.egg-info\requires.txt
writing top-level names to rio_color.egg-info\top_level.txt
reading manifest file 'rio_color.egg-info\SOURCES.txt'
reading manifest template 'MANIFEST.in'
writing manifest file 'rio_color.egg-info\SOURCES.txt'
copying rio_color\colorspace.c -> build\lib.win-amd64-3.6\rio_color
copying rio_color\colorspace.pyx -> build\lib.win-amd64-3.6\rio_color
running build_ext
building 'rio_color.colorspace' extension
creating build\temp.win-amd64-3.6
creating build\temp.win-amd64-3.6\Release
creating build\temp.win-amd64-3.6\Release\rio_color
C:\Program Files (x86)\Microsoft Visual Studio\2017\BuildTools\VC\Tools\MSVC\14.14.26428\bin\HostX86\x64\cl.exe /c /nologo /Ox /W3 /GL /DNDEBUG /MD -Ic:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\lib\site-packages\numpy\core\include -Ic:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\include -Ic:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\include "-IC:\Program Files (x86)\Microsoft Visual Studio\2017\BuildTools\VC\Tools\MSVC\14.14.26428\include" /Tcrio_color/colorspace.c /Fobuild\temp.win-amd64-3.6\Release\rio_color/colorspace.obj -O2
colorspace.c
c:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\include\pyconfig.h(59): fatal error C1083: Cannot open include file: 'io.h': No such file or directory
error: command 'C:\Program Files (x86)\Microsoft Visual Studio\2017\BuildTools\VC\Tools\MSVC\14.14.26428\bin\HostX86\x64\cl.exe' failed with exit status 2


Failed building wheel for rio-color
Running setup.py clean for rio-color
Failed to build rio-color
twisted 17.5.0 has requirement Automat>=0.3.0, but you'll have automat 0.0.0 which is incompatible.
Installing collected packages: rio-color
Running setup.py install for rio-color ... error
Complete output from command c:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\python.exe -u -c "import setuptools, tokenize;file='C:\Users\ROSS1.WIN\AppData\Local\Temp\1\pip-install-nxcvpadu\rio-color\setup.py';f=getattr(tokenize, 'open', open)(file);code=f.read().replace('\r\n', '\n');f.close();exec(compile(code, file, 'exec'))" install --record C:\Users\ROSS1.WIN\AppData\Local\Temp\1\pip-record-h4bnv4_s\install-record.txt --single-version-externally-managed --compile:
running install
running build
running build_py
creating build
creating build\lib.win-amd64-3.6
creating build\lib.win-amd64-3.6\rio_color
copying rio_color\operations.py -> build\lib.win-amd64-3.6\rio_color
copying rio_color\utils.py -> build\lib.win-amd64-3.6\rio_color
copying rio_color\workers.py -> build\lib.win-amd64-3.6\rio_color
copying rio_color_init_.py -> build\lib.win-amd64-3.6\rio_color
creating build\lib.win-amd64-3.6\rio_color\scripts
copying rio_color\scripts\cli.py -> build\lib.win-amd64-3.6\rio_color\scripts
copying rio_color\scripts_init_.py -> build\lib.win-amd64-3.6\rio_color\scripts
running egg_info
writing rio_color.egg-info\PKG-INFO
writing dependency_links to rio_color.egg-info\dependency_links.txt
writing entry points to rio_color.egg-info\entry_points.txt
writing requirements to rio_color.egg-info\requires.txt
writing top-level names to rio_color.egg-info\top_level.txt
reading manifest file 'rio_color.egg-info\SOURCES.txt'
reading manifest template 'MANIFEST.in'
writing manifest file 'rio_color.egg-info\SOURCES.txt'
copying rio_color\colorspace.c -> build\lib.win-amd64-3.6\rio_color
copying rio_color\colorspace.pyx -> build\lib.win-amd64-3.6\rio_color
running build_ext
building 'rio_color.colorspace' extension
creating build\temp.win-amd64-3.6
creating build\temp.win-amd64-3.6\Release
creating build\temp.win-amd64-3.6\Release\rio_color
C:\Program Files (x86)\Microsoft Visual Studio\2017\BuildTools\VC\Tools\MSVC\14.14.26428\bin\HostX86\x64\cl.exe /c /nologo /Ox /W3 /GL /DNDEBUG /MD -Ic:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\lib\site-packages\numpy\core\include -Ic:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\include -Ic:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\include "-IC:\Program Files (x86)\Microsoft Visual Studio\2017\BuildTools\VC\Tools\MSVC\14.14.26428\include" /Tcrio_color/colorspace.c /Fobuild\temp.win-amd64-3.6\Release\rio_color/colorspace.obj -O2
colorspace.c
c:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\include\pyconfig.h(59): fatal error C1083: Cannot open include file: 'io.h': No such file or directory
error: command 'C:\Program Files (x86)\Microsoft Visual Studio\2017\BuildTools\VC\Tools\MSVC\14.14.26428\bin\HostX86\x64\cl.exe' failed with exit status 2

----------------------------------------

Command "c:\users\ross.winans\appdata\local\continuum\anaconda3\envs\osgeo-36\python.exe -u -c "import setuptools, tokenize;file='C:\Users\ROSS1.WIN\AppData\Local\Temp\1\pip-install-nxcvpadu\rio-color\setup.py';f=getattr(tokenize, 'open', open)(file);code=f.read().replace('\r\n', '\n');f.close();exec(compile(code, file, 'exec'))" install --record C:\Users\ROSS1.WIN\AppData\Local\Temp\1\pip-record-h4bnv4_s\install-record.txt --single-version-externally-managed --compile" failed with error code 1 in C:\Users\ROSS~1.WIN\AppData\Local\Temp\1\pip-install-nxcvpadu\rio-color\

Easy conversion from rio atmos to rio color

rio atmos is a nice high-level tool for getting imagery looking good without much fiddling.

The downside is that systems using rio color won't we able to directly use those color formulas. The rio atmos forumulas can be broken down into rio color operations. We should provide an easy way to do that, maybe:

rio atmos --as-color

Other options?

1.0.4

To fix the numpy ABI issue reported in #79 .

update rasterio requirements to non-prerelease version

rasterio>=1.0a11

because it's now set to rasterio>=1.0a11, right now pip also install the 1.2b3 release.

pip install rio-color -t test_install
Collecting rio-color
  Using cached rio_color-1.0.1-cp38-cp38-macosx_10_9_x86_64.whl (88 kB)
Collecting click<8,>=4.0
  Using cached click-7.1.2-py2.py3-none-any.whl (82 kB)
Collecting rasterio>=1.0a11
  Using cached rasterio-1.2b3-cp38-cp38-macosx_10_9_x86_64.whl (20.5 MB)
Collecting cligj>=0.5
  Using cached cligj-0.7.1-py3-none-any.whl (7.1 kB)
Collecting snuggs>=1.4.1
  Using cached snuggs-1.4.7-py3-none-any.whl (5.4 kB)
Collecting pyparsing>=2.1.6
  Using cached pyparsing-2.4.7-py2.py3-none-any.whl (67 kB)
Collecting affine
  Using cached affine-2.3.0-py2.py3-none-any.whl (15 kB)
Collecting attrs
  Using cached attrs-20.3.0-py2.py3-none-any.whl (49 kB)
Collecting certifi
  Using cached certifi-2020.12.5-py2.py3-none-any.whl (147 kB)
Collecting click-plugins
  Using cached click_plugins-1.1.1-py2.py3-none-any.whl (7.5 kB)
Collecting numpy
  Using cached numpy-1.19.5-cp38-cp38-macosx_10_9_x86_64.whl (15.6 MB)
Collecting rio-mucho
  Using cached rio_mucho-1.0.0-py3-none-any.whl (5.8 kB)
Installing collected packages: pyparsing, numpy, click, snuggs, cligj, click-plugins, certifi, attrs, affine, rasterio, rio-mucho, rio-color
fio-extent 0.0.1 requires enum34, which is not installed.
Successfully installed affine-2.3.0 attrs-20.3.0 certifi-2020.12.5 click-7.1.2 click-plugins-1.1.1 cligj-0.7.1 numpy-1.19.5 pyparsing-2.4.7 rasterio-1.2b3 rio-color-1.0.1 rio-mucho-1.0.0 snuggs-1.4.7

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.