Ejemplo n.º 1
0
int main(int argc, char **argv) {
    // The camera pipe is specialized on the 2592x1968 images that
    // come in, so we'll just use an image instead of a uniform image.
    ImageParam input(UInt(16), 2);
    ImageParam matrix_3200(Float(32), 2, "m3200"), matrix_7000(Float(32), 2, "m7000");
    Param<float> color_temp("color_temp"); //, 3200.0f);
    Param<float> gamma("gamma"); //, 1.8f);
    Param<float> contrast("contrast"); //, 10.0f);
    Param<int> blackLevel("blackLevel"); //, 25);
    Param<int> whiteLevel("whiteLevel"); //, 1023);

    // shift things inwards to give us enough padding on the
    // boundaries so that we don't need to check bounds. We're going
    // to make a 2560x1920 output image, just like the FCam pipe, so
    // shift by 16, 12. We also convert it to be signed, so we can deal
    // with values that fall below 0 during processing.
    Func shifted;
    shifted(x, y) = cast<int16_t>(input(x+16, y+12));

    // Parameterized output type, because LLVM PTX (GPU) backend does not
    // currently allow 8-bit computations
    int bit_width = atoi(argv[1]);
    Type result_type = UInt(bit_width);

    // Pick a target
    target = get_target_from_environment();

    // Build the pipeline
    Func processed = process(shifted, result_type, matrix_3200, matrix_7000,
                             color_temp, gamma, contrast, blackLevel, whiteLevel);

    std::vector<Argument> args = {color_temp, gamma, contrast, blackLevel, whiteLevel,
                                  input, matrix_3200, matrix_7000};
    // TODO: it would be more efficient to call compile_to() a single time with the right arguments
    processed.compile_to_static_library("curved", args, "curved", target);
    processed.compile_to_assembly("curved.s", args, target);

    return 0;
}
Ejemplo n.º 2
0
int main(int argc, char **argv) {

    // First define the function that gives the initial state.
    {
        Func initial;

        // The initial state is a quantity of two chemicals present at each pixel
        initial(x, y, c) = random_float();
        initial.compile_to_static_library("reaction_diffusion_init", {}, "reaction_diffusion_init");
    }

    // Then the function that updates the state. Also depends on user input.
    {
        ImageParam state(Float(32), 3);
        Param<int> mouse_x, mouse_y;
        Expr a = state(x, y, 0), b = state(x, y, 1);

        Func clamped = BoundaryConditions::repeat_edge(state);

        RDom kernel(-2, 5);
        Func g, gaussian;
        g(x) = exp(-x*x*0.3f);
        gaussian(x) = g(x) / sum(g(kernel));
        gaussian.compute_root();

        Func blur_x, blur_y;
        blur_x(x, y, c) = sum(gaussian(kernel) * clamped(x + kernel, y, c));
        blur_y(x, y, c) = sum(gaussian(kernel) * blur_x(x, y + kernel, c));

        // Diffusion
        Expr new_a = blur_y(x, y, 0);
        Expr new_b = blur_y(x, y, 1);

        // Reaction
        Expr f = 0.08f;
        Expr k = 0.16f;
        new_a += 0.4f * (a - a*a*a - b + k);
        new_b += 0.4f * f * (a - b);

        new_a = clamp(new_a, 0.0f, 1.0f);
        new_b = clamp(new_b, 0.0f, 1.0f);

        Func new_state;
        new_state(x, y, c) = select(c == 0, new_a, new_b);

        // Finally add some noise at the edges to keep things moving
        Expr r = lerp(-0.05f, 0.05f, random_float());
        new_state(x, 0, c) += r;
        new_state(x, 1023, c) += r;
        new_state(0, y, c) += r;
        new_state(1023, y, c) += r;

        new_state
            .vectorize(x, 4)
            .bound(c, 0, 2).unroll(c);

        Var yi;
        new_state.split(y, y, yi, 16).parallel(y);

        blur_x.store_at(new_state, y).compute_at(new_state, yi);
        blur_x.vectorize(x, 4);

        clamped.store_at(new_state, y).compute_at(new_state, yi);

        new_state.compile_to_static_library("reaction_diffusion_update", {state, mouse_x, mouse_y}, "reaction_diffusion_update");
    }

    // Now the function that converts the state into an argb image.
    {
        ImageParam state(Float(32), 3);

        Expr a = state(x, y, 0), b = state(x, y, 1);

        Expr alpha = 255 << 24;
        Expr red = cast<int32_t>(a * 255) * (1 << 16);
        Expr green = 0;
        Expr blue = cast<int32_t>(b * 255);

        Func render;
        render(x, y) = alpha + red + green + blue;

        render.vectorize(x, 4);
        Var yi;
        render.split(y, y, yi, 16).parallel(y);

        render.compile_to_static_library("reaction_diffusion_render", {state}, "reaction_diffusion_render");
    }

    return 0;
}