Giter Site home page Giter Site logo

vladasz / contour-rs Goto Github PK

View Code? Open in Web Editor NEW

This project forked from mthh/contour-rs

0.0 0.0 0.0 289 KB

Contour polygon creation in Rust (using marching squares algorithm)

Home Page: https://crates.io/crates/contour

License: Apache License 2.0

Rust 100.00%

contour-rs's Introduction

contour-rs

Build status GitHub Actions Build status Appveyor Docs.rs version

Computes isolines, contour polygons and isobands by applying marching squares to a rectangular array of numeric values.
Outputs ring coordinates or geo-types geometries.

The results can also easily be serialised to GeoJSON.

Note : The core of the algorithm is ported from d3-contour.


Usage

Add this to your Cargo.toml:

[dependencies]
contour = "0.12.0"

and this to your crate root:

extern crate contour;

The API exposes:

  • a ContourBuilder struct, which computes isorings coordinates for a Vec of threshold values and transform them either :

    • in Contours (a type containing the threshold value and the geometry as a MultiPolygon), or,
    • in Lines (a type containing the threshold value and the geometry as a MultiLineString).
    • in Bands (a type containing a minimum value, a maximum value and the geometry as a MultiPolygon).
  • a contour_rings function, which computes isorings coordinates for a single threshold value (returns a Vec of rings coordinates - this is what is used internally by the ContourBuilder).

ContourBuilder is the recommended way to use this crate, as it is more flexible and easier to use (it enables to specify the origin and the step of the grid, and to smooth the contours, while contour_rings only speak in grid coordinates and doesn't smooth the resulting rings).

Line, Contour and Band can be serialised to GeoJSON using the geojson feature.

Example:

Without defining origin and step:

let c = ContourBuilder::new(10, 10, false); // x dim., y dim., smoothing
let res = c.contours(&vec![
    0., 0., 0., 0., 0., 0., 0., 0., 0., 0.,
    0., 0., 0., 0., 0., 0., 0., 0., 0., 0.,
    0., 0., 0., 0., 0., 0., 0., 0., 0., 0.,
    0., 0., 0., 1., 1., 1., 0., 0., 0., 0.,
    0., 0., 0., 1., 1., 1., 0., 0., 0., 0.,
    0., 0., 0., 1., 1., 1., 0., 0., 0., 0.,
    0., 0., 0., 1., 1., 1., 0., 0., 0., 0.,
    0., 0., 0., 1., 1., 1., 0., 0., 0., 0.,
    0., 0., 0., 0., 0., 0., 0., 0., 0., 0.,
    0., 0., 0., 0., 0., 0., 0., 0., 0., 0.
], &[0.5])?; // values, thresholds

With origin and step

let c = ContourBuilder::new(10, 10, true) // x dim., y dim., smoothing
    .x_step(2) // The horizontal coordinate for the origin of the grid.
    .y_step(2) // The vertical coordinate for the origin of the grid.
    .x_origin(100) // The horizontal step for the grid
    .y_origin(200); // The vertical step for the grid

let res = c.contours(&[
0., 0., 0., 0., 0., 0., 0., 0., 0., 0.,
0., 0., 0., 0., 0., 0., 0., 0., 0., 0.,
0., 0., 0., 0., 0., 0., 0., 0., 0., 0.,
0., 0., 0., 1., 1., 0., 1., 0., 0., 0.,
0., 0., 0., 1., 1., 0., 1., 0., 0., 0.,
0., 0., 0., 1., 1., 0., 1., 0., 0., 0.,
0., 0., 0., 1., 1., 0., 1., 0., 0., 0.,
0., 0., 0., 1., 1., 0., 1., 0., 0., 0.,
0., 0., 0., 0., 0., 0., 0., 0., 0., 0.,
0., 0., 0., 0., 0., 0., 0., 0., 0., 0.
], &[0.5]).unwrap(); // values, thresholds

Using the geojson feature

The geojson feature is not enabled by default, so you need to specify it in your Cargo.toml:

[dependencies]
contour = { version = "0.12.0", features = ["geojson"] }
let c = ContourBuilder::new(10, 10, true) // x dim., y dim., smoothing
    .x_step(2) // The horizontal coordinate for the origin of the grid.
    .y_step(2) // The vertical coordinate for the origin of the grid.
    .x_origin(100) // The horizontal step for the grid
    .y_origin(200); // The vertical step for the grid

let res = c.contours(&[
0., 0., 0., 0., 0., 0., 0., 0., 0., 0.,
0., 0., 0., 0., 0., 0., 0., 0., 0., 0.,
0., 0., 0., 0., 0., 0., 0., 0., 0., 0.,
0., 0., 0., 1., 1., 0., 1., 0., 0., 0.,
0., 0., 0., 1., 1., 0., 1., 0., 0., 0.,
0., 0., 0., 1., 1., 0., 1., 0., 0., 0.,
0., 0., 0., 1., 1., 0., 1., 0., 0., 0.,
0., 0., 0., 1., 1., 0., 1., 0., 0., 0.,
0., 0., 0., 0., 0., 0., 0., 0., 0., 0.,
0., 0., 0., 0., 0., 0., 0., 0., 0., 0.
], &[0.5]).unwrap(); // values, thresholds
println!("{:?}", res[0].to_geojson()); // prints the GeoJSON representation of the first contour

Output:

Feature {
    bbox: None,
    geometry: Some(Geometry {
        bbox: None,
        value: MultiPolygon([
            [[
                [110.0, 215.0], [110.0, 213.0], [110.0, 211.0], [110.0, 209.0],
                [110.0, 207.0], [109.0, 206.0], [107.0, 206.0], [106.0, 207.0],
                [106.0, 209.0], [106.0, 211.0], [106.0, 213.0], [106.0, 215.0],
                [107.0, 216.0], [109.0, 216.0], [110.0, 215.0]
            ]],
            [[
                [114.0, 215.0], [114.0, 213.0], [114.0, 211.0], [114.0, 209.0],
                [114.0, 207.0], [113.0, 206.0], [112.0, 207.0], [112.0, 209.0],
                [112.0, 211.0], [112.0, 213.0], [112.0, 215.0], [113.0, 216.0],
                [114.0, 215.0]
            ]]
        ]),
        foreign_members: None
    }),
    id: None,
    properties: Some({"threshold": Number(0.5)}),
    foreign_members: None
}

Using the f32 feature

By default, this crate expects f64 values as input and uses f64 values for its computations. If you want to use f32 values instead, you need to specify the f32 feature in your Cargo.toml:

[dependencies]
contour = { version = "0.12.0", features = ["f32"] }

WASM demo

Demo of this crate compiled to WebAssembly and used from JavaScript : wasm_demo_contour.

Difference with the contour-isobands crate (from mthh/contour-isobands-rs repository)

While this crate computes isolines (cf. wikipedia:Marching_squares) from which it derives contour polygons (i.e. polygons that contain all points above the threshold defined for a given isoline) and isobands (i.e. polygons that contain all points between a minimum and a maximum bound), contour-isobands-rs is only dedicated to compute isobands and use a slightly different implementation of the marching squares algorithm for the disambiguation of saddle points (cf. wikipedia:Marching_squares).

License

Licensed under either of

at your option.

Contribution

Unless you explicitly state otherwise, any contribution intentionally submitted for inclusion in the work by you, as defined in the Apache-2.0 license, shall be dual licensed as above, without any additional terms or conditions.

contour-rs's People

Contributors

dabreegster avatar hakolao avatar michaelkirk avatar mthh avatar tversteeg avatar

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.