2014-06-05 15:12:49 +00:00
|
|
|
#include "Canvas.h"
|
|
|
|
|
|
|
|
#include <cassert>
|
|
|
|
|
2014-06-10 13:13:16 +00:00
|
|
|
#include "CanvasPortion.h"
|
|
|
|
#include "CanvasPreview.h"
|
2014-08-21 10:36:28 +00:00
|
|
|
#include "CanvasPictureWriter.h"
|
2014-06-10 13:13:16 +00:00
|
|
|
|
2014-08-21 13:30:09 +00:00
|
|
|
#define CUTTER_SIZE 800
|
|
|
|
|
2015-11-09 21:30:46 +00:00
|
|
|
Canvas::Canvas() {
|
2014-06-05 15:12:49 +00:00
|
|
|
horizontal_portion_count = 1;
|
|
|
|
vertical_portion_count = 1;
|
|
|
|
width = 1;
|
|
|
|
height = 1;
|
2014-08-21 07:58:11 +00:00
|
|
|
portions.push_back(new CanvasPortion);
|
2014-06-10 13:13:16 +00:00
|
|
|
|
2014-06-12 15:45:59 +00:00
|
|
|
preview = new CanvasPreview;
|
2014-06-05 15:12:49 +00:00
|
|
|
}
|
|
|
|
|
2015-11-09 21:30:46 +00:00
|
|
|
Canvas::~Canvas() {
|
|
|
|
for (auto portion : portions) {
|
2014-06-05 15:12:49 +00:00
|
|
|
delete portion;
|
|
|
|
}
|
2014-06-10 13:13:16 +00:00
|
|
|
delete preview;
|
2014-06-05 15:12:49 +00:00
|
|
|
}
|
|
|
|
|
2015-11-09 21:30:46 +00:00
|
|
|
void Canvas::setSize(int width, int height) {
|
2014-08-21 13:30:09 +00:00
|
|
|
horizontal_portion_count = 1 + (width - 1) / CUTTER_SIZE;
|
|
|
|
vertical_portion_count = 1 + (height - 1) / CUTTER_SIZE;
|
2014-06-05 15:12:49 +00:00
|
|
|
|
|
|
|
int portion_width = width / horizontal_portion_count;
|
|
|
|
int portion_height = height / vertical_portion_count;
|
|
|
|
|
2015-11-09 21:30:46 +00:00
|
|
|
for (auto portion : portions) {
|
2014-06-05 15:12:49 +00:00
|
|
|
delete portion;
|
|
|
|
}
|
|
|
|
portions.clear();
|
|
|
|
|
|
|
|
int done_width = 0;
|
|
|
|
int done_height = 0;
|
2014-08-21 07:58:11 +00:00
|
|
|
int index = 0;
|
2014-06-05 15:12:49 +00:00
|
|
|
|
2015-11-09 21:30:46 +00:00
|
|
|
for (int y = 0; y < vertical_portion_count; y++) {
|
2014-06-05 15:12:49 +00:00
|
|
|
done_width = 0;
|
2015-11-09 21:30:46 +00:00
|
|
|
for (int x = 0; x < horizontal_portion_count; x++) {
|
2014-08-21 07:58:11 +00:00
|
|
|
CanvasPortion *portion = new CanvasPortion(index++, preview);
|
2014-06-05 15:12:49 +00:00
|
|
|
|
|
|
|
portion->setSize((x == horizontal_portion_count - 1) ? width - done_width : portion_width,
|
2015-11-09 21:30:46 +00:00
|
|
|
(y == vertical_portion_count - 1) ? height - done_height : portion_height, done_width,
|
2014-08-18 15:33:15 +00:00
|
|
|
done_height);
|
2014-06-05 15:12:49 +00:00
|
|
|
|
|
|
|
done_width += portion->getWidth();
|
2015-11-09 21:30:46 +00:00
|
|
|
if (x == horizontal_portion_count - 1) {
|
2014-06-05 15:12:49 +00:00
|
|
|
done_height += portion->getHeight();
|
|
|
|
}
|
|
|
|
|
|
|
|
portions.push_back(portion);
|
|
|
|
}
|
|
|
|
assert(done_width == width);
|
|
|
|
}
|
|
|
|
assert(done_height == height);
|
|
|
|
|
|
|
|
this->width = width;
|
|
|
|
this->height = height;
|
2014-06-10 13:13:16 +00:00
|
|
|
|
2014-08-18 15:16:17 +00:00
|
|
|
// Smaller preview
|
2015-11-09 21:30:46 +00:00
|
|
|
while (width > 1000 or height > 700) {
|
2014-08-18 15:16:17 +00:00
|
|
|
width = width / 2;
|
|
|
|
height = height / 2;
|
|
|
|
}
|
|
|
|
preview->setSize(this->width, this->height, width, height);
|
2014-06-05 15:12:49 +00:00
|
|
|
}
|
|
|
|
|
2015-11-09 21:30:46 +00:00
|
|
|
CanvasPortion *Canvas::at(int x, int y) const {
|
2014-06-05 15:12:49 +00:00
|
|
|
assert(x >= 0 && x < horizontal_portion_count);
|
|
|
|
assert(y >= 0 && y < vertical_portion_count);
|
|
|
|
|
|
|
|
return portions[y * horizontal_portion_count + x];
|
|
|
|
}
|
2014-08-21 10:36:28 +00:00
|
|
|
|
2015-11-09 21:30:46 +00:00
|
|
|
CanvasPortion *Canvas::atPixel(int x, int y) const {
|
2014-08-21 10:36:28 +00:00
|
|
|
assert(x >= 0 && x < width);
|
|
|
|
assert(y >= 0 && y < height);
|
|
|
|
|
|
|
|
int pwidth = portions[0]->getWidth();
|
|
|
|
int pheight = portions[0]->getHeight();
|
|
|
|
|
2014-08-21 20:23:04 +00:00
|
|
|
int px = x / pwidth;
|
|
|
|
int py = y / pheight;
|
|
|
|
|
2015-11-09 21:30:46 +00:00
|
|
|
if (px >= horizontal_portion_count) {
|
2014-08-21 20:23:04 +00:00
|
|
|
px = horizontal_portion_count - 1;
|
|
|
|
}
|
2015-11-09 21:30:46 +00:00
|
|
|
if (py >= vertical_portion_count) {
|
2014-08-21 20:23:04 +00:00
|
|
|
py = vertical_portion_count - 1;
|
|
|
|
}
|
|
|
|
|
|
|
|
return at(px, py);
|
2014-08-21 10:36:28 +00:00
|
|
|
}
|
|
|
|
|
2015-12-10 23:36:50 +00:00
|
|
|
bool Canvas::saveToDisk(const string &filepath, const ColorProfile &profile, int antialias) const {
|
2014-08-21 10:36:28 +00:00
|
|
|
assert(antialias >= 1);
|
|
|
|
|
|
|
|
CanvasPictureWriter writer(this);
|
|
|
|
writer.setColorProfile(profile);
|
|
|
|
writer.setAntialias(antialias);
|
|
|
|
return writer.saveCanvas(filepath);
|
|
|
|
}
|