Ejemplo n.º 1
0
void WriteImage(const std::string &name, const Float *rgb,
                const Bounds2i &outputBounds, const Point2i &totalResolution,
                Float gamma) {
    if (name.size() >= 5) {
        size_t suffixOffset = name.size() - 4;
        if (!strcmp(name.c_str() + suffixOffset, ".exr") ||
            !strcmp(name.c_str() + suffixOffset, ".EXR")) {
            WriteImageEXR(name, rgb, outputBounds.pMax.x - outputBounds.pMin.x,
                          outputBounds.pMax.y - outputBounds.pMin.y,
                          totalResolution.x, totalResolution.y,
                          outputBounds.pMin.x, outputBounds.pMin.y);
            return;
        }
        if (!strcmp(name.c_str() + suffixOffset, ".pfm") ||
            !strcmp(name.c_str() + suffixOffset, ".PFM")) {
            Vector2i resolution = outputBounds.Diagonal();
            WriteImagePFM(name, rgb, resolution.x, resolution.y);
            return;
        }
        if (!strcmp(name.c_str() + suffixOffset, ".tga") ||
            !strcmp(name.c_str() + suffixOffset, ".TGA") ||
            !strcmp(name.c_str() + suffixOffset, ".png") ||
            !strcmp(name.c_str() + suffixOffset, ".PNG")) {
            // 8-bit formats; apply gamma
            Vector2i resolution = outputBounds.Diagonal();
            std::unique_ptr<uint8_t[]> rgb8(
                new uint8_t[3 * resolution.x * resolution.y]);
            uint8_t *dst = rgb8.get();
            for (int y = 0; y < resolution.y; ++y) {
                for (int x = 0; x < resolution.x; ++x) {
#define TO_BYTE(v) (uint8_t(Clamp(255.f * powf((v), 1.f / gamma), 0.f, 255.f)))
                    dst[0] = TO_BYTE(rgb[3 * (y * resolution.x + x) + 0]);
                    dst[1] = TO_BYTE(rgb[3 * (y * resolution.x + x) + 1]);
                    dst[2] = TO_BYTE(rgb[3 * (y * resolution.x + x) + 2]);
#undef TO_BYTE
                    dst += 3;
                }
            }

            if (!strcmp(name.c_str() + suffixOffset, ".tga") ||
                !strcmp(name.c_str() + suffixOffset, ".TGA"))
                WriteImageTGA(name, rgb8.get(),
                              outputBounds.pMax.x - outputBounds.pMin.x,
                              outputBounds.pMax.y - outputBounds.pMin.y,
                              totalResolution.x, totalResolution.y,
                              outputBounds.pMin.x, outputBounds.pMin.y);
            else if (stbi_write_png(name.c_str(), resolution.x, resolution.y, 3,
                                    rgb8.get(), 3 * resolution.x) == 0)
                Error("Error writing PNG \"%s\"", name.c_str());
            return;
        }
    }
    Error("Can't determine image file type from suffix of filename \"%s\"",
          name.c_str());
}
Ejemplo n.º 2
0
void WriteImage(const std::string &name, const Float *rgb,
                const Bounds2i &outputBounds, const Point2i &totalResolution) {
    Vector2i resolution = outputBounds.Diagonal();
    if (HasExtension(name, ".exr")) {
        WriteImageEXR(name, rgb, resolution.x, resolution.y, totalResolution.x,
                      totalResolution.y, outputBounds.pMin.x,
                      outputBounds.pMin.y);
    } else if (HasExtension(name, ".exr")) {
        WriteImagePFM(name, rgb, resolution.x, resolution.y);
    } else if (HasExtension(name, ".tga") || HasExtension(name, ".png")) {
        // 8-bit formats; apply gamma
        Vector2i resolution = outputBounds.Diagonal();
        std::unique_ptr<uint8_t[]> rgb8(
            new uint8_t[3 * resolution.x * resolution.y]);
        uint8_t *dst = rgb8.get();
        for (int y = 0; y < resolution.y; ++y) {
            for (int x = 0; x < resolution.x; ++x) {
#define TO_BYTE(v) (uint8_t) Clamp(255.f * GammaCorrect(v) + 0.5f, 0.f, 255.f)
                dst[0] = TO_BYTE(rgb[3 * (y * resolution.x + x) + 0]);
                dst[1] = TO_BYTE(rgb[3 * (y * resolution.x + x) + 1]);
                dst[2] = TO_BYTE(rgb[3 * (y * resolution.x + x) + 2]);
#undef TO_BYTE
                dst += 3;
            }
        }

        if (HasExtension(name, ".tga"))
            WriteImageTGA(
                name, rgb8.get(), outputBounds.pMax.x - outputBounds.pMin.x,
                outputBounds.pMax.y - outputBounds.pMin.y, totalResolution.x,
                totalResolution.y, outputBounds.pMin.x, outputBounds.pMin.y);
        else if (stbi_write_png(name.c_str(), resolution.x, resolution.y, 3,
                                rgb8.get(), 3 * resolution.x) == 0)
            Error("Error writing PNG \"%s\"", name.c_str());
    } else {
        Error("Can't determine image file type from suffix of filename \"%s\"",
              name.c_str());
    }
}