Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include <GL/glew.h>
- #include <GLFW/glfw3.h>
- #include <cstdio>
- #include <iostream>
- #include <vector>
- #include <math.h>
- #include <algorithm>
- #include <set>
- using namespace std;
- struct point {
- int x, y;
- bool operator==(const point &p) const {
- return (x == p.x) && (y == p.y);
- }
- };
- struct edge {
- point first, second;
- bool operator<(const edge &e) const {
- return first.y < e.first.y;
- }
- void resize(float kW, float kH) {
- first.x *= kW;
- first.y *= kH;
- second.x *= kW;
- second.y *= kH;
- }
- };
- GLint windowWidth, windowHeight;
- const unsigned int bcolor = 0x000c1d3d, dcolor = 0x00AD0255;
- point v0;
- vector <edge> edg;
- vector <unsigned int> pixels(1024 * 620);
- vector <unsigned int> oldp;
- bool f = false;
- void drawRustFill(GLFWwindow *window) {
- vector<edge> ESY = edg;
- sort(ESY.begin(), ESY.end());
- int go = 0;
- vector <edge> CAP;
- for (int i = 0; i < windowHeight; i++) {
- for (;go < ESY.size();)
- if (ESY[go].first.y == i) {
- CAP.push_back(ESY[go]);
- ++go;
- } else break;
- for (int j = 0; j < CAP.size(); j++)
- if (CAP[j].second.y == i)
- CAP.erase(CAP.begin() + j--);
- vector <int> xes;
- for (int j = 0; j < CAP.size(); j++) {
- edge e = CAP[j];
- if (e.second.y == e.first.y) break;
- else xes.push_back(e.first.x + (float)((float)(e.second.x - e.first.x) / (float)(e.second.y - e.first.y)) * (float)(i - e.first.y));
- }
- sort(xes.begin(), xes.end());
- for (int j = 1; j < xes.size(); j+=2)
- for (int k = xes[j-1]; k <= xes[j]; k++)
- pixels[(windowHeight - i - 1) * windowWidth + k] = dcolor;
- }
- oldp = pixels;
- }
- void filter(GLFWwindow * window) {
- if (f) {
- f = false;
- pixels = oldp;
- }
- else {
- vector <unsigned int> save = pixels;
- f = true;
- const unsigned int base[] = { 0, 1, 0, 1, 2, 1, 0, 1, 0 };
- for (int y = 1; y < windowHeight - 1; y++)
- for (int x = 1; x < windowWidth - 1; x++) {
- unsigned int c = 0;
- for (int i = x - 1; i <= x + 1; i++)
- for (int j = y - 1; j <= y + 1; j++) {
- for (unsigned int k = 0; k < 3; ++k)
- c += (unsigned int)((((pixels[i + j * windowWidth]) >> (k * 8)) % 256) * base[i - x + 1 + j - y + 1]/6 ) << (k * 8);
- c += (unsigned int)(((pixels[i + j * windowWidth]) >> (3 * 8)) * base[i - x + 1 + j - y + 1]/6 ) << (3 * 8);
- }
- save[x + y * windowWidth] = c;
- }
- pixels = save;
- }
- }
- void error(int error, const char * description) {
- fputs(description, stderr);
- }
- void key(GLFWwindow * window, int key, int scancode, int action, int mods) {
- if (key == GLFW_KEY_ESCAPE && action == GLFW_PRESS)
- glfwSetWindowShouldClose(window, GL_TRUE);
- if (key == GLFW_KEY_DELETE && action == GLFW_PRESS) {
- edg.clear();
- fill(pixels.begin(), pixels.end(), bcolor);
- }
- if (key == GLFW_KEY_ENTER && action == GLFW_PRESS)
- filter(window);
- }
- void mouseb(GLFWwindow * window, int button, int action, int mode) {
- if (button == GLFW_MOUSE_BUTTON_LEFT && action == GLFW_PRESS) {
- double xpos, ypos;
- glfwGetCursorPos(window, &xpos, &ypos);
- point p;
- p.x = xpos;
- p.y = ypos;
- edge e;
- if (!edg.empty()) {
- if (edg.at(edg.size() - 1).first == v0)
- edg.at(edg.size() - 1).first = p;
- else edg.at(edg.size() - 1).second = p;
- if (edg.at(edg.size() - 1).first.y > edg.at(edg.size() - 1).second.y)
- swap(edg.at(edg.size() - 1).first, edg.at(edg.size() - 1).second);
- e.first = p;
- e.second = v0;
- if (e.first.y > e.second.y)
- swap(e.first, e.second);
- } else {
- e.first = e.second = v0 = p;
- }
- edg.push_back(e);
- for (int i = 0; i < windowHeight; i++)
- for (int j = 0; j < windowWidth; j++)
- pixels[(windowHeight - i - 1) * windowWidth + j] = bcolor;
- drawRustFill(window);
- }
- }
- void resizeCallback(GLFWwindow* window, int W, int H) {
- int w = windowWidth, h = windowHeight;
- glfwGetWindowSize(window, &windowWidth, &windowHeight);
- float kW = (float)windowWidth / w;
- float kH = (float)windowHeight / h;
- for (int i = 0; i < edg.size(); i++)
- edg[i].resize(kW, kH);
- pixels.resize(windowWidth * windowHeight);
- v0.x *= kW;
- v0.y *= kH;
- fill(pixels.begin(), pixels.end(), bcolor);
- drawRustFill(window);
- glViewport(0, 0, windowWidth, windowHeight);
- }
- int main() {
- glfwSetErrorCallback(error);
- if (!glfwInit()) exit(1);
- GLFWwindow * window = glfwCreateWindow(800, 500, "Lab 4", NULL, NULL);
- if (!window) {
- glfwTerminate();
- exit(1);
- }
- glfwMakeContextCurrent(window);
- glfwSetKeyCallback(window, key);
- glfwSetMouseButtonCallback(window, mouseb);
- glfwSetWindowSizeCallback(window, resizeCallback);
- glfwGetWindowSize(window, &windowWidth, &windowHeight);
- while (!glfwWindowShouldClose(window)) {
- glClear(GL_COLOR_BUFFER_BIT);
- glDrawPixels(windowWidth, windowHeight, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8, pixels.data());
- glfwSwapBuffers(window);
- glfwPollEvents();
- }
- glfwDestroyWindow(window);
- glfwTerminate();
- return 0;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement