BioImager  4.9.0
A .NET microscopy imaging application based on Bio library. Supports various microscopes by using imported libraries & GUI automation. Supports XInput game controllers to move stage, take images, run ImageJ macros on images or Bio C# scripts.
Loading...
Searching...
No Matches
BioImager.SlideGLArea Class Reference
Inheritance diagram for BioImager.SlideGLArea:

Public Member Functions

bool UploadTileTexture (TileIndex index, byte[] pixelData, int tileWidth, int tileHeight)
 Upload a tile texture to the GPU. Call from the main thread. Returns true if upload succeeded.
 
bool HasTileTexture (TileIndex index)
 Check if a tile texture is already in the GPU cache.
 
void ReleaseTileTexture (TileIndex index)
 Release a specific tile texture.
 
void ReleaseLevelTextures (int level)
 Release all textures for a specific pyramid level.
 
void ClearTextureCache ()
 Clear all cached textures.
 
void RequestRedraw ()
 Request a redraw of the GLArea.
 
void SetTilesToRender (IEnumerable< TileRenderInfo > tiles)
 Prepare tiles for rendering. Call before RequestRedraw().
 
byte[] ReadPixels ()
 Read pixels from the current framebuffer (for export/save operations). This is slow — only use for export, not display.
 

Properties

List< TileRenderInfoTilesToRender = new() [get]
 
bool NeedsRedraw [get]
 
bool IsGLReady [get]
 True after the GL context has been fully initialized and is ready for texture uploads and rendering.
 

Events

EventHandler GLReady
 Fires exactly once after the GL context has been successfully initialized. Subscribe to this from ImageView to trigger the first tile load at a point where GL texture uploads are guaranteed to work.
 

Detailed Description

Definition at line 14 of file SlideGLArea.cs.

Constructor & Destructor Documentation

◆ SlideGLArea()

BioImager.SlideGLArea.SlideGLArea ( )

Definition at line 114 of file SlideGLArea.cs.

115 {
116 Paint += OnPaint;
117 Disposed += OnDisposed;
118 Resize += OnResized;
119 }

Member Function Documentation

◆ ClearTextureCache()

void BioImager.SlideGLArea.ClearTextureCache ( )

Clear all cached textures.

Definition at line 465 of file SlideGLArea.cs.

466 {
467 if (!_glInitialized) return;
468
469 MakeCurrent();
470
471 foreach (var tex in _textureCache.Values)
472 GL.DeleteTexture(tex);
473
474 _textureCache.Clear();
475 }

◆ HasTileTexture()

bool BioImager.SlideGLArea.HasTileTexture ( TileIndex index)

Check if a tile texture is already in the GPU cache.

Definition at line 427 of file SlideGLArea.cs.

428 {
429 return _textureCache.ContainsKey(index);
430 }

◆ ReadPixels()

byte[] BioImager.SlideGLArea.ReadPixels ( )

Read pixels from the current framebuffer (for export/save operations). This is slow — only use for export, not display.

Definition at line 514 of file SlideGLArea.cs.

515 {
516 if (!_glInitialized) return null;
517
518 MakeCurrent();
519
520 int width = Width;
521 int height = Height;
522
523 byte[] pixels = new byte[width * height * 4];
524 GL.ReadPixels(0, 0, width, height, PixelFormat.Rgba, PixelType.UnsignedByte, pixels);
525
526 return pixels;
527 }

◆ ReleaseLevelTextures()

void BioImager.SlideGLArea.ReleaseLevelTextures ( int level)

Release all textures for a specific pyramid level.

Definition at line 448 of file SlideGLArea.cs.

449 {
450 if (!_glInitialized) return;
451
452 MakeCurrent();
453
454 var toRemove = _textureCache.Where(kvp => kvp.Key.Level == level).ToList();
455 foreach (var kvp in toRemove)
456 {
457 GL.DeleteTexture(kvp.Value);
458 _textureCache.Remove(kvp.Key);
459 }
460 }

◆ ReleaseTileTexture()

void BioImager.SlideGLArea.ReleaseTileTexture ( TileIndex index)

Release a specific tile texture.

Definition at line 435 of file SlideGLArea.cs.

436 {
437 if (_textureCache.TryGetValue(index, out int tex))
438 {
439 MakeCurrent();
440 GL.DeleteTexture(tex);
441 _textureCache.Remove(index);
442 }
443 }

◆ RequestRedraw()

void BioImager.SlideGLArea.RequestRedraw ( )

Request a redraw of the GLArea.

Definition at line 495 of file SlideGLArea.cs.

496 {
497 NeedsRedraw = true;
498 Invalidate();
499 }

◆ SetTilesToRender()

void BioImager.SlideGLArea.SetTilesToRender ( IEnumerable< TileRenderInfo > tiles)

Prepare tiles for rendering. Call before RequestRedraw().

Definition at line 504 of file SlideGLArea.cs.

505 {
506 TilesToRender.Clear();
507 TilesToRender.AddRange(tiles);
508 }

◆ UploadTileTexture()

bool BioImager.SlideGLArea.UploadTileTexture ( TileIndex index,
byte[] pixelData,
int tileWidth,
int tileHeight )

Upload a tile texture to the GPU. Call from the main thread. Returns true if upload succeeded.

Definition at line 351 of file SlideGLArea.cs.

352 {
353 if (pixelData == null || pixelData.Length == 0)
354 return false;
355
356 // Guard: don't attempt GL operations if the context isn't ready
357 if (!IsHandleCreated)
358 {
359 Console.WriteLine($"[SlideGLArea] UploadTileTexture skipped — control handle not created yet.");
360 return false;
361 }
362
363 try
364 {
365 MakeCurrent();
366 }
367 catch (Exception ex)
368 {
369 Console.WriteLine($"[SlideGLArea] MakeCurrent failed in UploadTileTexture: {ex.Message}");
370 return false;
371 }
372
373 if (!_glInitialized)
374 InitializeGL();
375
376 if (!_glInitialized)
377 {
378 Console.WriteLine($"[SlideGLArea] UploadTileTexture skipped — GL init failed.");
379 return false;
380 }
381
382 // Already cached — nothing to do
383 if (_textureCache.ContainsKey(index))
384 return true;
385
386 // Evict old textures if cache is full
387 if (_textureCache.Count >= MAX_CACHED_TEXTURES)
388 EvictOldestTextures(MAX_CACHED_TEXTURES / 4);
389
390 // Validate pixel data size
391 int expectedBytes = tileWidth * tileHeight * 4;
392 if (pixelData.Length < expectedBytes)
393 {
394 Console.WriteLine($"[SlideGLArea] UploadTileTexture: pixel data too small. Expected {expectedBytes} bytes for {tileWidth}x{tileHeight}, got {pixelData.Length}.");
395 return false;
396 }
397
398 // Create and upload texture
399 int tex = GL.GenTexture();
400 GL.BindTexture(TextureTarget.Texture2D, tex);
401 GL.PixelStore(PixelStoreParameter.UnpackAlignment, 1);
402
403 GL.TexImage2D(TextureTarget.Texture2D, 0, PixelInternalFormat.Rgba,
404 tileWidth, tileHeight, 0, PixelFormat.Rgba, PixelType.UnsignedByte, pixelData);
405
406 var glErr = GL.GetError();
407 if (glErr != ErrorCode.NoError)
408 {
409 Console.WriteLine($"[SlideGLArea] GL error after TexImage2D ({tileWidth}x{tileHeight}): {glErr}");
410 GL.DeleteTexture(tex);
411 return false;
412 }
413
414 GL.TexParameter(TextureTarget.Texture2D, TextureParameterName.TextureMinFilter, (int)TextureMinFilter.Linear);
415 GL.TexParameter(TextureTarget.Texture2D, TextureParameterName.TextureMagFilter, (int)TextureMagFilter.Linear);
416 GL.TexParameter(TextureTarget.Texture2D, TextureParameterName.TextureWrapS, (int)TextureWrapMode.ClampToEdge);
417 GL.TexParameter(TextureTarget.Texture2D, TextureParameterName.TextureWrapT, (int)TextureWrapMode.ClampToEdge);
418
419 GL.BindTexture(TextureTarget.Texture2D, 0);
420 _textureCache[index] = tex;
421 return true;
422 }

Property Documentation

◆ IsGLReady

bool BioImager.SlideGLArea.IsGLReady
get

True after the GL context has been fully initialized and is ready for texture uploads and rendering.

Definition at line 61 of file SlideGLArea.cs.

◆ NeedsRedraw

bool BioImager.SlideGLArea.NeedsRedraw
get

Definition at line 43 of file SlideGLArea.cs.

43{ get; private set; }

◆ TilesToRender

List<TileRenderInfo> BioImager.SlideGLArea.TilesToRender = new()
get

Definition at line 42 of file SlideGLArea.cs.

42{ get; } = new();

Event Documentation

◆ GLReady

EventHandler BioImager.SlideGLArea.GLReady

Fires exactly once after the GL context has been successfully initialized. Subscribe to this from ImageView to trigger the first tile load at a point where GL texture uploads are guaranteed to work.

Definition at line 54 of file SlideGLArea.cs.


The documentation for this class was generated from the following file: