closure.h
1.88 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
// Copyright (c) 2010 LearnBoost <tj@learnboost.com>
#pragma once
#include "Canvas.h"
#include <jpeglib.h>
#include <nan.h>
#include <png.h>
#include <stdint.h> // node < 7 uses libstdc++ on macOS which lacks complete c++11
#include <vector>
#ifndef PAGE_SIZE
#define PAGE_SIZE 4096
#endif
/*
* Image encoding closures.
*/
struct Closure {
std::vector<uint8_t> vec;
Nan::Callback cb;
Canvas* canvas = nullptr;
cairo_status_t status = CAIRO_STATUS_SUCCESS;
static cairo_status_t writeVec(void *c, const uint8_t *odata, unsigned len) {
Closure* closure = static_cast<Closure*>(c);
try {
closure->vec.insert(closure->vec.end(), odata, odata + len);
} catch (const std::bad_alloc &) {
return CAIRO_STATUS_NO_MEMORY;
}
return CAIRO_STATUS_SUCCESS;
}
Closure(Canvas* canvas) : canvas(canvas) {};
};
struct PdfSvgClosure : Closure {
PdfSvgClosure(Canvas* canvas) : Closure(canvas) {};
};
struct PngClosure : Closure {
uint32_t compressionLevel = 6;
uint32_t filters = PNG_ALL_FILTERS;
uint32_t resolution = 0; // 0 = unspecified
// Indexed PNGs:
uint32_t nPaletteColors = 0;
uint8_t* palette = nullptr;
uint8_t backgroundIndex = 0;
PngClosure(Canvas* canvas) : Closure(canvas) {};
};
struct JpegClosure : Closure {
uint32_t quality = 75;
uint32_t chromaSubsampling = 2;
bool progressive = false;
jpeg_destination_mgr* jpeg_dest_mgr = nullptr;
static void init_destination(j_compress_ptr cinfo);
static boolean empty_output_buffer(j_compress_ptr cinfo);
static void term_destination(j_compress_ptr cinfo);
JpegClosure(Canvas* canvas) : Closure(canvas) {
jpeg_dest_mgr = new jpeg_destination_mgr;
jpeg_dest_mgr->init_destination = init_destination;
jpeg_dest_mgr->empty_output_buffer = empty_output_buffer;
jpeg_dest_mgr->term_destination = term_destination;
};
~JpegClosure() {
delete jpeg_dest_mgr;
}
};