Merge lp:~alan-griffiths/mir/fix-1663130 into lp:mir
- fix-1663130
- Merge into development-branch
Proposed by
Alan Griffiths
Status: | Merged |
---|---|
Approved by: | Chris Halse Rogers |
Approved revision: | no longer in the source branch. |
Merged at revision: | 4205 |
Proposed branch: | lp:~alan-griffiths/mir/fix-1663130 |
Merge into: | lp:mir |
Diff against target: |
623 lines (+0/-599) 3 files modified
examples/CMakeLists.txt (+0/-23) examples/render_surfaces.cpp (+0/-468) examples/render_to_fb.cpp (+0/-108) |
To merge this branch: | bzr merge lp:~alan-griffiths/mir/fix-1663130 |
Related bugs: |
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
Chris Halse Rogers | Approve | ||
Mir CI Bot | continuous-integration | Approve | |
Review via email: mp+327420@code.launchpad.net |
Commit message
Remove obsolete & broken example code
Description of the change
To post a comment you must log in.
Revision history for this message
Mir CI Bot (mir-ci-bot) wrote : | # |
review:
Approve
(continuous-integration)
Revision history for this message
Chris Halse Rogers (raof) wrote : | # |
Yup, that's not code we want to support.
review:
Approve
Preview Diff
[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1 | === modified file 'examples/CMakeLists.txt' | |||
2 | --- examples/CMakeLists.txt 2017-06-06 16:26:18 +0000 | |||
3 | +++ examples/CMakeLists.txt 2017-07-14 11:41:27 +0000 | |||
4 | @@ -1,15 +1,3 @@ | |||
5 | 1 | mir_add_wrapped_executable(mir_demo_standalone_render_surfaces | ||
6 | 2 | render_surfaces.cpp | ||
7 | 3 | buffer_render_target.cpp | ||
8 | 4 | image_renderer.cpp | ||
9 | 5 | ) | ||
10 | 6 | |||
11 | 7 | target_link_libraries(mir_demo_standalone_render_surfaces | ||
12 | 8 | mirserver | ||
13 | 9 | exampleserverconfig | ||
14 | 10 | ${Boost_LIBRARIES} | ||
15 | 11 | ) | ||
16 | 12 | |||
17 | 13 | set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -std=c99 -Wall -fno-strict-aliasing -Wextra") | 1 | set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -std=c99 -Wall -fno-strict-aliasing -Wextra") |
18 | 14 | 2 | ||
19 | 15 | add_library(eglapp STATIC | 3 | add_library(eglapp STATIC |
20 | @@ -192,17 +180,6 @@ | |||
21 | 192 | ${GL_INCLUDE_DIRS} | 180 | ${GL_INCLUDE_DIRS} |
22 | 193 | ) | 181 | ) |
23 | 194 | 182 | ||
24 | 195 | mir_add_wrapped_executable(mir_demo_standalone_render_to_fb | ||
25 | 196 | render_to_fb.cpp | ||
26 | 197 | ) | ||
27 | 198 | |||
28 | 199 | target_link_libraries(mir_demo_standalone_render_to_fb | ||
29 | 200 | mirserver | ||
30 | 201 | mirdraw | ||
31 | 202 | ${GL_LIBRARIES} | ||
32 | 203 | ${Boost_LIBRARIES} | ||
33 | 204 | ) | ||
34 | 205 | |||
35 | 206 | add_library(mir_demo_server_loadable MODULE | 183 | add_library(mir_demo_server_loadable MODULE |
36 | 207 | server_example.cpp | 184 | server_example.cpp |
37 | 208 | glog_logger.cpp | 185 | glog_logger.cpp |
38 | 209 | 186 | ||
39 | === removed file 'examples/render_surfaces.cpp' | |||
40 | --- examples/render_surfaces.cpp 2017-05-08 03:04:26 +0000 | |||
41 | +++ examples/render_surfaces.cpp 1970-01-01 00:00:00 +0000 | |||
42 | @@ -1,468 +0,0 @@ | |||
43 | 1 | /* | ||
44 | 2 | * Copyright © 2012-2014 Canonical Ltd. | ||
45 | 3 | * | ||
46 | 4 | * This program is free software: you can redistribute it and/or modify | ||
47 | 5 | * it under the terms of the GNU General Public License version 3 as | ||
48 | 6 | * published by the Free Software Foundation. | ||
49 | 7 | * | ||
50 | 8 | * This program is distributed in the hope that it will be useful, | ||
51 | 9 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
52 | 10 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
53 | 11 | * GNU General Public License for more details. | ||
54 | 12 | * | ||
55 | 13 | * You should have received a copy of the GNU General Public License | ||
56 | 14 | * along with this program. If not, see <http://www.gnu.org/licenses/>. | ||
57 | 15 | * | ||
58 | 16 | * Authored by: Alexandros Frantzis <alexandros.frantzis@canonical.com> | ||
59 | 17 | */ | ||
60 | 18 | |||
61 | 19 | #include "server_example_input_event_filter.h" | ||
62 | 20 | #include "server_example_display_configuration_policy.h" | ||
63 | 21 | #include "mir/server_status_listener.h" | ||
64 | 22 | #include "mir/compositor/display_buffer_compositor.h" | ||
65 | 23 | #include "mir/compositor/display_buffer_compositor_factory.h" | ||
66 | 24 | #include "mir/scene/surface_creation_parameters.h" | ||
67 | 25 | #include "mir/geometry/size.h" | ||
68 | 26 | #include "mir/geometry/rectangles.h" | ||
69 | 27 | #include "mir/graphics/display.h" | ||
70 | 28 | #include "mir/graphics/display_buffer.h" | ||
71 | 29 | #include "mir/graphics/platform.h" | ||
72 | 30 | #include "mir/graphics/graphic_buffer_allocator.h" | ||
73 | 31 | #include "mir/options/option.h" | ||
74 | 32 | #include "mir/scene/surface.h" | ||
75 | 33 | #include "mir/scene/buffer_stream_factory.h" | ||
76 | 34 | #include "mir/scene/surface_factory.h" | ||
77 | 35 | #include "mir/shell/surface_stack.h" | ||
78 | 36 | #include "mir/frontend/buffer_sink.h" | ||
79 | 37 | #include "mir/frontend/client_buffers.h" | ||
80 | 38 | #include "mir/server.h" | ||
81 | 39 | #include "mir/report_exception.h" | ||
82 | 40 | #include "mir/renderer/gl/context.h" | ||
83 | 41 | #include "mir/renderer/gl/context_source.h" | ||
84 | 42 | |||
85 | 43 | #include "mir_image.h" | ||
86 | 44 | #include "buffer_render_target.h" | ||
87 | 45 | #include "image_renderer.h" | ||
88 | 46 | |||
89 | 47 | #define GLM_FORCE_RADIANS | ||
90 | 48 | #include <glm/gtc/matrix_transform.hpp> | ||
91 | 49 | |||
92 | 50 | #include <thread> | ||
93 | 51 | #include <atomic> | ||
94 | 52 | #include <chrono> | ||
95 | 53 | #include <csignal> | ||
96 | 54 | #include <iostream> | ||
97 | 55 | #include <sstream> | ||
98 | 56 | #include <vector> | ||
99 | 57 | |||
100 | 58 | namespace mg = mir::graphics; | ||
101 | 59 | namespace mc = mir::compositor; | ||
102 | 60 | namespace ms = mir::scene; | ||
103 | 61 | namespace mf = mir::frontend; | ||
104 | 62 | namespace mo = mir::options; | ||
105 | 63 | namespace msh = mir::shell; | ||
106 | 64 | namespace mi = mir::input; | ||
107 | 65 | namespace geom = mir::geometry; | ||
108 | 66 | namespace mt = mir::tools; | ||
109 | 67 | namespace me = mir::examples; | ||
110 | 68 | |||
111 | 69 | |||
112 | 70 | ///\page render_surfaces-example render_surfaces.cpp: A simple program using the mir library. | ||
113 | 71 | ///\tableofcontents | ||
114 | 72 | ///render_surfaces shows the use of mir to render some moving surfaces | ||
115 | 73 | ///\section main main() | ||
116 | 74 | /// The main() function uses a RenderSurfacesServerConfiguration to initialize and run mir. | ||
117 | 75 | /// \snippet render_surfaces.cpp main_tag | ||
118 | 76 | ///\section RenderSurfacesServerConfiguration RenderSurfacesServerConfiguration | ||
119 | 77 | /// The configuration stubs out client connectivity and input. | ||
120 | 78 | /// \snippet render_surfaces.cpp RenderSurfacesServerConfiguration_stubs_tag | ||
121 | 79 | /// it also provides a bespoke display buffer compositor | ||
122 | 80 | /// \snippet render_surfaces.cpp RenderSurfacesDisplayBufferCompositor_tag | ||
123 | 81 | ///\section Utilities Utility classes | ||
124 | 82 | /// For smooth animation we need to track time and move surfaces accordingly | ||
125 | 83 | ///\subsection StopWatch StopWatch | ||
126 | 84 | /// \snippet render_surfaces.cpp StopWatch_tag | ||
127 | 85 | ///\subsection Moveable Moveable | ||
128 | 86 | /// \snippet render_surfaces.cpp Moveable_tag | ||
129 | 87 | |||
130 | 88 | ///\example render_surfaces.cpp A simple program using the mir library. | ||
131 | 89 | |||
132 | 90 | namespace | ||
133 | 91 | { | ||
134 | 92 | std::atomic<bool> created{false}; | ||
135 | 93 | |||
136 | 94 | static const float min_alpha = 0.3f; | ||
137 | 95 | |||
138 | 96 | char const* const surfaces_to_render = "surfaces-to-render"; | ||
139 | 97 | |||
140 | 98 | auto as_context_source(mg::Display* display) | ||
141 | 99 | { | ||
142 | 100 | auto ctx = dynamic_cast<mir::renderer::gl::ContextSource*>(display->native_display()); | ||
143 | 101 | if (!ctx) | ||
144 | 102 | BOOST_THROW_EXCEPTION(std::logic_error("Display does not support GL rendering")); | ||
145 | 103 | return ctx; | ||
146 | 104 | } | ||
147 | 105 | |||
148 | 106 | ///\internal [StopWatch_tag] | ||
149 | 107 | // tracks elapsed time - for animation. | ||
150 | 108 | class StopWatch | ||
151 | 109 | { | ||
152 | 110 | public: | ||
153 | 111 | StopWatch() : start(std::chrono::high_resolution_clock::now()), | ||
154 | 112 | last(start), | ||
155 | 113 | now(last) | ||
156 | 114 | { | ||
157 | 115 | } | ||
158 | 116 | |||
159 | 117 | void stop() | ||
160 | 118 | { | ||
161 | 119 | now = std::chrono::high_resolution_clock::now(); | ||
162 | 120 | } | ||
163 | 121 | |||
164 | 122 | double elapsed_seconds_since_start() | ||
165 | 123 | { | ||
166 | 124 | auto elapsed = now - start; | ||
167 | 125 | float elapsed_sec = std::chrono::duration_cast<std::chrono::microseconds>(elapsed).count() / 1000000.0f; | ||
168 | 126 | return elapsed_sec; | ||
169 | 127 | } | ||
170 | 128 | |||
171 | 129 | double elapsed_seconds_since_last_restart() | ||
172 | 130 | { | ||
173 | 131 | auto elapsed = now - last; | ||
174 | 132 | float elapsed_sec = std::chrono::duration_cast<std::chrono::microseconds>(elapsed).count() / 1000000.0f; | ||
175 | 133 | return elapsed_sec; | ||
176 | 134 | } | ||
177 | 135 | |||
178 | 136 | void restart() | ||
179 | 137 | { | ||
180 | 138 | std::swap(last, now); | ||
181 | 139 | } | ||
182 | 140 | |||
183 | 141 | private: | ||
184 | 142 | std::chrono::high_resolution_clock::time_point start; | ||
185 | 143 | std::chrono::high_resolution_clock::time_point last; | ||
186 | 144 | std::chrono::high_resolution_clock::time_point now; | ||
187 | 145 | }; | ||
188 | 146 | ///\internal [StopWatch_tag] | ||
189 | 147 | |||
190 | 148 | ///\internal [Moveable_tag] | ||
191 | 149 | // Adapter to support movement of surfaces. | ||
192 | 150 | class Moveable | ||
193 | 151 | { | ||
194 | 152 | public: | ||
195 | 153 | Moveable() {} | ||
196 | 154 | Moveable(std::shared_ptr<ms::Surface> const& s, const geom::Size& display_size, | ||
197 | 155 | float dx, float dy, const glm::vec3& rotation_axis, float alpha_offset) | ||
198 | 156 | : surface(s), display_size(display_size), | ||
199 | 157 | x(s->top_left().x.as_int()), | ||
200 | 158 | y(s->top_left().y.as_int()), | ||
201 | 159 | w(s->size().width.as_int()), | ||
202 | 160 | h(s->size().height.as_int()), | ||
203 | 161 | dx{dx}, | ||
204 | 162 | dy{dy}, | ||
205 | 163 | rotation_axis(rotation_axis), | ||
206 | 164 | alpha_offset{alpha_offset} | ||
207 | 165 | { | ||
208 | 166 | } | ||
209 | 167 | |||
210 | 168 | void step() | ||
211 | 169 | { | ||
212 | 170 | stop_watch.stop(); | ||
213 | 171 | float elapsed_sec = stop_watch.elapsed_seconds_since_last_restart(); | ||
214 | 172 | float total_elapsed_sec = stop_watch.elapsed_seconds_since_start(); | ||
215 | 173 | stop_watch.restart(); | ||
216 | 174 | |||
217 | 175 | bool should_update = true; | ||
218 | 176 | float new_x = x + elapsed_sec * dx; | ||
219 | 177 | float new_y = y + elapsed_sec * dy; | ||
220 | 178 | if (new_x < 0.0 || new_x + w > display_size.width.as_uint32_t()) | ||
221 | 179 | { | ||
222 | 180 | dx = -dx; | ||
223 | 181 | should_update = false; | ||
224 | 182 | } | ||
225 | 183 | |||
226 | 184 | if (new_y < 0.0 || new_y + h > display_size.height.as_uint32_t()) | ||
227 | 185 | { | ||
228 | 186 | dy = -dy; | ||
229 | 187 | should_update = false; | ||
230 | 188 | } | ||
231 | 189 | |||
232 | 190 | if (should_update) | ||
233 | 191 | { | ||
234 | 192 | surface->move_to({new_x, new_y}); | ||
235 | 193 | x = new_x; | ||
236 | 194 | y = new_y; | ||
237 | 195 | } | ||
238 | 196 | |||
239 | 197 | glm::mat4 trans = glm::rotate(glm::mat4(1.0f), | ||
240 | 198 | glm::radians(total_elapsed_sec * 120.0f), | ||
241 | 199 | rotation_axis); | ||
242 | 200 | surface->set_transformation(trans); | ||
243 | 201 | |||
244 | 202 | float const alpha_amplitude = (1.0f - min_alpha) / 2.0f; | ||
245 | 203 | surface->set_alpha(min_alpha + alpha_amplitude + | ||
246 | 204 | alpha_amplitude * | ||
247 | 205 | sin(alpha_offset + 2 * M_PI * total_elapsed_sec / | ||
248 | 206 | 3.0)); | ||
249 | 207 | } | ||
250 | 208 | |||
251 | 209 | private: | ||
252 | 210 | std::shared_ptr<ms::Surface> surface; | ||
253 | 211 | geom::Size display_size; | ||
254 | 212 | float x; | ||
255 | 213 | float y; | ||
256 | 214 | float w; | ||
257 | 215 | float h; | ||
258 | 216 | float dx; | ||
259 | 217 | float dy; | ||
260 | 218 | StopWatch stop_watch; | ||
261 | 219 | glm::vec3 rotation_axis; | ||
262 | 220 | float alpha_offset; | ||
263 | 221 | }; | ||
264 | 222 | ///\internal [Moveable_tag] | ||
265 | 223 | |||
266 | 224 | void callback_when_started(mir::Server& server, std::function<void()> callback) | ||
267 | 225 | { | ||
268 | 226 | struct ServerStatusListener : mir::ServerStatusListener | ||
269 | 227 | { | ||
270 | 228 | ServerStatusListener(std::function<void()> callback) : | ||
271 | 229 | callback(callback) {} | ||
272 | 230 | |||
273 | 231 | virtual void paused() override {} | ||
274 | 232 | virtual void resumed() override {} | ||
275 | 233 | virtual void started() override {callback(); callback = []{}; } | ||
276 | 234 | virtual void ready_for_user_input() override {} | ||
277 | 235 | virtual void stop_receiving_input() override {} | ||
278 | 236 | |||
279 | 237 | std::function<void()> callback; | ||
280 | 238 | }; | ||
281 | 239 | |||
282 | 240 | server.override_the_server_status_listener([callback] | ||
283 | 241 | { | ||
284 | 242 | return std::make_shared<ServerStatusListener>(callback); | ||
285 | 243 | }); | ||
286 | 244 | } | ||
287 | 245 | |||
288 | 246 | ///\internal [RenderSurfacesServerConfiguration_stubs_tag] | ||
289 | 247 | class RenderSurfacesDisplayBufferCompositor : public mc::DisplayBufferCompositor | ||
290 | 248 | { | ||
291 | 249 | public: | ||
292 | 250 | RenderSurfacesDisplayBufferCompositor( | ||
293 | 251 | std::unique_ptr<DisplayBufferCompositor> db_compositor, | ||
294 | 252 | std::vector<Moveable>& moveables) | ||
295 | 253 | : db_compositor{std::move(db_compositor)}, | ||
296 | 254 | moveables(moveables), | ||
297 | 255 | frames{0} | ||
298 | 256 | { | ||
299 | 257 | } | ||
300 | 258 | |||
301 | 259 | void composite(mc::SceneElementSequence&& scene_sequence) override | ||
302 | 260 | { | ||
303 | 261 | while (!created) std::this_thread::yield(); | ||
304 | 262 | stop_watch.stop(); | ||
305 | 263 | if (stop_watch.elapsed_seconds_since_last_restart() >= 1) | ||
306 | 264 | { | ||
307 | 265 | std::cout << "FPS: " << frames << " Frame Time: " << 1.0 / frames << std::endl; | ||
308 | 266 | frames = 0; | ||
309 | 267 | stop_watch.restart(); | ||
310 | 268 | } | ||
311 | 269 | |||
312 | 270 | db_compositor->composite(std::move(scene_sequence)); | ||
313 | 271 | |||
314 | 272 | for (auto& m : moveables) | ||
315 | 273 | m.step(); | ||
316 | 274 | |||
317 | 275 | frames++; | ||
318 | 276 | } | ||
319 | 277 | |||
320 | 278 | private: | ||
321 | 279 | std::unique_ptr<DisplayBufferCompositor> const db_compositor; | ||
322 | 280 | StopWatch stop_watch; | ||
323 | 281 | std::vector<Moveable>& moveables; | ||
324 | 282 | uint32_t frames; | ||
325 | 283 | }; | ||
326 | 284 | ///\internal [RenderSurfacesServerConfiguration_stubs_tag] | ||
327 | 285 | |||
328 | 286 | class RenderSurfacesDisplayBufferCompositorFactory : public mc::DisplayBufferCompositorFactory | ||
329 | 287 | { | ||
330 | 288 | public: | ||
331 | 289 | RenderSurfacesDisplayBufferCompositorFactory( | ||
332 | 290 | std::shared_ptr<mc::DisplayBufferCompositorFactory> const& factory, | ||
333 | 291 | std::vector<Moveable>& moveables) | ||
334 | 292 | : factory{factory}, | ||
335 | 293 | moveables(moveables) | ||
336 | 294 | { | ||
337 | 295 | } | ||
338 | 296 | |||
339 | 297 | std::unique_ptr<mc::DisplayBufferCompositor> create_compositor_for(mg::DisplayBuffer& display_buffer) | ||
340 | 298 | { | ||
341 | 299 | auto compositor = factory->create_compositor_for(display_buffer); | ||
342 | 300 | auto raw = new RenderSurfacesDisplayBufferCompositor( | ||
343 | 301 | std::move(compositor), moveables); | ||
344 | 302 | return std::unique_ptr<RenderSurfacesDisplayBufferCompositor>(raw); | ||
345 | 303 | } | ||
346 | 304 | |||
347 | 305 | private: | ||
348 | 306 | std::shared_ptr<mc::DisplayBufferCompositorFactory> const factory; | ||
349 | 307 | std::vector<Moveable>& moveables; | ||
350 | 308 | }; | ||
351 | 309 | |||
352 | 310 | ///\internal [RenderSurfacesServer_tag] | ||
353 | 311 | // Extend the default configuration to manage moveables. | ||
354 | 312 | class RenderSurfacesServer : private mir::Server | ||
355 | 313 | { | ||
356 | 314 | std::shared_ptr<mir::input::EventFilter> const quit_filter{me::make_quit_filter_for(*this)}; | ||
357 | 315 | public: | ||
358 | 316 | RenderSurfacesServer(int argc, char const** argv) | ||
359 | 317 | { | ||
360 | 318 | me::add_display_configuration_options_to(*this); | ||
361 | 319 | |||
362 | 320 | ///\internal [RenderSurfacesDisplayBufferCompositor_tag] | ||
363 | 321 | // Decorate the DefaultDisplayBufferCompositor in order to move surfaces. | ||
364 | 322 | wrap_display_buffer_compositor_factory([this](std::shared_ptr<mc::DisplayBufferCompositorFactory> const& wrapped) | ||
365 | 323 | { | ||
366 | 324 | return std::make_shared<RenderSurfacesDisplayBufferCompositorFactory>( | ||
367 | 325 | wrapped, | ||
368 | 326 | moveables); | ||
369 | 327 | }); | ||
370 | 328 | ///\internal [RenderSurfacesDisplayBufferCompositor_tag] | ||
371 | 329 | |||
372 | 330 | add_configuration_option(surfaces_to_render, "Number of surfaces to render", 5); | ||
373 | 331 | |||
374 | 332 | // Provide the command line and run the *this | ||
375 | 333 | set_command_line(argc, argv); | ||
376 | 334 | setenv("MIR_SERVER_NO_FILE", "", 1); | ||
377 | 335 | |||
378 | 336 | // If there's a server available, try connecting to it | ||
379 | 337 | if (auto const socket = getenv("MIR_SOCKET")) | ||
380 | 338 | setenv("MIR_SERVER_HOST_SOCKET", socket, 0); | ||
381 | 339 | |||
382 | 340 | // Unless the compositor starts before we create the surfaces it won't respond to | ||
383 | 341 | // the change notification that causes. | ||
384 | 342 | callback_when_started(*this, [this] { create_surfaces(); }); | ||
385 | 343 | |||
386 | 344 | apply_settings(); | ||
387 | 345 | } | ||
388 | 346 | |||
389 | 347 | using mir::Server::run; | ||
390 | 348 | using mir::Server::exited_normally; | ||
391 | 349 | |||
392 | 350 | // New function to initialize moveables with surfaces | ||
393 | 351 | void create_surfaces() | ||
394 | 352 | try | ||
395 | 353 | { | ||
396 | 354 | moveables.resize(get_options()->get<int>(surfaces_to_render)); | ||
397 | 355 | std::cout << "Rendering " << moveables.size() << " surfaces" << std::endl; | ||
398 | 356 | |||
399 | 357 | auto const display = the_display(); | ||
400 | 358 | auto const buffer_stream_factory = the_buffer_stream_factory(); | ||
401 | 359 | auto const gralloc = the_graphics_platform()->create_buffer_allocator(); | ||
402 | 360 | auto const surface_factory = the_surface_factory(); | ||
403 | 361 | auto const surface_stack = the_surface_stack(); | ||
404 | 362 | auto const gl_context = as_context_source(the_display().get())->create_gl_context(); | ||
405 | 363 | |||
406 | 364 | /* TODO: Get proper configuration */ | ||
407 | 365 | geom::Rectangles view_area; | ||
408 | 366 | display->for_each_display_sync_group([&](mg::DisplaySyncGroup& group) | ||
409 | 367 | { | ||
410 | 368 | group.for_each_display_buffer([&](mg::DisplayBuffer& db) | ||
411 | 369 | { | ||
412 | 370 | view_area.add(db.view_area()); | ||
413 | 371 | }); | ||
414 | 372 | }); | ||
415 | 373 | geom::Size const display_size{view_area.bounding_rectangle().size}; | ||
416 | 374 | uint32_t const surface_side{300}; | ||
417 | 375 | geom::Size const surface_size{surface_side, surface_side}; | ||
418 | 376 | |||
419 | 377 | float const angular_step = 2.0 * M_PI / moveables.size(); | ||
420 | 378 | float const w = display_size.width.as_uint32_t(); | ||
421 | 379 | float const h = display_size.height.as_uint32_t(); | ||
422 | 380 | auto const surface_pf = supported_pixel_formats()[0]; | ||
423 | 381 | |||
424 | 382 | int i = 0; | ||
425 | 383 | for (auto& m : moveables) | ||
426 | 384 | { | ||
427 | 385 | auto params = ms::a_surface() | ||
428 | 386 | .of_size(surface_size) | ||
429 | 387 | .of_pixel_format(surface_pf) | ||
430 | 388 | .of_buffer_usage(mg::BufferUsage::hardware); | ||
431 | 389 | mg::BufferProperties properties{params.size, params.pixel_format, params.buffer_usage}; | ||
432 | 390 | struct NullBufferSink : mf::BufferSink | ||
433 | 391 | { | ||
434 | 392 | void send_buffer(mf::BufferStreamId, mg::Buffer&, mg::BufferIpcMsgType) override {} | ||
435 | 393 | void add_buffer(mg::Buffer&) override {} | ||
436 | 394 | void remove_buffer(mg::Buffer&) override {} | ||
437 | 395 | void update_buffer(mg::Buffer&) override {} | ||
438 | 396 | void error_buffer(geom::Size, MirPixelFormat, std::string const&) override {} | ||
439 | 397 | }; | ||
440 | 398 | |||
441 | 399 | auto buffers = buffer_stream_factory->create_buffer_map(std::make_shared<NullBufferSink>()); | ||
442 | 400 | auto const stream = buffer_stream_factory->create_buffer_stream({}, buffers, properties); | ||
443 | 401 | auto const surface = surface_factory->create_surface( | ||
444 | 402 | {ms::StreamInfo{stream, {}, {}}}, params); | ||
445 | 403 | surface_stack->add_surface(surface, params.input_mode); | ||
446 | 404 | |||
447 | 405 | { | ||
448 | 406 | auto buffer = gralloc->alloc_buffer(properties); | ||
449 | 407 | |||
450 | 408 | { | ||
451 | 409 | gl_context->make_current(); | ||
452 | 410 | |||
453 | 411 | mt::ImageRenderer img_renderer{mir_image.pixel_data, | ||
454 | 412 | geom::Size{mir_image.width, mir_image.height}, | ||
455 | 413 | mir_image.bytes_per_pixel}; | ||
456 | 414 | mt::BufferRenderTarget brt{*buffer}; | ||
457 | 415 | brt.make_current(); | ||
458 | 416 | img_renderer.render(); | ||
459 | 417 | |||
460 | 418 | gl_context->release_current(); | ||
461 | 419 | } | ||
462 | 420 | surface->primary_buffer_stream()->submit_buffer(buffer); | ||
463 | 421 | } | ||
464 | 422 | |||
465 | 423 | /* | ||
466 | 424 | * Place each surface at a different starting location and give it a | ||
467 | 425 | * different speed, rotation and alpha offset. | ||
468 | 426 | */ | ||
469 | 427 | uint32_t const x = w * (0.5 + 0.25 * cos(i * angular_step)) - surface_side / 2.0; | ||
470 | 428 | uint32_t const y = h * (0.5 + 0.25 * sin(i * angular_step)) - surface_side / 2.0; | ||
471 | 429 | |||
472 | 430 | surface->move_to({x, y}); | ||
473 | 431 | m = Moveable(surface, display_size, | ||
474 | 432 | cos(0.1f + i * M_PI / 6.0f) * w / 3.0f, | ||
475 | 433 | sin(0.1f + i * M_PI / 6.0f) * h / 3.0f, | ||
476 | 434 | glm::vec3{(i % 3 == 0) * 1.0f, (i % 3 == 1) * 1.0f, (i % 3 == 2) * 1.0f}, | ||
477 | 435 | 2.0f * M_PI * cos(i)); | ||
478 | 436 | ++i; | ||
479 | 437 | } | ||
480 | 438 | |||
481 | 439 | created = true; | ||
482 | 440 | } | ||
483 | 441 | catch (...) | ||
484 | 442 | { | ||
485 | 443 | mir::report_exception(); | ||
486 | 444 | exit(EXIT_FAILURE); | ||
487 | 445 | } | ||
488 | 446 | |||
489 | 447 | private: | ||
490 | 448 | std::vector<Moveable> moveables; | ||
491 | 449 | }; | ||
492 | 450 | ///\internal [RenderSurfacesServer_tag] | ||
493 | 451 | } | ||
494 | 452 | |||
495 | 453 | int main(int argc, char const** argv) | ||
496 | 454 | try | ||
497 | 455 | { | ||
498 | 456 | ///\internal [main_tag] | ||
499 | 457 | RenderSurfacesServer render_surfaces{argc, argv}; | ||
500 | 458 | |||
501 | 459 | render_surfaces.run(); | ||
502 | 460 | |||
503 | 461 | return render_surfaces.exited_normally() ? EXIT_SUCCESS : EXIT_FAILURE; | ||
504 | 462 | ///\internal [main_tag] | ||
505 | 463 | } | ||
506 | 464 | catch (...) | ||
507 | 465 | { | ||
508 | 466 | mir::report_exception(); | ||
509 | 467 | return EXIT_FAILURE; | ||
510 | 468 | } | ||
511 | 469 | 0 | ||
512 | === removed file 'examples/render_to_fb.cpp' | |||
513 | --- examples/render_to_fb.cpp 2017-05-08 03:04:26 +0000 | |||
514 | +++ examples/render_to_fb.cpp 1970-01-01 00:00:00 +0000 | |||
515 | @@ -1,108 +0,0 @@ | |||
516 | 1 | /* | ||
517 | 2 | * Copyright © 2012-2014 Canonical Ltd. | ||
518 | 3 | * | ||
519 | 4 | * This program is free software: you can redistribute it and/or modify | ||
520 | 5 | * it under the terms of the GNU General Public License version 3 as | ||
521 | 6 | * published by the Free Software Foundation. | ||
522 | 7 | * | ||
523 | 8 | * This program is distributed in the hope that it will be useful, | ||
524 | 9 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
525 | 10 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
526 | 11 | * GNU General Public License for more details. | ||
527 | 12 | * | ||
528 | 13 | * You should have received a copy of the GNU General Public License | ||
529 | 14 | * along with this program. If not, see <http://www.gnu.org/licenses/>. | ||
530 | 15 | * | ||
531 | 16 | * Authored by: Kevin DuBois <kevin.dubois@canonical.com> | ||
532 | 17 | */ | ||
533 | 18 | |||
534 | 19 | #include "graphics.h" | ||
535 | 20 | #include "as_render_target.h" | ||
536 | 21 | |||
537 | 22 | #include "mir/server.h" | ||
538 | 23 | #include "mir/report_exception.h" | ||
539 | 24 | #include "mir/graphics/display.h" | ||
540 | 25 | #include "mir/graphics/display_buffer.h" | ||
541 | 26 | #include "mir/renderer/gl/render_target.h" | ||
542 | 27 | |||
543 | 28 | #include <csignal> | ||
544 | 29 | |||
545 | 30 | namespace mg=mir::graphics; | ||
546 | 31 | namespace mo=mir::options; | ||
547 | 32 | namespace me=mir::examples; | ||
548 | 33 | |||
549 | 34 | namespace | ||
550 | 35 | { | ||
551 | 36 | volatile std::sig_atomic_t running = true; | ||
552 | 37 | |||
553 | 38 | void signal_handler(int /*signum*/) | ||
554 | 39 | { | ||
555 | 40 | running = false; | ||
556 | 41 | } | ||
557 | 42 | } | ||
558 | 43 | |||
559 | 44 | void render_loop(mir::Server& server) | ||
560 | 45 | { | ||
561 | 46 | /* Set up graceful exit on SIGINT and SIGTERM */ | ||
562 | 47 | struct sigaction sa; | ||
563 | 48 | sa.sa_handler = signal_handler; | ||
564 | 49 | sa.sa_flags = 0; | ||
565 | 50 | sigemptyset(&sa.sa_mask); | ||
566 | 51 | |||
567 | 52 | sigaction(SIGINT, &sa, NULL); | ||
568 | 53 | sigaction(SIGTERM, &sa, NULL); | ||
569 | 54 | |||
570 | 55 | auto display = server.the_display(); | ||
571 | 56 | |||
572 | 57 | mir::draw::glAnimationBasic gl_animation; | ||
573 | 58 | |||
574 | 59 | display->for_each_display_sync_group([&](mg::DisplaySyncGroup& group) | ||
575 | 60 | { | ||
576 | 61 | group.for_each_display_buffer([&](mg::DisplayBuffer& buffer) | ||
577 | 62 | { | ||
578 | 63 | me::as_render_target(buffer)->make_current(); | ||
579 | 64 | gl_animation.init_gl(); | ||
580 | 65 | }); | ||
581 | 66 | }); | ||
582 | 67 | |||
583 | 68 | while (running) | ||
584 | 69 | { | ||
585 | 70 | display->for_each_display_sync_group([&](mg::DisplaySyncGroup& group) | ||
586 | 71 | { | ||
587 | 72 | group.for_each_display_buffer([&](mg::DisplayBuffer& buffer) | ||
588 | 73 | { | ||
589 | 74 | auto const render_target = me::as_render_target(buffer); | ||
590 | 75 | render_target->make_current(); | ||
591 | 76 | gl_animation.render_gl(); | ||
592 | 77 | render_target->swap_buffers(); | ||
593 | 78 | }); | ||
594 | 79 | group.post(); | ||
595 | 80 | }); | ||
596 | 81 | |||
597 | 82 | gl_animation.step(); | ||
598 | 83 | } | ||
599 | 84 | } | ||
600 | 85 | |||
601 | 86 | int main(int argc, char const** argv) | ||
602 | 87 | try | ||
603 | 88 | { | ||
604 | 89 | // We don't want to act as a server by providing an endpoint | ||
605 | 90 | setenv("MIR_SERVER_NO_FILE", "", 1); | ||
606 | 91 | |||
607 | 92 | // If there's a server available, try connecting to it | ||
608 | 93 | if (auto const socket = getenv("MIR_SOCKET")) | ||
609 | 94 | setenv("MIR_SERVER_HOST_SOCKET", socket, 0); | ||
610 | 95 | |||
611 | 96 | mir::Server server; | ||
612 | 97 | server.set_command_line(argc, argv); | ||
613 | 98 | server.apply_settings(); | ||
614 | 99 | |||
615 | 100 | render_loop(server); | ||
616 | 101 | |||
617 | 102 | return EXIT_SUCCESS; | ||
618 | 103 | } | ||
619 | 104 | catch (...) | ||
620 | 105 | { | ||
621 | 106 | mir::report_exception(); | ||
622 | 107 | return EXIT_FAILURE; | ||
623 | 108 | } |
PASSED: Continuous integration, rev:4205 /mir-jenkins. ubuntu. com/job/ mir-ci/ 3485/ /mir-jenkins. ubuntu. com/job/ build-mir/ 4760 /mir-jenkins. ubuntu. com/job/ build-0- fetch/4926 /mir-jenkins. ubuntu. com/job/ build-1- sourcepkg/ release= artful/ 4915 /mir-jenkins. ubuntu. com/job/ build-1- sourcepkg/ release= xenial/ 4915 /mir-jenkins. ubuntu. com/job/ build-1- sourcepkg/ release= zesty/4915 /mir-jenkins. ubuntu. com/job/ build-2- binpkg- mir/arch= amd64,compiler= clang,platform= mesa,release= artful/ 4797 /mir-jenkins. ubuntu. com/job/ build-2- binpkg- mir/arch= amd64,compiler= clang,platform= mesa,release= artful/ 4797/artifact/ output/ *zip*/output. zip /mir-jenkins. ubuntu. com/job/ build-2- binpkg- mir/arch= amd64,compiler= clang,platform= mesa,release= zesty/4797 /mir-jenkins. ubuntu. com/job/ build-2- binpkg- mir/arch= amd64,compiler= clang,platform= mesa,release= zesty/4797/ artifact/ output/ *zip*/output. zip /mir-jenkins. ubuntu. com/job/ build-2- binpkg- mir/arch= amd64,compiler= gcc,platform= mesa,release= artful/ 4797 /mir-jenkins. ubuntu. com/job/ build-2- binpkg- mir/arch= amd64,compiler= gcc,platform= mesa,release= artful/ 4797/artifact/ output/ *zip*/output. zip /mir-jenkins. ubuntu. com/job/ build-2- binpkg- mir/arch= amd64,compiler= gcc,platform= mesa,release= xenial/ 4797 /mir-jenkins. ubuntu. com/job/ build-2- binpkg- mir/arch= amd64,compiler= gcc,platform= mesa,release= xenial/ 4797/artifact/ output/ *zip*/output. zip /mir-jenkins. ubuntu. com/job/ build-2- binpkg- mir/arch= amd64,compiler= gcc,platform= mesa,release= zesty/4797 /mir-jenkins. ubuntu. com/job/ build-2- binpkg- mir/arch= amd64,compiler= gcc,platform= mesa,release= zesty/4797/ artifact/ output/ *zip*/output. zip /mir-jenkins. ubuntu. com/job/ build-2- binpkg- mir/arch= cross-armhf, compiler= gcc,platform= mesa,release= artful/ 4797 /mir-jenkins. ubuntu. com/job/ build-2- binpkg- mir/arch= cross-armhf, compiler= gcc,platform= mesa,release= artful/ 4797/artifact/ output/ *zip*/output. zip /mir-jenkins. ubuntu. com/job/ build-2- binpkg- mir/arch= cross-armhf, compiler= gcc,platform= mesa,release= zesty/4797 /mir-jenkins. ubuntu. com/job/ build-2- binpkg- mir/arch= cross-armhf, compiler= gcc,platform= mesa,release= zesty/4797/ artifact/ output/ *zip*/output. zip /mir-jenkins. ubuntu. com/job/ build-2- binpkg- mir/arch= i386,compiler= gcc,platform= mesa,release= xenial/ 4797 /mir-jenkins. ubuntu. com/job/ build-2- binpkg- mir/arch= i386,compiler= gcc,platform= mesa,release= xenial/ 4797/artifact/ output/ *zip*/output. zip
https:/
Executed test runs:
SUCCESS: https:/
SUCCESS: https:/
SUCCESS: https:/
SUCCESS: https:/
SUCCESS: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
Click here to trigger a rebuild: /mir-jenkins. ubuntu. com/job/ mir-ci/ 3485/rebuild
https:/