1 /* |
|
2 * LDForge: LDraw parts authoring CAD |
|
3 * Copyright (C) 2020 Teemu Piippo |
|
4 * |
|
5 * This program is free software: you can redistribute it and/or modify |
|
6 * it under the terms of the GNU General Public License as published by |
|
7 * the Free Software Foundation, either version 3 of the License, or |
|
8 * (at your option) any later version. |
|
9 * |
|
10 * This program is distributed in the hope that it will be useful, |
|
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of |
|
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
|
13 * GNU General Public License for more details. |
|
14 * |
|
15 * You should have received a copy of the GNU General Public License |
|
16 * along with this program. If not, see <http://www.gnu.org/licenses/>. |
|
17 */ |
|
18 |
|
19 #include "gridprogram.h" |
|
20 #include "partrenderer.h" |
|
21 |
|
22 constexpr char vertexShaderSource[] = R"( |
|
23 #version 330 core |
|
24 |
|
25 layout (location = 0) in vec2 in_position; |
|
26 uniform mat4 mvp; |
|
27 smooth out vec2 ex_uv; |
|
28 uniform mat4 grid; |
|
29 |
|
30 void main() |
|
31 { |
|
32 gl_Position = mvp * grid * vec4(in_position, 0.0, 1.0); |
|
33 ex_uv = in_position; |
|
34 } |
|
35 )"; |
|
36 |
|
37 constexpr char fragmentShaderSource[] = R"( |
|
38 #version 330 core |
|
39 |
|
40 out vec4 color; |
|
41 smooth in vec2 ex_uv; |
|
42 uniform vec4 gridColor; |
|
43 |
|
44 void main(void) |
|
45 { |
|
46 float dx = fract(ex_uv.y); |
|
47 float dy = fract(ex_uv.x); |
|
48 /* fade the grid towards extreme co-ordinates */ |
|
49 float d = (1.0f - 0.015 * max(abs(ex_uv.x), abs(ex_uv.y))); |
|
50 color = vec4(gridColor.xyz, gridColor.w * d); |
|
51 } |
|
52 )"; |
|
53 |
|
54 template<int extent> |
|
55 constexpr auto calcGridData() |
|
56 { |
|
57 std::array<glm::vec2, 8 * extent + 4> result; |
|
58 std::size_t ix = 0; |
|
59 for (int i = -extent; i <= extent; i += 1) { |
|
60 result[ix++] = {i, -extent}; |
|
61 result[ix++] = {i, extent}; |
|
62 } |
|
63 for (int i = -extent; i <= extent; i += 1) { |
|
64 result[ix++] = {-extent, i}; |
|
65 result[ix++] = {extent, i}; |
|
66 } |
|
67 return result; |
|
68 } |
|
69 |
|
70 void GridLayer::setGridMatrix(const glm::mat4& newGridMatrix) |
|
71 { |
|
72 this->gridMatrix = newGridMatrix; |
|
73 if (this->isInitialized) { |
|
74 this->shader.setUniformMatrix("grid", newGridMatrix); |
|
75 } |
|
76 } |
|
77 |
|
78 void GridLayer::setGridColor(const QColor& newGridColor) |
|
79 { |
|
80 this->gridColor = gl::colorToVector4(newGridColor); |
|
81 if (this->isInitialized) { |
|
82 this->shader.setUniformVector("gridColor", this->gridColor); |
|
83 } |
|
84 } |
|
85 |
|
86 void GridLayer::settingsChanged() |
|
87 { |
|
88 this->setGridColor(this->renderer->isDark() ? Qt::white : Qt::black); |
|
89 } |
|
90 |
|
91 void GridLayer::initializeGL() |
|
92 { |
|
93 this->shader.initialize( |
|
94 ::vertexShaderSource, |
|
95 ::fragmentShaderSource, |
|
96 QOpenGLBuffer::StaticDraw, |
|
97 { |
|
98 GLAttributeSpec{ |
|
99 .type = GL_FLOAT, |
|
100 .offset = 0, |
|
101 .tuplesize = 2, |
|
102 .stride = 0, |
|
103 }, |
|
104 } |
|
105 ); |
|
106 this->isInitialized = true; |
|
107 constexpr auto data = calcGridData<50>(); |
|
108 this->shader.setUniformVector("gridColor", this->gridColor); |
|
109 this->setGridMatrix(this->gridMatrix); |
|
110 this->settingsChanged(); |
|
111 this->shader.bufferData(data.data(), data.size(), sizeof data[0]); |
|
112 } |
|
113 |
|
114 void GridLayer::paintGL() |
|
115 { |
|
116 glLineWidth(1); |
|
117 glEnable(GL_BLEND); |
|
118 glLineStipple(1, 0x8888); |
|
119 glEnable(GL_LINE_STIPPLE); |
|
120 glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); |
|
121 this->shader.draw(GL_LINES); |
|
122 glDisable(GL_BLEND); |
|
123 glDisable(GL_LINE_STIPPLE); |
|
124 } |
|
125 |
|
126 void GridLayer::mvpMatrixChanged(const glm::mat4& mvpMatrix) |
|
127 { |
|
128 this->shader.setMvpMatrix(mvpMatrix); |
|
129 } |
|