diff options
author | Armin Weatherwax | 2010-06-14 12:04:49 +0200 |
---|---|---|
committer | Armin Weatherwax | 2010-09-23 15:38:25 +0200 |
commit | 35df5441d3e2789663532c948731aff3a1e04728 (patch) | |
tree | ac7674289784a5f96106ea507637055a8dada78a /linden/indra/media_plugins/example | |
parent | Changed version to Experimental 2010.09.18 (diff) | |
download | meta-impy-35df5441d3e2789663532c948731aff3a1e04728.zip meta-impy-35df5441d3e2789663532c948731aff3a1e04728.tar.gz meta-impy-35df5441d3e2789663532c948731aff3a1e04728.tar.bz2 meta-impy-35df5441d3e2789663532c948731aff3a1e04728.tar.xz |
llmediaplugins first step
Diffstat (limited to 'linden/indra/media_plugins/example')
-rw-r--r-- | linden/indra/media_plugins/example/CMakeLists.txt | 74 | ||||
-rw-r--r-- | linden/indra/media_plugins/example/media_plugin_example.cpp | 488 |
2 files changed, 562 insertions, 0 deletions
diff --git a/linden/indra/media_plugins/example/CMakeLists.txt b/linden/indra/media_plugins/example/CMakeLists.txt new file mode 100644 index 0000000..4d82f27 --- /dev/null +++ b/linden/indra/media_plugins/example/CMakeLists.txt | |||
@@ -0,0 +1,74 @@ | |||
1 | # -*- cmake -*- | ||
2 | |||
3 | project(media_plugin_example) | ||
4 | |||
5 | include(00-Common) | ||
6 | include(LLCommon) | ||
7 | include(LLImage) | ||
8 | include(LLPlugin) | ||
9 | include(LLMath) | ||
10 | include(LLRender) | ||
11 | include(LLWindow) | ||
12 | include(Linking) | ||
13 | include(PluginAPI) | ||
14 | include(MediaPluginBase) | ||
15 | include(FindOpenGL) | ||
16 | |||
17 | include(ExamplePlugin) | ||
18 | |||
19 | include_directories( | ||
20 | ${LLPLUGIN_INCLUDE_DIRS} | ||
21 | ${MEDIA_PLUGIN_BASE_INCLUDE_DIRS} | ||
22 | ${LLCOMMON_INCLUDE_DIRS} | ||
23 | ${LLMATH_INCLUDE_DIRS} | ||
24 | ${LLIMAGE_INCLUDE_DIRS} | ||
25 | ${LLRENDER_INCLUDE_DIRS} | ||
26 | ${LLWINDOW_INCLUDE_DIRS} | ||
27 | ) | ||
28 | |||
29 | |||
30 | ### media_plugin_example | ||
31 | |||
32 | set(media_plugin_example_SOURCE_FILES | ||
33 | media_plugin_example.cpp | ||
34 | ) | ||
35 | |||
36 | add_library(media_plugin_example | ||
37 | SHARED | ||
38 | ${media_plugin_example_SOURCE_FILES} | ||
39 | ) | ||
40 | |||
41 | target_link_libraries(media_plugin_example | ||
42 | ${LLPLUGIN_LIBRARIES} | ||
43 | ${MEDIA_PLUGIN_BASE_LIBRARIES} | ||
44 | ${LLCOMMON_LIBRARIES} | ||
45 | ${EXAMPLE_PLUGIN_LIBRARIES} | ||
46 | ${PLUGIN_API_WINDOWS_LIBRARIES} | ||
47 | ) | ||
48 | |||
49 | add_dependencies(media_plugin_example | ||
50 | ${LLPLUGIN_LIBRARIES} | ||
51 | ${MEDIA_PLUGIN_BASE_LIBRARIES} | ||
52 | ${LLCOMMON_LIBRARIES} | ||
53 | ) | ||
54 | |||
55 | if (WINDOWS) | ||
56 | set_target_properties( | ||
57 | media_plugin_example | ||
58 | PROPERTIES | ||
59 | LINK_FLAGS "/MANIFEST:NO" | ||
60 | ) | ||
61 | endif (WINDOWS) | ||
62 | |||
63 | if (DARWIN) | ||
64 | # Don't prepend 'lib' to the executable name, and don't embed a full path in the library's install name | ||
65 | set_target_properties( | ||
66 | media_plugin_example | ||
67 | PROPERTIES | ||
68 | PREFIX "" | ||
69 | BUILD_WITH_INSTALL_RPATH 1 | ||
70 | INSTALL_NAME_DIR "@executable_path" | ||
71 | LINK_FLAGS "-exported_symbols_list ${CMAKE_CURRENT_SOURCE_DIR}/../base/media_plugin_base.exp" | ||
72 | ) | ||
73 | |||
74 | endif (DARWIN) \ No newline at end of file | ||
diff --git a/linden/indra/media_plugins/example/media_plugin_example.cpp b/linden/indra/media_plugins/example/media_plugin_example.cpp new file mode 100644 index 0000000..99e0199 --- /dev/null +++ b/linden/indra/media_plugins/example/media_plugin_example.cpp | |||
@@ -0,0 +1,488 @@ | |||
1 | /** | ||
2 | * @file media_plugin_example.cpp | ||
3 | * @brief Example plugin for LLMedia API plugin system | ||
4 | * | ||
5 | * $LicenseInfo:firstyear=2008&license=viewergpl$ | ||
6 | * | ||
7 | * Copyright (c) 2009, Linden Research, Inc. | ||
8 | * | ||
9 | * Second Life Viewer Source Code | ||
10 | * The source code in this file ("Source Code") is provided by Linden Lab | ||
11 | * to you under the terms of the GNU General Public License, version 2.0 | ||
12 | * ("GPL"), unless you have obtained a separate licensing agreement | ||
13 | * ("Other License"), formally executed by you and Linden Lab. Terms of | ||
14 | * the GPL can be found in doc/GPL-license.txt in this distribution, or | ||
15 | * online at http://secondlife.com/developers/opensource/gplv2 | ||
16 | * | ||
17 | * There are special exceptions to the terms and conditions of the GPL as | ||
18 | * it is applied to this Source Code. View the full text of the exception | ||
19 | * in the file doc/FLOSS-exception.txt in this software distribution, or | ||
20 | * online at http://secondlife.com/developers/opensource/flossexception | ||
21 | * | ||
22 | * By copying, modifying or distributing this software, you acknowledge | ||
23 | * that you have read and understood your obligations described above, | ||
24 | * and agree to abide by those obligations. | ||
25 | * | ||
26 | * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO | ||
27 | * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY, | ||
28 | * COMPLETENESS OR PERFORMANCE. | ||
29 | * $/LicenseInfo$ | ||
30 | */ | ||
31 | |||
32 | #include "linden_common.h" | ||
33 | |||
34 | #include "llgl.h" | ||
35 | #include "llplugininstance.h" | ||
36 | #include "llpluginmessage.h" | ||
37 | #include "llpluginmessageclasses.h" | ||
38 | #include "media_plugin_base.h" | ||
39 | |||
40 | #include <time.h> | ||
41 | |||
42 | //////////////////////////////////////////////////////////////////////////////// | ||
43 | // | ||
44 | class MediaPluginExample : | ||
45 | public MediaPluginBase | ||
46 | { | ||
47 | public: | ||
48 | MediaPluginExample( LLPluginInstance::sendMessageFunction host_send_func, void *host_user_data ); | ||
49 | ~MediaPluginExample(); | ||
50 | |||
51 | /*virtual*/ void receiveMessage( const char* message_string ); | ||
52 | |||
53 | private: | ||
54 | bool init(); | ||
55 | void update( F64 milliseconds ); | ||
56 | void write_pixel( int x, int y, unsigned char r, unsigned char g, unsigned char b ); | ||
57 | bool mFirstTime; | ||
58 | |||
59 | time_t mLastUpdateTime; | ||
60 | enum Constants { ENumObjects = 10 }; | ||
61 | unsigned char* mBackgroundPixels; | ||
62 | int mColorR[ ENumObjects ]; | ||
63 | int mColorG[ ENumObjects ]; | ||
64 | int mColorB[ ENumObjects ]; | ||
65 | int mXpos[ ENumObjects ]; | ||
66 | int mYpos[ ENumObjects ]; | ||
67 | int mXInc[ ENumObjects ]; | ||
68 | int mYInc[ ENumObjects ]; | ||
69 | int mBlockSize[ ENumObjects ]; | ||
70 | bool mMouseButtonDown; | ||
71 | bool mStopAction; | ||
72 | }; | ||
73 | |||
74 | //////////////////////////////////////////////////////////////////////////////// | ||
75 | // | ||
76 | MediaPluginExample::MediaPluginExample( LLPluginInstance::sendMessageFunction host_send_func, void *host_user_data ) : | ||
77 | MediaPluginBase( host_send_func, host_user_data ) | ||
78 | { | ||
79 | mFirstTime = true; | ||
80 | mWidth = 0; | ||
81 | mHeight = 0; | ||
82 | mDepth = 4; | ||
83 | mPixels = 0; | ||
84 | mMouseButtonDown = false; | ||
85 | mStopAction = false; | ||
86 | mLastUpdateTime = 0; | ||
87 | } | ||
88 | |||
89 | //////////////////////////////////////////////////////////////////////////////// | ||
90 | // | ||
91 | MediaPluginExample::~MediaPluginExample() | ||
92 | { | ||
93 | } | ||
94 | |||
95 | //////////////////////////////////////////////////////////////////////////////// | ||
96 | // | ||
97 | void MediaPluginExample::receiveMessage( const char* message_string ) | ||
98 | { | ||
99 | LLPluginMessage message_in; | ||
100 | |||
101 | if ( message_in.parse( message_string ) >= 0 ) | ||
102 | { | ||
103 | std::string message_class = message_in.getClass(); | ||
104 | std::string message_name = message_in.getName(); | ||
105 | |||
106 | if ( message_class == LLPLUGIN_MESSAGE_CLASS_BASE ) | ||
107 | { | ||
108 | if ( message_name == "init" ) | ||
109 | { | ||
110 | LLPluginMessage message( "base", "init_response" ); | ||
111 | LLSD versions = LLSD::emptyMap(); | ||
112 | versions[ LLPLUGIN_MESSAGE_CLASS_BASE ] = LLPLUGIN_MESSAGE_CLASS_BASE_VERSION; | ||
113 | versions[ LLPLUGIN_MESSAGE_CLASS_MEDIA ] = LLPLUGIN_MESSAGE_CLASS_MEDIA_VERSION; | ||
114 | versions[ LLPLUGIN_MESSAGE_CLASS_MEDIA_BROWSER ] = LLPLUGIN_MESSAGE_CLASS_MEDIA_BROWSER_VERSION; | ||
115 | message.setValueLLSD( "versions", versions ); | ||
116 | |||
117 | std::string plugin_version = "Example media plugin, Example Version 1.0.0.0"; | ||
118 | message.setValue( "plugin_version", plugin_version ); | ||
119 | sendMessage( message ); | ||
120 | |||
121 | // Plugin gets to decide the texture parameters to use. | ||
122 | message.setMessage( LLPLUGIN_MESSAGE_CLASS_MEDIA, "texture_params" ); | ||
123 | message.setValueS32( "default_width", mWidth ); | ||
124 | message.setValueS32( "default_height", mHeight ); | ||
125 | message.setValueS32( "depth", mDepth ); | ||
126 | message.setValueU32( "internalformat", GL_RGBA ); | ||
127 | message.setValueU32( "format", GL_RGBA ); | ||
128 | message.setValueU32( "type", GL_UNSIGNED_BYTE ); | ||
129 | message.setValueBoolean( "coords_opengl", false ); | ||
130 | sendMessage( message ); | ||
131 | } | ||
132 | else | ||
133 | if ( message_name == "idle" ) | ||
134 | { | ||
135 | // no response is necessary here. | ||
136 | F64 time = message_in.getValueReal( "time" ); | ||
137 | |||
138 | // Convert time to milliseconds for update() | ||
139 | update( time ); | ||
140 | } | ||
141 | else | ||
142 | if ( message_name == "cleanup" ) | ||
143 | { | ||
144 | // clean up here | ||
145 | } | ||
146 | else | ||
147 | if ( message_name == "shm_added" ) | ||
148 | { | ||
149 | SharedSegmentInfo info; | ||
150 | info.mAddress = message_in.getValuePointer( "address" ); | ||
151 | info.mSize = ( size_t )message_in.getValueS32( "size" ); | ||
152 | std::string name = message_in.getValue( "name" ); | ||
153 | |||
154 | mSharedSegments.insert( SharedSegmentMap::value_type( name, info ) ); | ||
155 | |||
156 | } | ||
157 | else | ||
158 | if ( message_name == "shm_remove" ) | ||
159 | { | ||
160 | std::string name = message_in.getValue( "name" ); | ||
161 | |||
162 | SharedSegmentMap::iterator iter = mSharedSegments.find( name ); | ||
163 | if( iter != mSharedSegments.end() ) | ||
164 | { | ||
165 | if ( mPixels == iter->second.mAddress ) | ||
166 | { | ||
167 | // This is the currently active pixel buffer. | ||
168 | // Make sure we stop drawing to it. | ||
169 | mPixels = NULL; | ||
170 | mTextureSegmentName.clear(); | ||
171 | }; | ||
172 | mSharedSegments.erase( iter ); | ||
173 | } | ||
174 | else | ||
175 | { | ||
176 | //std::cerr << "MediaPluginExample::receiveMessage: unknown shared memory region!" << std::endl; | ||
177 | }; | ||
178 | |||
179 | // Send the response so it can be cleaned up. | ||
180 | LLPluginMessage message( "base", "shm_remove_response" ); | ||
181 | message.setValue( "name", name ); | ||
182 | sendMessage( message ); | ||
183 | } | ||
184 | else | ||
185 | { | ||
186 | //std::cerr << "MediaPluginExample::receiveMessage: unknown base message: " << message_name << std::endl; | ||
187 | }; | ||
188 | } | ||
189 | else | ||
190 | if ( message_class == LLPLUGIN_MESSAGE_CLASS_MEDIA ) | ||
191 | { | ||
192 | if ( message_name == "size_change" ) | ||
193 | { | ||
194 | std::string name = message_in.getValue( "name" ); | ||
195 | S32 width = message_in.getValueS32( "width" ); | ||
196 | S32 height = message_in.getValueS32( "height" ); | ||
197 | S32 texture_width = message_in.getValueS32( "texture_width" ); | ||
198 | S32 texture_height = message_in.getValueS32( "texture_height" ); | ||
199 | |||
200 | if ( ! name.empty() ) | ||
201 | { | ||
202 | // Find the shared memory region with this name | ||
203 | SharedSegmentMap::iterator iter = mSharedSegments.find( name ); | ||
204 | if ( iter != mSharedSegments.end() ) | ||
205 | { | ||
206 | mPixels = ( unsigned char* )iter->second.mAddress; | ||
207 | mWidth = width; | ||
208 | mHeight = height; | ||
209 | |||
210 | mTextureWidth = texture_width; | ||
211 | mTextureHeight = texture_height; | ||
212 | |||
213 | init(); | ||
214 | }; | ||
215 | }; | ||
216 | |||
217 | LLPluginMessage message( LLPLUGIN_MESSAGE_CLASS_MEDIA, "size_change_response" ); | ||
218 | message.setValue( "name", name ); | ||
219 | message.setValueS32( "width", width ); | ||
220 | message.setValueS32( "height", height ); | ||
221 | message.setValueS32( "texture_width", texture_width ); | ||
222 | message.setValueS32( "texture_height", texture_height ); | ||
223 | sendMessage( message ); | ||
224 | } | ||
225 | else | ||
226 | if ( message_name == "load_uri" ) | ||
227 | { | ||
228 | std::string uri = message_in.getValue( "uri" ); | ||
229 | if ( ! uri.empty() ) | ||
230 | { | ||
231 | }; | ||
232 | } | ||
233 | else | ||
234 | if ( message_name == "mouse_event" ) | ||
235 | { | ||
236 | std::string event = message_in.getValue( "event" ); | ||
237 | S32 button = message_in.getValueS32( "button" ); | ||
238 | |||
239 | // left mouse button | ||
240 | if ( button == 0 ) | ||
241 | { | ||
242 | int mouse_x = message_in.getValueS32( "x" ); | ||
243 | int mouse_y = message_in.getValueS32( "y" ); | ||
244 | std::string modifiers = message_in.getValue( "modifiers" ); | ||
245 | |||
246 | if ( event == "move" ) | ||
247 | { | ||
248 | if ( mMouseButtonDown ) | ||
249 | write_pixel( mouse_x, mouse_y, rand() % 0x80 + 0x80, rand() % 0x80 + 0x80, rand() % 0x80 + 0x80 ); | ||
250 | } | ||
251 | else | ||
252 | if ( event == "down" ) | ||
253 | { | ||
254 | mMouseButtonDown = true; | ||
255 | } | ||
256 | else | ||
257 | if ( event == "up" ) | ||
258 | { | ||
259 | mMouseButtonDown = false; | ||
260 | } | ||
261 | else | ||
262 | if ( event == "double_click" ) | ||
263 | { | ||
264 | }; | ||
265 | }; | ||
266 | } | ||
267 | else | ||
268 | if ( message_name == "key_event" ) | ||
269 | { | ||
270 | std::string event = message_in.getValue( "event" ); | ||
271 | S32 key = message_in.getValueS32( "key" ); | ||
272 | std::string modifiers = message_in.getValue( "modifiers" ); | ||
273 | |||
274 | if ( event == "down" ) | ||
275 | { | ||
276 | if ( key == ' ') | ||
277 | { | ||
278 | mLastUpdateTime = 0; | ||
279 | update( 0.0f ); | ||
280 | }; | ||
281 | }; | ||
282 | } | ||
283 | else | ||
284 | { | ||
285 | //std::cerr << "MediaPluginExample::receiveMessage: unknown media message: " << message_string << std::endl; | ||
286 | }; | ||
287 | } | ||
288 | else | ||
289 | if ( message_class == LLPLUGIN_MESSAGE_CLASS_MEDIA_BROWSER ) | ||
290 | { | ||
291 | if ( message_name == "browse_reload" ) | ||
292 | { | ||
293 | mLastUpdateTime = 0; | ||
294 | mFirstTime = true; | ||
295 | mStopAction = false; | ||
296 | update( 0.0f ); | ||
297 | } | ||
298 | else | ||
299 | if ( message_name == "browse_stop" ) | ||
300 | { | ||
301 | for( int n = 0; n < ENumObjects; ++n ) | ||
302 | mXInc[ n ] = mYInc[ n ] = 0; | ||
303 | |||
304 | mStopAction = true; | ||
305 | update( 0.0f ); | ||
306 | } | ||
307 | else | ||
308 | { | ||
309 | //std::cerr << "MediaPluginExample::receiveMessage: unknown media_browser message: " << message_string << std::endl; | ||
310 | }; | ||
311 | } | ||
312 | else | ||
313 | { | ||
314 | //std::cerr << "MediaPluginExample::receiveMessage: unknown message class: " << message_class << std::endl; | ||
315 | }; | ||
316 | }; | ||
317 | } | ||
318 | |||
319 | //////////////////////////////////////////////////////////////////////////////// | ||
320 | // | ||
321 | void MediaPluginExample::write_pixel( int x, int y, unsigned char r, unsigned char g, unsigned char b ) | ||
322 | { | ||
323 | // make sure we don't write outside the buffer | ||
324 | if ( ( x < 0 ) || ( x >= mWidth ) || ( y < 0 ) || ( y >= mHeight ) ) | ||
325 | return; | ||
326 | |||
327 | if ( mBackgroundPixels != NULL ) | ||
328 | { | ||
329 | unsigned char *pixel = mBackgroundPixels; | ||
330 | pixel += y * mWidth * mDepth; | ||
331 | pixel += ( x * mDepth ); | ||
332 | pixel[ 0 ] = b; | ||
333 | pixel[ 1 ] = g; | ||
334 | pixel[ 2 ] = r; | ||
335 | |||
336 | setDirty( x, y, x + 1, y + 1 ); | ||
337 | }; | ||
338 | } | ||
339 | |||
340 | //////////////////////////////////////////////////////////////////////////////// | ||
341 | // | ||
342 | void MediaPluginExample::update( F64 milliseconds ) | ||
343 | { | ||
344 | if ( mWidth < 1 || mWidth > 2048 || mHeight < 1 || mHeight > 2048 ) | ||
345 | return; | ||
346 | |||
347 | if ( mPixels == 0 ) | ||
348 | return; | ||
349 | |||
350 | if ( mFirstTime ) | ||
351 | { | ||
352 | for( int n = 0; n < ENumObjects; ++n ) | ||
353 | { | ||
354 | mXpos[ n ] = ( mWidth / 2 ) + rand() % ( mWidth / 16 ) - ( mWidth / 32 ); | ||
355 | mYpos[ n ] = ( mHeight / 2 ) + rand() % ( mHeight / 16 ) - ( mHeight / 32 ); | ||
356 | |||
357 | mColorR[ n ] = rand() % 0x60 + 0x60; | ||
358 | mColorG[ n ] = rand() % 0x60 + 0x60; | ||
359 | mColorB[ n ] = rand() % 0x60 + 0x60; | ||
360 | |||
361 | mXInc[ n ] = 0; | ||
362 | while ( mXInc[ n ] == 0 ) | ||
363 | mXInc[ n ] = rand() % 7 - 3; | ||
364 | |||
365 | mYInc[ n ] = 0; | ||
366 | while ( mYInc[ n ] == 0 ) | ||
367 | mYInc[ n ] = rand() % 9 - 4; | ||
368 | |||
369 | mBlockSize[ n ] = rand() % 0x30 + 0x10; | ||
370 | }; | ||
371 | |||
372 | delete [] mBackgroundPixels; | ||
373 | |||
374 | mBackgroundPixels = new unsigned char[ mWidth * mHeight * mDepth ]; | ||
375 | |||
376 | mFirstTime = false; | ||
377 | }; | ||
378 | |||
379 | if ( mStopAction ) | ||
380 | return; | ||
381 | |||
382 | if ( time( NULL ) > mLastUpdateTime + 3 ) | ||
383 | { | ||
384 | const int num_squares = rand() % 20 + 4; | ||
385 | int sqr1_r = rand() % 0x80 + 0x20; | ||
386 | int sqr1_g = rand() % 0x80 + 0x20; | ||
387 | int sqr1_b = rand() % 0x80 + 0x20; | ||
388 | int sqr2_r = rand() % 0x80 + 0x20; | ||
389 | int sqr2_g = rand() % 0x80 + 0x20; | ||
390 | int sqr2_b = rand() % 0x80 + 0x20; | ||
391 | |||
392 | for ( int y1 = 0; y1 < num_squares; ++y1 ) | ||
393 | { | ||
394 | for ( int x1 = 0; x1 < num_squares; ++x1 ) | ||
395 | { | ||
396 | int px_start = mWidth * x1 / num_squares; | ||
397 | int px_end = ( mWidth * ( x1 + 1 ) ) / num_squares; | ||
398 | int py_start = mHeight * y1 / num_squares; | ||
399 | int py_end = ( mHeight * ( y1 + 1 ) ) / num_squares; | ||
400 | |||
401 | for( int y2 = py_start; y2 < py_end; ++y2 ) | ||
402 | { | ||
403 | for( int x2 = px_start; x2 < px_end; ++x2 ) | ||
404 | { | ||
405 | int rowspan = mWidth * mDepth; | ||
406 | |||
407 | if ( ( y1 % 2 ) ^ ( x1 % 2 ) ) | ||
408 | { | ||
409 | mBackgroundPixels[ y2 * rowspan + x2 * mDepth + 0 ] = sqr1_r; | ||
410 | mBackgroundPixels[ y2 * rowspan + x2 * mDepth + 1 ] = sqr1_g; | ||
411 | mBackgroundPixels[ y2 * rowspan + x2 * mDepth + 2 ] = sqr1_b; | ||
412 | } | ||
413 | else | ||
414 | { | ||
415 | mBackgroundPixels[ y2 * rowspan + x2 * mDepth + 0 ] = sqr2_r; | ||
416 | mBackgroundPixels[ y2 * rowspan + x2 * mDepth + 1 ] = sqr2_g; | ||
417 | mBackgroundPixels[ y2 * rowspan + x2 * mDepth + 2 ] = sqr2_b; | ||
418 | }; | ||
419 | }; | ||
420 | }; | ||
421 | }; | ||
422 | }; | ||
423 | |||
424 | time( &mLastUpdateTime ); | ||
425 | }; | ||
426 | |||
427 | memcpy( mPixels, mBackgroundPixels, mWidth * mHeight * mDepth ); | ||
428 | |||
429 | for( int n = 0; n < ENumObjects; ++n ) | ||
430 | { | ||
431 | if ( rand() % 50 == 0 ) | ||
432 | { | ||
433 | mXInc[ n ] = 0; | ||
434 | while ( mXInc[ n ] == 0 ) | ||
435 | mXInc[ n ] = rand() % 7 - 3; | ||
436 | |||
437 | mYInc[ n ] = 0; | ||
438 | while ( mYInc[ n ] == 0 ) | ||
439 | mYInc[ n ] = rand() % 9 - 4; | ||
440 | }; | ||
441 | |||
442 | if ( mXpos[ n ] + mXInc[ n ] < 0 || mXpos[ n ] + mXInc[ n ] >= mWidth - mBlockSize[ n ] ) | ||
443 | mXInc[ n ] =- mXInc[ n ]; | ||
444 | |||
445 | if ( mYpos[ n ] + mYInc[ n ] < 0 || mYpos[ n ] + mYInc[ n ] >= mHeight - mBlockSize[ n ] ) | ||
446 | mYInc[ n ] =- mYInc[ n ]; | ||
447 | |||
448 | mXpos[ n ] += mXInc[ n ]; | ||
449 | mYpos[ n ] += mYInc[ n ]; | ||
450 | |||
451 | for( int y = 0; y < mBlockSize[ n ]; ++y ) | ||
452 | { | ||
453 | for( int x = 0; x < mBlockSize[ n ]; ++x ) | ||
454 | { | ||
455 | mPixels[ ( mXpos[ n ] + x ) * mDepth + ( mYpos[ n ] + y ) * mDepth * mWidth + 0 ] = mColorR[ n ]; | ||
456 | mPixels[ ( mXpos[ n ] + x ) * mDepth + ( mYpos[ n ] + y ) * mDepth * mWidth + 1 ] = mColorG[ n ]; | ||
457 | mPixels[ ( mXpos[ n ] + x ) * mDepth + ( mYpos[ n ] + y ) * mDepth * mWidth + 2 ] = mColorB[ n ]; | ||
458 | }; | ||
459 | }; | ||
460 | }; | ||
461 | |||
462 | setDirty( 0, 0, mWidth, mHeight ); | ||
463 | }; | ||
464 | |||
465 | //////////////////////////////////////////////////////////////////////////////// | ||
466 | // | ||
467 | bool MediaPluginExample::init() | ||
468 | { | ||
469 | LLPluginMessage message( LLPLUGIN_MESSAGE_CLASS_MEDIA, "name_text" ); | ||
470 | message.setValue( "name", "Example Plugin" ); | ||
471 | sendMessage( message ); | ||
472 | |||
473 | return true; | ||
474 | }; | ||
475 | |||
476 | //////////////////////////////////////////////////////////////////////////////// | ||
477 | // | ||
478 | int init_media_plugin( LLPluginInstance::sendMessageFunction host_send_func, | ||
479 | void* host_user_data, | ||
480 | LLPluginInstance::sendMessageFunction *plugin_send_func, | ||
481 | void **plugin_user_data ) | ||
482 | { | ||
483 | MediaPluginExample* self = new MediaPluginExample( host_send_func, host_user_data ); | ||
484 | *plugin_send_func = MediaPluginExample::staticReceiveMessage; | ||
485 | *plugin_user_data = ( void* )self; | ||
486 | |||
487 | return 0; | ||
488 | } | ||