@@ -139,7 +139,10 @@ void IWriter.AddPoint(int index, float x, float y, float z, float r, float g, fl
139
139
140
140
void IWriter . Save ( int fileIndex )
141
141
{
142
- int skippedCounter = 0 ;
142
+ // TEST
143
+ bool useLossyFiltering = false ;
144
+ int skippedNodesCounter = 0 ;
145
+ int skippedPointsCounter = 0 ;
143
146
144
147
string fileOnly = Path . GetFileNameWithoutExtension ( importSettings . outputFile ) ;
145
148
string baseFolder = Path . GetDirectoryName ( importSettings . outputFile ) ;
@@ -159,7 +162,7 @@ void IWriter.Save(int fileIndex)
159
162
{
160
163
if ( nodeData . Value . Count < importSettings . minimumPointCount )
161
164
{
162
- skippedCounter ++ ;
165
+ skippedNodesCounter ++ ;
163
166
continue ;
164
167
}
165
168
@@ -208,6 +211,13 @@ void IWriter.Save(int fileIndex)
208
211
// FIXME this is wrong value, if file is appended.. but for now append is disabled
209
212
int totalPointsWritten = 0 ;
210
213
214
+ // TESTING
215
+ int cells = 32 ;
216
+ float center = ( 1f / ( float ) cells ) / 2f ;
217
+ bool [ ] usedGrid = null ;
218
+
219
+ if ( useLossyFiltering == true ) usedGrid = new bool [ cells * cells * cells ] ;
220
+
211
221
// output all points within that node tile
212
222
for ( int i = 0 , len = nodeTempX . Count ; i < len ; i ++ )
213
223
{
@@ -217,6 +227,7 @@ void IWriter.Save(int fileIndex)
217
227
// keep points
218
228
if ( importSettings . keepPoints == true && ( i % importSettings . keepEveryN != 0 ) ) continue ;
219
229
230
+ // original world positions
220
231
float px = nodeTempX [ i ] ;
221
232
float py = nodeTempY [ i ] ;
222
233
float pz = nodeTempZ [ i ] ;
@@ -250,10 +261,71 @@ void IWriter.Save(int fileIndex)
250
261
// pack blue and z
251
262
pz = Tools . SuperPacker ( nodeTempB [ i ] * 0.98f , pz , importSettings . gridSize * importSettings . packMagicValue ) ;
252
263
}
264
+ else if ( useLossyFiltering == true )
265
+ {
266
+ // get local coords within tile
267
+ var keys = nodeData . Key . Split ( '_' ) ;
268
+ // TODO no need to parse, we should know these values?
269
+ cellX = int . Parse ( keys [ 0 ] ) ;
270
+ cellY = int . Parse ( keys [ 1 ] ) ;
271
+ cellZ = int . Parse ( keys [ 2 ] ) ;
272
+ px -= ( cellX * importSettings . gridSize ) ;
273
+ py -= ( cellY * importSettings . gridSize ) ;
274
+ pz -= ( cellZ * importSettings . gridSize ) ;
275
+
276
+ byte packx = ( byte ) ( px * cells ) ;
277
+ byte packy = ( byte ) ( py * cells ) ;
278
+ byte packz = ( byte ) ( pz * cells ) ;
279
+ var index = packx + cells * ( packy + cells * packz ) ;
280
+
281
+ // TODO could decide which point is more important or stronger color?
282
+ if ( usedGrid [ index ] == true )
283
+ {
284
+ skippedPointsCounter ++ ;
285
+ continue ;
286
+ }
253
287
254
- writerPoints . Write ( px ) ;
255
- writerPoints . Write ( py ) ;
256
- writerPoints . Write ( pz ) ;
288
+ usedGrid [ index ] = true ;
289
+
290
+ //if (i < 3) Console.WriteLine("px: " + px + " py: " + py + " pz: " + pz + " index: " + index + " packx: " + packx + " packy: " + packy + " packz: " + packz);
291
+
292
+ }
293
+
294
+ if ( useLossyFiltering == true )
295
+ {
296
+ byte bx = ( byte ) ( px * cells ) ;
297
+ byte by = ( byte ) ( py * cells ) ;
298
+ byte bz = ( byte ) ( pz * cells ) ;
299
+
300
+ float h = 0f ;
301
+ float s = 0f ;
302
+ float v = 0f ;
303
+ RGBtoHSV ( nodeTempR [ i ] , nodeTempG [ i ] , nodeTempB [ i ] , out h , out s , out v ) ;
304
+
305
+ if ( i < 3 ) Console . WriteLine ( "h: " + h + " s: " + s + " v: " + v ) ;
306
+
307
+ // fix values
308
+ h = h / 360f ;
309
+
310
+ byte bh = ( byte ) ( h * 255f ) ;
311
+ byte bs = ( byte ) ( s * 255f ) ;
312
+ byte bv = ( byte ) ( v * 255f ) ;
313
+ byte huepacked = ( byte ) ( bh >> 2 ) ;
314
+ // cut off 3 bits, then move in the middle bits
315
+ byte satpacked = ( byte ) ( bs >> 3 ) ;
316
+ // cut off 3 bits
317
+ byte valpacked = ( byte ) ( bv >> 3 ) ;
318
+ uint hsv655 = ( uint ) ( ( huepacked << 10 ) + ( satpacked << 5 ) + valpacked ) ;
319
+
320
+ uint combinedXYZHSV = ( uint ) ( ( ( bz | by << 5 | bx << 10 ) ) << 16 ) + hsv655 ;
321
+ writerPoints . Write ( ( uint ) combinedXYZHSV ) ;
322
+ }
323
+ else
324
+ {
325
+ writerPoints . Write ( px ) ;
326
+ writerPoints . Write ( py ) ;
327
+ writerPoints . Write ( pz ) ;
328
+ }
257
329
258
330
totalPointsWritten ++ ;
259
331
} // loop all points in tile (node)
@@ -262,7 +334,7 @@ void IWriter.Save(int fileIndex)
262
334
writerPoints . Close ( ) ;
263
335
bsPoints . Dispose ( ) ;
264
336
265
- if ( importSettings . packColors == false )
337
+ if ( importSettings . packColors == false || useLossyFiltering == false )
266
338
{
267
339
// save separate RGB
268
340
BufferedStream bsColors ;
@@ -312,7 +384,7 @@ void IWriter.Save(int fileIndex)
312
384
cb . cellZ = cellZ ;
313
385
314
386
nodeBounds . Add ( cb ) ;
315
- } // loop all nodes
387
+ } // loop all nodes foreach
316
388
317
389
// save rootfile
318
390
// only save after last file, TODO should save this if process fails or user cancels, so no need to start from 0 again.. but then needs some merge or continue from index n feature
@@ -334,6 +406,7 @@ void IWriter.Save(int fileIndex)
334
406
335
407
int versionID = importSettings . packColors ? 2 : 1 ; // (1 = original, 2 = packed v3 format)
336
408
if ( importSettings . packColors == true ) versionID = 2 ;
409
+ if ( useLossyFiltering == true ) versionID = 3 ;
337
410
338
411
// add global header settings to first row
339
412
// version, gridsize, pointcount, boundsMinX, boundsMinY, boundsMinZ, boundsMaxX, boundsMaxY, boundsMaxZ
@@ -348,7 +421,8 @@ void IWriter.Save(int fileIndex)
348
421
Console . ForegroundColor = ConsoleColor . Green ;
349
422
Console . WriteLine ( "Done saving v3 : " + outputFileRoot ) ;
350
423
Console . ForegroundColor = ConsoleColor . White ;
351
- if ( skippedCounter > 0 ) Console . WriteLine ( "*Skipped " + skippedCounter + " nodes with less than " + importSettings . minimumPointCount + " points)" ) ;
424
+ if ( skippedNodesCounter > 0 ) Console . WriteLine ( "*Skipped " + skippedNodesCounter + " nodes with less than " + importSettings . minimumPointCount + " points)" ) ;
425
+ if ( useLossyFiltering == true && skippedPointsCounter > 0 ) Console . WriteLine ( "*Skipped " + skippedPointsCounter + " points due to bytepacked grid filtering" ) ;
352
426
353
427
if ( ( tilerootdata . Count - 1 ) <= 0 )
354
428
{
@@ -357,8 +431,41 @@ void IWriter.Save(int fileIndex)
357
431
Console . ForegroundColor = ConsoleColor . White ;
358
432
}
359
433
}
434
+ } // Save()
360
435
436
+ void RGBtoHSV ( float r , float g , float b , out float h , out float s , out float v )
437
+ {
438
+ float min , max , delta ;
439
+
440
+ min = Math . Min ( Math . Min ( r , g ) , b ) ;
441
+ max = Math . Max ( Math . Max ( r , g ) , b ) ;
442
+ v = max ; // v
443
+
444
+ delta = max - min ;
445
+
446
+ if ( max != 0 )
447
+ s = delta / max ; // s
448
+ else
449
+ {
450
+ // r = g = b = 0 // s = 0, v is undefined
451
+ s = 0 ;
452
+ h = - 1 ;
453
+ return ;
454
+ }
455
+
456
+ if ( r == max )
457
+ h = ( g - b ) / delta ; // between yellow & magenta
458
+ else if ( g == max )
459
+ h = 2 + ( b - r ) / delta ; // between cyan & yellow
460
+ else
461
+ h = 4 + ( r - g ) / delta ; // between magenta & cyan
462
+
463
+ h *= 60 ; // degrees
464
+
465
+ if ( h < 0 ) h += 360 ;
361
466
}
362
- }
363
467
364
- }
468
+
469
+
470
+ } // class
471
+ } // namespace
0 commit comments