3D-Viewer: intercect modules and cooper items
show module and net information. highlight shapes when selected.
This commit is contained in:
parent
456112de03
commit
6bc19dbfe9
|
@ -425,10 +425,13 @@ void BOARD_ADAPTER::InitSettings( REPORTER* aStatusReporter, REPORTER* aWarningR
|
||||||
|
|
||||||
wxString msg;
|
wxString msg;
|
||||||
|
|
||||||
if( !createBoardPolygon( &msg ) )
|
if( aWarningReporter )
|
||||||
aWarningReporter->Report( _( "Board outline is not closed: " ) + msg, RPT_SEVERITY_WARNING );
|
{
|
||||||
else
|
if( !createBoardPolygon( &msg ) )
|
||||||
aWarningReporter->Report( wxEmptyString );
|
aWarningReporter->Report( _( "Board outline is not closed: " ) + msg, RPT_SEVERITY_WARNING );
|
||||||
|
else
|
||||||
|
aWarningReporter->Report( wxEmptyString );
|
||||||
|
}
|
||||||
|
|
||||||
if( aStatusReporter )
|
if( aStatusReporter )
|
||||||
aStatusReporter->Report( _( "Create layers" ) );
|
aStatusReporter->Report( _( "Create layers" ) );
|
||||||
|
|
|
@ -36,6 +36,7 @@
|
||||||
#include <eda_3d_viewer.h>
|
#include <eda_3d_viewer.h>
|
||||||
#include <3d_rendering/3d_render_raytracing/c3d_render_raytracing.h>
|
#include <3d_rendering/3d_render_raytracing/c3d_render_raytracing.h>
|
||||||
#include <3d_rendering/3d_render_ogl_legacy/c3d_render_ogl_legacy.h>
|
#include <3d_rendering/3d_render_ogl_legacy/c3d_render_ogl_legacy.h>
|
||||||
|
#include <3d_rendering/3d_render_raytracing/accelerators/cbvh_pbrt.h>
|
||||||
#include <3d_viewer_id.h>
|
#include <3d_viewer_id.h>
|
||||||
#include <class_board.h>
|
#include <class_board.h>
|
||||||
#include <reporter.h>
|
#include <reporter.h>
|
||||||
|
@ -112,7 +113,9 @@ EDA_3D_CANVAS::EDA_3D_CANVAS( wxWindow* aParent, const int* aAttribList, BOARD*
|
||||||
m_camera( aCamera ),
|
m_camera( aCamera ),
|
||||||
m_3d_render( nullptr ),
|
m_3d_render( nullptr ),
|
||||||
m_opengl_supports_raytracing( false ),
|
m_opengl_supports_raytracing( false ),
|
||||||
m_render_raytracing_was_requested( false )
|
m_render_raytracing_was_requested( false ),
|
||||||
|
m_accelerator3DShapes( nullptr ),
|
||||||
|
m_currentIntersectedBoardItem( nullptr )
|
||||||
{
|
{
|
||||||
wxLogTrace( m_logTrace, "EDA_3D_CANVAS::EDA_3D_CANVAS" );
|
wxLogTrace( m_logTrace, "EDA_3D_CANVAS::EDA_3D_CANVAS" );
|
||||||
|
|
||||||
|
@ -176,6 +179,9 @@ EDA_3D_CANVAS::~EDA_3D_CANVAS()
|
||||||
{
|
{
|
||||||
wxLogTrace( m_logTrace, "EDA_3D_CANVAS::~EDA_3D_CANVAS" );
|
wxLogTrace( m_logTrace, "EDA_3D_CANVAS::~EDA_3D_CANVAS" );
|
||||||
|
|
||||||
|
delete m_accelerator3DShapes;
|
||||||
|
m_accelerator3DShapes = NULL;
|
||||||
|
|
||||||
releaseOpenGL();
|
releaseOpenGL();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -462,8 +468,17 @@ void EDA_3D_CANVAS::DoRePaint()
|
||||||
{
|
{
|
||||||
m_3d_render->SetCurWindowSize( clientSize );
|
m_3d_render->SetCurWindowSize( clientSize );
|
||||||
|
|
||||||
|
bool reloadRaytracingForIntersectionCalculations = false;
|
||||||
|
|
||||||
|
if( ( m_boardAdapter.RenderEngineGet() == RENDER_ENGINE::OPENGL_LEGACY ) &&
|
||||||
|
m_3d_render_ogl_legacy->IsReloadRequestPending() )
|
||||||
|
reloadRaytracingForIntersectionCalculations = true;
|
||||||
|
|
||||||
requested_redraw = m_3d_render->Redraw( m_mouse_was_moved || m_camera_is_moving,
|
requested_redraw = m_3d_render->Redraw( m_mouse_was_moved || m_camera_is_moving,
|
||||||
&activityReporter, &warningReporter );
|
&activityReporter, &warningReporter );
|
||||||
|
|
||||||
|
if( reloadRaytracingForIntersectionCalculations )
|
||||||
|
m_3d_render_raytracing->Reload( nullptr, nullptr, true );
|
||||||
}
|
}
|
||||||
|
|
||||||
if( m_render_pivot )
|
if( m_render_pivot )
|
||||||
|
@ -659,6 +674,102 @@ void EDA_3D_CANVAS::OnMouseMove( wxMouseEvent &event )
|
||||||
|
|
||||||
const wxPoint eventPosition = event.GetPosition();
|
const wxPoint eventPosition = event.GetPosition();
|
||||||
m_camera.SetCurMousePosition( eventPosition );
|
m_camera.SetCurMousePosition( eventPosition );
|
||||||
|
|
||||||
|
if( !event.Dragging() )
|
||||||
|
{
|
||||||
|
STATUSBAR_REPORTER activityReporter(
|
||||||
|
m_parentStatusBar, static_cast<int>( EDA_3D_VIEWER_STATUSBAR::STATUS_TEXT ) );
|
||||||
|
|
||||||
|
RAY mouseRay = getRayAtCurrrentMousePosition();
|
||||||
|
|
||||||
|
BOARD_ITEM *intersectedBoardItem = m_3d_render_raytracing->IntersectBoardItem( mouseRay );
|
||||||
|
|
||||||
|
if( intersectedBoardItem )
|
||||||
|
{
|
||||||
|
if( intersectedBoardItem != m_currentIntersectedBoardItem )
|
||||||
|
{
|
||||||
|
m_3d_render_ogl_legacy->SetCurrentIntersectedBoardItem( intersectedBoardItem );
|
||||||
|
m_currentIntersectedBoardItem = intersectedBoardItem;
|
||||||
|
|
||||||
|
if( m_boardAdapter.RenderEngineGet() == RENDER_ENGINE::OPENGL_LEGACY )
|
||||||
|
Request_refresh();
|
||||||
|
}
|
||||||
|
|
||||||
|
switch( intersectedBoardItem->Type() )
|
||||||
|
{
|
||||||
|
case PCB_PAD_T:
|
||||||
|
{
|
||||||
|
D_PAD* item = dynamic_cast<D_PAD *>( intersectedBoardItem );
|
||||||
|
|
||||||
|
if( item )
|
||||||
|
{
|
||||||
|
if( item->IsOnCopperLayer() )
|
||||||
|
activityReporter.Report( wxString::Format( _( "Net %s\tNetClass %s\tPadName %s" ),
|
||||||
|
item->GetNet()->GetNetname(),
|
||||||
|
item->GetNet()->GetClassName(),
|
||||||
|
item->GetName() ) );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case PCB_MODULE_T:
|
||||||
|
{
|
||||||
|
MODULE* module = dynamic_cast<MODULE *>( intersectedBoardItem );
|
||||||
|
|
||||||
|
if( module )
|
||||||
|
{
|
||||||
|
activityReporter.Report( module->GetReference() );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case PCB_TRACE_T:
|
||||||
|
case PCB_VIA_T:
|
||||||
|
case PCB_ARC_T:
|
||||||
|
{
|
||||||
|
TRACK* item = dynamic_cast<TRACK *>( intersectedBoardItem );
|
||||||
|
|
||||||
|
if( item )
|
||||||
|
{
|
||||||
|
activityReporter.Report( wxString::Format( _( "Net %s\tNetClass %s" ),
|
||||||
|
item->GetNet()->GetNetname(),
|
||||||
|
item->GetNet()->GetClassName() ) );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case PCB_ZONE_AREA_T:
|
||||||
|
{
|
||||||
|
ZONE_CONTAINER* item = dynamic_cast<ZONE_CONTAINER *>( intersectedBoardItem );
|
||||||
|
|
||||||
|
if( item )
|
||||||
|
{
|
||||||
|
if( item->IsOnCopperLayer() )
|
||||||
|
activityReporter.Report( wxString::Format( _( "Net %s\tNetClass %s" ),
|
||||||
|
item->GetNet()->GetNetname(),
|
||||||
|
item->GetNet()->GetClassName() ) );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if( ( m_currentIntersectedBoardItem != nullptr ) &&
|
||||||
|
( m_boardAdapter.RenderEngineGet() == RENDER_ENGINE::OPENGL_LEGACY ) )
|
||||||
|
{
|
||||||
|
m_3d_render_ogl_legacy->SetCurrentIntersectedBoardItem( nullptr );
|
||||||
|
Request_refresh();
|
||||||
|
|
||||||
|
activityReporter.Report( "" );
|
||||||
|
}
|
||||||
|
|
||||||
|
m_currentIntersectedBoardItem = nullptr;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -666,6 +777,15 @@ void EDA_3D_CANVAS::OnLeftDown( wxMouseEvent &event )
|
||||||
{
|
{
|
||||||
SetFocus();
|
SetFocus();
|
||||||
stop_editingTimeOut_Timer();
|
stop_editingTimeOut_Timer();
|
||||||
|
|
||||||
|
if( !event.Dragging() && ( m_3d_render_raytracing != nullptr ) )
|
||||||
|
{
|
||||||
|
RAY mouseRay = getRayAtCurrrentMousePosition();
|
||||||
|
|
||||||
|
BOARD_ITEM *intersectedBoardItem = m_3d_render_raytracing->IntersectBoardItem( mouseRay );
|
||||||
|
|
||||||
|
// !TODO: send a selection item to pcbnew, eg: via kiway?
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -793,14 +913,7 @@ void EDA_3D_CANVAS::request_start_moving_camera( float aMovingSpeed, bool aRende
|
||||||
|
|
||||||
void EDA_3D_CANVAS::move_pivot_based_on_cur_mouse_position()
|
void EDA_3D_CANVAS::move_pivot_based_on_cur_mouse_position()
|
||||||
{
|
{
|
||||||
SFVEC3F rayOrigin;
|
RAY mouseRay = getRayAtCurrrentMousePosition();
|
||||||
SFVEC3F rayDir;
|
|
||||||
|
|
||||||
// Generate a ray origin and direction based on current mouser position and camera
|
|
||||||
m_camera.MakeRayAtCurrrentMousePosition( rayOrigin, rayDir );
|
|
||||||
|
|
||||||
RAY mouseRay;
|
|
||||||
mouseRay.Init( rayOrigin, rayDir );
|
|
||||||
|
|
||||||
float hit_t;
|
float hit_t;
|
||||||
|
|
||||||
|
@ -994,3 +1107,18 @@ void EDA_3D_CANVAS::RenderEngineChanged()
|
||||||
|
|
||||||
Request_refresh();
|
Request_refresh();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
RAY EDA_3D_CANVAS::getRayAtCurrrentMousePosition()
|
||||||
|
{
|
||||||
|
SFVEC3F rayOrigin;
|
||||||
|
SFVEC3F rayDir;
|
||||||
|
|
||||||
|
// Generate a ray origin and direction based on current mouser position and camera
|
||||||
|
m_camera.MakeRayAtCurrrentMousePosition( rayOrigin, rayDir );
|
||||||
|
|
||||||
|
RAY mouseRay;
|
||||||
|
mouseRay.Init( rayOrigin, rayDir );
|
||||||
|
|
||||||
|
return mouseRay;
|
||||||
|
}
|
||||||
|
|
|
@ -27,6 +27,7 @@
|
||||||
|
|
||||||
|
|
||||||
#include "board_adapter.h"
|
#include "board_adapter.h"
|
||||||
|
#include "3d_rendering/3d_render_raytracing/accelerators/caccelerator.h"
|
||||||
#include "3d_rendering/c3d_render_base.h"
|
#include "3d_rendering/c3d_render_base.h"
|
||||||
#include "3d_cache/3d_cache.h"
|
#include "3d_cache/3d_cache.h"
|
||||||
#include <gal/hidpi_gl_canvas.h>
|
#include <gal/hidpi_gl_canvas.h>
|
||||||
|
@ -233,6 +234,8 @@ private:
|
||||||
*/
|
*/
|
||||||
void releaseOpenGL();
|
void releaseOpenGL();
|
||||||
|
|
||||||
|
RAY getRayAtCurrrentMousePosition();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
|
||||||
TOOL_DISPATCHER* m_eventDispatcher;
|
TOOL_DISPATCHER* m_eventDispatcher;
|
||||||
|
@ -267,6 +270,11 @@ private:
|
||||||
bool m_opengl_supports_raytracing;
|
bool m_opengl_supports_raytracing;
|
||||||
bool m_render_raytracing_was_requested;
|
bool m_render_raytracing_was_requested;
|
||||||
|
|
||||||
|
CCONTAINER m_3DShapes_container; // Holds 3D shapes from modules
|
||||||
|
CGENERICACCELERATOR *m_accelerator3DShapes; // used for mouse over searching
|
||||||
|
|
||||||
|
BOARD_ITEM* m_currentIntersectedBoardItem;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Trace mask used to enable or disable the trace output of this class.
|
* Trace mask used to enable or disable the trace output of this class.
|
||||||
* The debug output can be turned on by setting the WXTRACE environment variable to
|
* The debug output can be turned on by setting the WXTRACE environment variable to
|
||||||
|
|
|
@ -75,6 +75,7 @@ C3D_RENDER_OGL_LEGACY::C3D_RENDER_OGL_LEGACY( BOARD_ADAPTER& aAdapter, CCAMERA&
|
||||||
m_ogl_circle_texture = 0;
|
m_ogl_circle_texture = 0;
|
||||||
m_ogl_disp_list_grid = 0;
|
m_ogl_disp_list_grid = 0;
|
||||||
m_last_grid_type = GRID3D_TYPE::NONE;
|
m_last_grid_type = GRID3D_TYPE::NONE;
|
||||||
|
m_currentIntersectedBoardItem = nullptr;
|
||||||
|
|
||||||
m_3dmodel_map.clear();
|
m_3dmodel_map.clear();
|
||||||
}
|
}
|
||||||
|
@ -1241,15 +1242,34 @@ void C3D_RENDER_OGL_LEGACY::render_3D_models_selected( bool aRenderTopOrBot, boo
|
||||||
// Go for all modules
|
// Go for all modules
|
||||||
for( auto module : m_boardAdapter.GetBoard()->Modules() )
|
for( auto module : m_boardAdapter.GetBoard()->Modules() )
|
||||||
{
|
{
|
||||||
if( ( aRenderSelectedOnly && !module->IsSelected() ) ||
|
const bool isIntersected = ( module == m_currentIntersectedBoardItem );
|
||||||
( !aRenderSelectedOnly && module->IsSelected() ) )
|
|
||||||
|
if( !isIntersected &&
|
||||||
|
( ( aRenderSelectedOnly && !module->IsSelected() ) ||
|
||||||
|
( !aRenderSelectedOnly && module->IsSelected() ) ) )
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
if( isIntersected && aRenderSelectedOnly )
|
||||||
|
{
|
||||||
|
glEnable( GL_POLYGON_OFFSET_LINE );
|
||||||
|
glPolygonOffset( 8.0, 1.0 );
|
||||||
|
|
||||||
|
glPolygonMode( GL_FRONT, GL_LINE );
|
||||||
|
glLineWidth( 6 );
|
||||||
|
}
|
||||||
|
|
||||||
if( !module->Models().empty() )
|
if( !module->Models().empty() )
|
||||||
if( m_boardAdapter.ShouldModuleBeDisplayed((MODULE_ATTR_T) module->GetAttributes() ) )
|
if( m_boardAdapter.ShouldModuleBeDisplayed((MODULE_ATTR_T) module->GetAttributes() ) )
|
||||||
if( ( aRenderTopOrBot && !module->IsFlipped() )
|
if( ( aRenderTopOrBot && !module->IsFlipped() )
|
||||||
|| ( !aRenderTopOrBot && module->IsFlipped() ) )
|
|| ( !aRenderTopOrBot && module->IsFlipped() ) )
|
||||||
render_3D_module( module, aRenderTransparentOnly );
|
render_3D_module( module, aRenderTransparentOnly, isIntersected );
|
||||||
|
|
||||||
|
if( isIntersected && aRenderSelectedOnly )
|
||||||
|
{
|
||||||
|
// Restore
|
||||||
|
glDisable( GL_POLYGON_OFFSET_LINE );
|
||||||
|
glPolygonMode( GL_FRONT_AND_BACK, GL_FILL );
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
C_OGL_3DMODEL::EndDrawMulti();
|
C_OGL_3DMODEL::EndDrawMulti();
|
||||||
|
@ -1264,7 +1284,8 @@ void C3D_RENDER_OGL_LEGACY::render_3D_models( bool aRenderTopOrBot,
|
||||||
|
|
||||||
|
|
||||||
void C3D_RENDER_OGL_LEGACY::render_3D_module( const MODULE* module,
|
void C3D_RENDER_OGL_LEGACY::render_3D_module( const MODULE* module,
|
||||||
bool aRenderTransparentOnly )
|
bool aRenderTransparentOnly,
|
||||||
|
bool aIsSelected )
|
||||||
{
|
{
|
||||||
if( !module->Models().empty() )
|
if( !module->Models().empty() )
|
||||||
{
|
{
|
||||||
|
@ -1328,9 +1349,9 @@ void C3D_RENDER_OGL_LEGACY::render_3D_module( const MODULE* module,
|
||||||
glMultMatrixf( glm::value_ptr( mtx ) );
|
glMultMatrixf( glm::value_ptr( mtx ) );
|
||||||
|
|
||||||
if( aRenderTransparentOnly )
|
if( aRenderTransparentOnly )
|
||||||
modelPtr->Draw_transparent( sM.m_Opacity, module->IsSelected() );
|
modelPtr->Draw_transparent( sM.m_Opacity, module->IsSelected() || aIsSelected );
|
||||||
else
|
else
|
||||||
modelPtr->Draw_opaque( module->IsSelected() );
|
modelPtr->Draw_opaque( module->IsSelected() || aIsSelected );
|
||||||
|
|
||||||
if( m_boardAdapter.GetFlag( FL_RENDER_OPENGL_SHOW_MODEL_BBOX ) )
|
if( m_boardAdapter.GetFlag( FL_RENDER_OPENGL_SHOW_MODEL_BBOX ) )
|
||||||
{
|
{
|
||||||
|
|
|
@ -69,6 +69,8 @@ public:
|
||||||
|
|
||||||
int GetWaitForEditingTimeOut() override;
|
int GetWaitForEditingTimeOut() override;
|
||||||
|
|
||||||
|
void SetCurrentIntersectedBoardItem( BOARD_ITEM* aCurrentIntersectedBoardItem ) { m_currentIntersectedBoardItem = aCurrentIntersectedBoardItem; }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
bool initializeOpenGL();
|
bool initializeOpenGL();
|
||||||
void reload( REPORTER* aStatusReporter, REPORTER* aWarningReporter );
|
void reload( REPORTER* aStatusReporter, REPORTER* aWarningReporter );
|
||||||
|
@ -108,6 +110,8 @@ private:
|
||||||
|
|
||||||
MAP_3DMODEL m_3dmodel_map;
|
MAP_3DMODEL m_3dmodel_map;
|
||||||
|
|
||||||
|
BOARD_ITEM* m_currentIntersectedBoardItem;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
CLAYERS_OGL_DISP_LISTS *generate_holes_display_list( const LIST_OBJECT2D &aListHolesObject2d,
|
CLAYERS_OGL_DISP_LISTS *generate_holes_display_list( const LIST_OBJECT2D &aListHolesObject2d,
|
||||||
const SHAPE_POLY_SET &aPoly,
|
const SHAPE_POLY_SET &aPoly,
|
||||||
|
@ -192,7 +196,7 @@ private:
|
||||||
|
|
||||||
void render_3D_models_selected( bool aRenderTopOrBot, bool aRenderTransparentOnly, bool aRenderSelectedOnly );
|
void render_3D_models_selected( bool aRenderTopOrBot, bool aRenderTransparentOnly, bool aRenderSelectedOnly );
|
||||||
|
|
||||||
void render_3D_module( const MODULE* module, bool aRenderTransparentOnly );
|
void render_3D_module( const MODULE* module, bool aRenderTransparentOnly, bool aIsSelected );
|
||||||
|
|
||||||
void setLight_Front( bool enabled );
|
void setLight_Front( bool enabled );
|
||||||
void setLight_Top( bool enabled );
|
void setLight_Top( bool enabled );
|
||||||
|
|
|
@ -440,7 +440,9 @@ void C3D_RENDER_RAYTRACING::createItemsFromContainer( const CBVHCONTAINER2D *aCo
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void C3D_RENDER_RAYTRACING::reload( REPORTER* aStatusReporter, REPORTER* aWarningReporter )
|
void C3D_RENDER_RAYTRACING::Reload( REPORTER* aStatusReporter,
|
||||||
|
REPORTER* aWarningReporter,
|
||||||
|
bool aOnlyLoadCopperAndShapes )
|
||||||
{
|
{
|
||||||
m_reloadRequested = false;
|
m_reloadRequested = false;
|
||||||
|
|
||||||
|
@ -451,10 +453,13 @@ void C3D_RENDER_RAYTRACING::reload( REPORTER* aStatusReporter, REPORTER* aWarnin
|
||||||
|
|
||||||
unsigned stats_startReloadTime = GetRunningMicroSecs();
|
unsigned stats_startReloadTime = GetRunningMicroSecs();
|
||||||
|
|
||||||
m_boardAdapter.InitSettings( aStatusReporter, aWarningReporter );
|
if( !aOnlyLoadCopperAndShapes )
|
||||||
|
{
|
||||||
|
m_boardAdapter.InitSettings( aStatusReporter, aWarningReporter );
|
||||||
|
|
||||||
SFVEC3F camera_pos = m_boardAdapter.GetBoardCenter3DU();
|
SFVEC3F camera_pos = m_boardAdapter.GetBoardCenter3DU();
|
||||||
m_camera.SetBoardLookAtPos( camera_pos );
|
m_camera.SetBoardLookAtPos( camera_pos );
|
||||||
|
}
|
||||||
|
|
||||||
m_object_container.Clear();
|
m_object_container.Clear();
|
||||||
m_containerWithObjectsToDelete.Clear();
|
m_containerWithObjectsToDelete.Clear();
|
||||||
|
@ -468,153 +473,156 @@ void C3D_RENDER_RAYTRACING::reload( REPORTER* aStatusReporter, REPORTER* aWarnin
|
||||||
|
|
||||||
m_outlineBoard2dObjects = new CCONTAINER2D;
|
m_outlineBoard2dObjects = new CCONTAINER2D;
|
||||||
|
|
||||||
const int outlineCount = m_boardAdapter.GetBoardPoly().OutlineCount();
|
if( !aOnlyLoadCopperAndShapes )
|
||||||
|
|
||||||
if( outlineCount > 0 )
|
|
||||||
{
|
{
|
||||||
float divFactor = 0.0f;
|
const int outlineCount = m_boardAdapter.GetBoardPoly().OutlineCount();
|
||||||
|
|
||||||
if( m_boardAdapter.GetStats_Nr_Vias() )
|
if( outlineCount > 0 )
|
||||||
divFactor = m_boardAdapter.GetStats_Med_Via_Hole_Diameter3DU() * 18.0f;
|
|
||||||
else
|
|
||||||
if( m_boardAdapter.GetStats_Nr_Holes() )
|
|
||||||
divFactor = m_boardAdapter.GetStats_Med_Hole_Diameter3DU() * 8.0f;
|
|
||||||
|
|
||||||
SHAPE_POLY_SET boardPolyCopy = m_boardAdapter.GetBoardPoly();
|
|
||||||
boardPolyCopy.Fracture( SHAPE_POLY_SET::PM_FAST );
|
|
||||||
|
|
||||||
for( int iOutlinePolyIdx = 0; iOutlinePolyIdx < outlineCount; iOutlinePolyIdx++ )
|
|
||||||
{
|
{
|
||||||
Convert_path_polygon_to_polygon_blocks_and_dummy_blocks(
|
float divFactor = 0.0f;
|
||||||
boardPolyCopy,
|
|
||||||
*m_outlineBoard2dObjects,
|
|
||||||
m_boardAdapter.BiuTo3Dunits(),
|
|
||||||
divFactor,
|
|
||||||
*dynamic_cast<const BOARD_ITEM*>( m_boardAdapter.GetBoard() ),
|
|
||||||
iOutlinePolyIdx );
|
|
||||||
}
|
|
||||||
|
|
||||||
if( m_boardAdapter.GetFlag( FL_SHOW_BOARD_BODY ) )
|
if( m_boardAdapter.GetStats_Nr_Vias() )
|
||||||
{
|
divFactor = m_boardAdapter.GetStats_Med_Via_Hole_Diameter3DU() * 18.0f;
|
||||||
const LIST_OBJECT2D &listObjects = m_outlineBoard2dObjects->GetList();
|
else
|
||||||
|
if( m_boardAdapter.GetStats_Nr_Holes() )
|
||||||
|
divFactor = m_boardAdapter.GetStats_Med_Hole_Diameter3DU() * 8.0f;
|
||||||
|
|
||||||
for( LIST_OBJECT2D::const_iterator object2d_iterator = listObjects.begin();
|
SHAPE_POLY_SET boardPolyCopy = m_boardAdapter.GetBoardPoly();
|
||||||
object2d_iterator != listObjects.end();
|
boardPolyCopy.Fracture( SHAPE_POLY_SET::PM_FAST );
|
||||||
++object2d_iterator )
|
|
||||||
|
for( int iOutlinePolyIdx = 0; iOutlinePolyIdx < outlineCount; iOutlinePolyIdx++ )
|
||||||
{
|
{
|
||||||
const COBJECT2D *object2d_A = static_cast<const COBJECT2D *>(*object2d_iterator);
|
Convert_path_polygon_to_polygon_blocks_and_dummy_blocks(
|
||||||
|
boardPolyCopy,
|
||||||
std::vector<const COBJECT2D *> *object2d_B = new std::vector<const COBJECT2D *>();
|
*m_outlineBoard2dObjects,
|
||||||
|
m_boardAdapter.BiuTo3Dunits(),
|
||||||
// Check if there are any THT that intersects this outline object part
|
divFactor,
|
||||||
if( !m_boardAdapter.GetThroughHole_Outer().GetList().empty() )
|
*dynamic_cast<const BOARD_ITEM*>( m_boardAdapter.GetBoard() ),
|
||||||
{
|
iOutlinePolyIdx );
|
||||||
|
|
||||||
CONST_LIST_OBJECT2D intersectionList;
|
|
||||||
m_boardAdapter.GetThroughHole_Outer().GetListObjectsIntersects(
|
|
||||||
object2d_A->GetBBox(),
|
|
||||||
intersectionList );
|
|
||||||
|
|
||||||
if( !intersectionList.empty() )
|
|
||||||
{
|
|
||||||
for( CONST_LIST_OBJECT2D::const_iterator hole = intersectionList.begin();
|
|
||||||
hole != intersectionList.end();
|
|
||||||
++hole )
|
|
||||||
{
|
|
||||||
const COBJECT2D *hole2d = static_cast<const COBJECT2D *>(*hole);
|
|
||||||
|
|
||||||
if( object2d_A->Intersects( hole2d->GetBBox() ) )
|
|
||||||
//if( object2d_A->GetBBox().Intersects( hole2d->GetBBox() ) )
|
|
||||||
object2d_B->push_back( hole2d );
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if( object2d_B->empty() )
|
|
||||||
{
|
|
||||||
delete object2d_B;
|
|
||||||
object2d_B = CSGITEM_EMPTY;
|
|
||||||
}
|
|
||||||
|
|
||||||
if( object2d_B == CSGITEM_EMPTY )
|
|
||||||
{
|
|
||||||
#if 0
|
|
||||||
create_3d_object_from( m_object_container, object2d_A,
|
|
||||||
m_boardAdapter.GetLayerBottomZpos3DU( F_Cu ),
|
|
||||||
m_boardAdapter.GetLayerBottomZpos3DU( B_Cu ),
|
|
||||||
&m_materials.m_EpoxyBoard,
|
|
||||||
g_epoxyColor );
|
|
||||||
#else
|
|
||||||
|
|
||||||
CLAYERITEM *objPtr = new CLAYERITEM( object2d_A,
|
|
||||||
m_boardAdapter.GetLayerBottomZpos3DU( F_Cu ),
|
|
||||||
m_boardAdapter.GetLayerBottomZpos3DU( B_Cu ) );
|
|
||||||
|
|
||||||
objPtr->SetMaterial( &m_materials.m_EpoxyBoard );
|
|
||||||
objPtr->SetColor( ConvertSRGBToLinear( (SFVEC3F)m_boardAdapter.m_BoardBodyColor ) );
|
|
||||||
m_object_container.Add( objPtr );
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
|
|
||||||
CITEMLAYERCSG2D *itemCSG2d = new CITEMLAYERCSG2D(
|
|
||||||
object2d_A,
|
|
||||||
object2d_B,
|
|
||||||
CSGITEM_FULL,
|
|
||||||
(const BOARD_ITEM &)*m_boardAdapter.GetBoard() );
|
|
||||||
|
|
||||||
m_containerWithObjectsToDelete.Add( itemCSG2d );
|
|
||||||
|
|
||||||
CLAYERITEM *objPtr = new CLAYERITEM( itemCSG2d,
|
|
||||||
m_boardAdapter.GetLayerBottomZpos3DU( F_Cu ),
|
|
||||||
m_boardAdapter.GetLayerBottomZpos3DU( B_Cu ) );
|
|
||||||
|
|
||||||
objPtr->SetMaterial( &m_materials.m_EpoxyBoard );
|
|
||||||
objPtr->SetColor( ConvertSRGBToLinear( (SFVEC3F)m_boardAdapter.m_BoardBodyColor ) );
|
|
||||||
m_object_container.Add( objPtr );
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Add cylinders of the board body to container
|
if( m_boardAdapter.GetFlag( FL_SHOW_BOARD_BODY ) )
|
||||||
// Note: This is actually a workarround for the holes in the board.
|
|
||||||
// The issue is because if a hole is in a border of a divided polygon ( ex
|
|
||||||
// a polygon or dummyblock) it will cut also the render of the hole.
|
|
||||||
// So this will add a full hole.
|
|
||||||
// In fact, that is not need if the hole have copper.
|
|
||||||
// /////////////////////////////////////////////////////////////////////////
|
|
||||||
if( !m_boardAdapter.GetThroughHole_Outer().GetList().empty() )
|
|
||||||
{
|
{
|
||||||
const LIST_OBJECT2D &holeList = m_boardAdapter.GetThroughHole_Outer().GetList();
|
const LIST_OBJECT2D &listObjects = m_outlineBoard2dObjects->GetList();
|
||||||
|
|
||||||
for( LIST_OBJECT2D::const_iterator hole = holeList.begin();
|
for( LIST_OBJECT2D::const_iterator object2d_iterator = listObjects.begin();
|
||||||
hole != holeList.end();
|
object2d_iterator != listObjects.end();
|
||||||
++hole )
|
++object2d_iterator )
|
||||||
{
|
{
|
||||||
const COBJECT2D *hole2d = static_cast<const COBJECT2D *>(*hole);
|
const COBJECT2D *object2d_A = static_cast<const COBJECT2D *>(*object2d_iterator);
|
||||||
|
|
||||||
switch( hole2d->GetObjectType() )
|
std::vector<const COBJECT2D *> *object2d_B = new std::vector<const COBJECT2D *>();
|
||||||
{
|
|
||||||
case OBJECT2D_TYPE::FILLED_CIRCLE:
|
|
||||||
{
|
|
||||||
const float radius = hole2d->GetBBox().GetExtent().x * 0.5f * 0.999f;
|
|
||||||
|
|
||||||
CVCYLINDER *objPtr = new CVCYLINDER(
|
// Check if there are any THT that intersects this outline object part
|
||||||
hole2d->GetCentroid(),
|
if( !m_boardAdapter.GetThroughHole_Outer().GetList().empty() )
|
||||||
NextFloatDown( m_boardAdapter.GetLayerBottomZpos3DU( F_Cu ) ),
|
{
|
||||||
NextFloatUp( m_boardAdapter.GetLayerBottomZpos3DU( B_Cu ) ),
|
|
||||||
radius );
|
CONST_LIST_OBJECT2D intersectionList;
|
||||||
|
m_boardAdapter.GetThroughHole_Outer().GetListObjectsIntersects(
|
||||||
|
object2d_A->GetBBox(),
|
||||||
|
intersectionList );
|
||||||
|
|
||||||
|
if( !intersectionList.empty() )
|
||||||
|
{
|
||||||
|
for( CONST_LIST_OBJECT2D::const_iterator hole = intersectionList.begin();
|
||||||
|
hole != intersectionList.end();
|
||||||
|
++hole )
|
||||||
|
{
|
||||||
|
const COBJECT2D *hole2d = static_cast<const COBJECT2D *>(*hole);
|
||||||
|
|
||||||
|
if( object2d_A->Intersects( hole2d->GetBBox() ) )
|
||||||
|
//if( object2d_A->GetBBox().Intersects( hole2d->GetBBox() ) )
|
||||||
|
object2d_B->push_back( hole2d );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if( object2d_B->empty() )
|
||||||
|
{
|
||||||
|
delete object2d_B;
|
||||||
|
object2d_B = CSGITEM_EMPTY;
|
||||||
|
}
|
||||||
|
|
||||||
|
if( object2d_B == CSGITEM_EMPTY )
|
||||||
|
{
|
||||||
|
#if 0
|
||||||
|
create_3d_object_from( m_object_container, object2d_A,
|
||||||
|
m_boardAdapter.GetLayerBottomZpos3DU( F_Cu ),
|
||||||
|
m_boardAdapter.GetLayerBottomZpos3DU( B_Cu ),
|
||||||
|
&m_materials.m_EpoxyBoard,
|
||||||
|
g_epoxyColor );
|
||||||
|
#else
|
||||||
|
|
||||||
|
CLAYERITEM *objPtr = new CLAYERITEM( object2d_A,
|
||||||
|
m_boardAdapter.GetLayerBottomZpos3DU( F_Cu ),
|
||||||
|
m_boardAdapter.GetLayerBottomZpos3DU( B_Cu ) );
|
||||||
|
|
||||||
objPtr->SetMaterial( &m_materials.m_EpoxyBoard );
|
objPtr->SetMaterial( &m_materials.m_EpoxyBoard );
|
||||||
objPtr->SetColor( ConvertSRGBToLinear( (SFVEC3F)m_boardAdapter.m_BoardBodyColor ) );
|
objPtr->SetColor( ConvertSRGBToLinear( (SFVEC3F)m_boardAdapter.m_BoardBodyColor ) );
|
||||||
|
|
||||||
m_object_container.Add( objPtr );
|
m_object_container.Add( objPtr );
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
break;
|
else
|
||||||
|
{
|
||||||
|
|
||||||
default:
|
CITEMLAYERCSG2D *itemCSG2d = new CITEMLAYERCSG2D(
|
||||||
|
object2d_A,
|
||||||
|
object2d_B,
|
||||||
|
CSGITEM_FULL,
|
||||||
|
(const BOARD_ITEM &)*m_boardAdapter.GetBoard() );
|
||||||
|
|
||||||
|
m_containerWithObjectsToDelete.Add( itemCSG2d );
|
||||||
|
|
||||||
|
CLAYERITEM *objPtr = new CLAYERITEM( itemCSG2d,
|
||||||
|
m_boardAdapter.GetLayerBottomZpos3DU( F_Cu ),
|
||||||
|
m_boardAdapter.GetLayerBottomZpos3DU( B_Cu ) );
|
||||||
|
|
||||||
|
objPtr->SetMaterial( &m_materials.m_EpoxyBoard );
|
||||||
|
objPtr->SetColor( ConvertSRGBToLinear( (SFVEC3F)m_boardAdapter.m_BoardBodyColor ) );
|
||||||
|
m_object_container.Add( objPtr );
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Add cylinders of the board body to container
|
||||||
|
// Note: This is actually a workarround for the holes in the board.
|
||||||
|
// The issue is because if a hole is in a border of a divided polygon ( ex
|
||||||
|
// a polygon or dummyblock) it will cut also the render of the hole.
|
||||||
|
// So this will add a full hole.
|
||||||
|
// In fact, that is not need if the hole have copper.
|
||||||
|
// /////////////////////////////////////////////////////////////////////////
|
||||||
|
if( !m_boardAdapter.GetThroughHole_Outer().GetList().empty() )
|
||||||
|
{
|
||||||
|
const LIST_OBJECT2D &holeList = m_boardAdapter.GetThroughHole_Outer().GetList();
|
||||||
|
|
||||||
|
for( LIST_OBJECT2D::const_iterator hole = holeList.begin();
|
||||||
|
hole != holeList.end();
|
||||||
|
++hole )
|
||||||
|
{
|
||||||
|
const COBJECT2D *hole2d = static_cast<const COBJECT2D *>(*hole);
|
||||||
|
|
||||||
|
switch( hole2d->GetObjectType() )
|
||||||
|
{
|
||||||
|
case OBJECT2D_TYPE::FILLED_CIRCLE:
|
||||||
|
{
|
||||||
|
const float radius = hole2d->GetBBox().GetExtent().x * 0.5f * 0.999f;
|
||||||
|
|
||||||
|
CVCYLINDER *objPtr = new CVCYLINDER(
|
||||||
|
hole2d->GetCentroid(),
|
||||||
|
NextFloatDown( m_boardAdapter.GetLayerBottomZpos3DU( F_Cu ) ),
|
||||||
|
NextFloatUp( m_boardAdapter.GetLayerBottomZpos3DU( B_Cu ) ),
|
||||||
|
radius );
|
||||||
|
|
||||||
|
objPtr->SetMaterial( &m_materials.m_EpoxyBoard );
|
||||||
|
objPtr->SetColor( ConvertSRGBToLinear( (SFVEC3F)m_boardAdapter.m_BoardBodyColor ) );
|
||||||
|
|
||||||
|
m_object_container.Add( objPtr );
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -631,6 +639,9 @@ void C3D_RENDER_RAYTRACING::reload( REPORTER* aStatusReporter, REPORTER* aWarnin
|
||||||
{
|
{
|
||||||
PCB_LAYER_ID layer_id = static_cast<PCB_LAYER_ID>(ii->first);
|
PCB_LAYER_ID layer_id = static_cast<PCB_LAYER_ID>(ii->first);
|
||||||
|
|
||||||
|
if( aOnlyLoadCopperAndShapes && !IsCopperLayer( layer_id ) )
|
||||||
|
continue;
|
||||||
|
|
||||||
// Mask kayers are not processed here because they are a special case
|
// Mask kayers are not processed here because they are a special case
|
||||||
if( (layer_id == B_Mask) || (layer_id == F_Mask) )
|
if( (layer_id == B_Mask) || (layer_id == F_Mask) )
|
||||||
continue;
|
continue;
|
||||||
|
@ -718,152 +729,155 @@ void C3D_RENDER_RAYTRACING::reload( REPORTER* aStatusReporter, REPORTER* aWarnin
|
||||||
createItemsFromContainer( m_boardAdapter.GetPlatedPads_Back(), B_Cu, &m_materials.m_Copper, layerColor_B_Cu, -m_boardAdapter.GetCopperThickness3DU() * 0.1f );
|
createItemsFromContainer( m_boardAdapter.GetPlatedPads_Back(), B_Cu, &m_materials.m_Copper, layerColor_B_Cu, -m_boardAdapter.GetCopperThickness3DU() * 0.1f );
|
||||||
}
|
}
|
||||||
|
|
||||||
// Add Mask layer
|
if( !aOnlyLoadCopperAndShapes )
|
||||||
// Solder mask layers are "negative" layers so the elements that we have
|
|
||||||
// (in the container) should remove the board outline.
|
|
||||||
// We will check for all objects in the outline if it intersects any object
|
|
||||||
// in the layer container and also any hole.
|
|
||||||
// /////////////////////////////////////////////////////////////////////////
|
|
||||||
if( m_boardAdapter.GetFlag( FL_SOLDERMASK ) &&
|
|
||||||
(m_outlineBoard2dObjects->GetList().size() >= 1) )
|
|
||||||
{
|
{
|
||||||
const CMATERIAL *materialLayer = &m_materials.m_SolderMask;
|
// Add Mask layer
|
||||||
|
// Solder mask layers are "negative" layers so the elements that we have
|
||||||
for( MAP_CONTAINER_2D::const_iterator ii = m_boardAdapter.GetMapLayers().begin();
|
// (in the container) should remove the board outline.
|
||||||
ii != m_boardAdapter.GetMapLayers().end();
|
// We will check for all objects in the outline if it intersects any object
|
||||||
++ii )
|
// in the layer container and also any hole.
|
||||||
|
// /////////////////////////////////////////////////////////////////////////
|
||||||
|
if( m_boardAdapter.GetFlag( FL_SOLDERMASK ) &&
|
||||||
|
(m_outlineBoard2dObjects->GetList().size() >= 1) )
|
||||||
{
|
{
|
||||||
PCB_LAYER_ID layer_id = static_cast<PCB_LAYER_ID>(ii->first);
|
const CMATERIAL *materialLayer = &m_materials.m_SolderMask;
|
||||||
|
|
||||||
const CBVHCONTAINER2D *containerLayer2d =
|
for( MAP_CONTAINER_2D::const_iterator ii = m_boardAdapter.GetMapLayers().begin();
|
||||||
static_cast<const CBVHCONTAINER2D *>(ii->second);
|
ii != m_boardAdapter.GetMapLayers().end();
|
||||||
|
++ii )
|
||||||
// Only get the Solder mask layers
|
|
||||||
if( !((layer_id == B_Mask) || (layer_id == F_Mask)) )
|
|
||||||
continue;
|
|
||||||
|
|
||||||
SFVEC3F layerColor;
|
|
||||||
if( m_boardAdapter.GetFlag( FL_USE_REALISTIC_MODE ) )
|
|
||||||
{
|
{
|
||||||
if( layer_id == B_Mask )
|
PCB_LAYER_ID layer_id = static_cast<PCB_LAYER_ID>(ii->first);
|
||||||
layerColor = m_boardAdapter.m_SolderMaskColorBot;
|
|
||||||
else
|
|
||||||
layerColor = m_boardAdapter.m_SolderMaskColorTop;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
layerColor = m_boardAdapter.GetLayerColor( layer_id );
|
|
||||||
|
|
||||||
const float zLayerMin = m_boardAdapter.GetLayerBottomZpos3DU( layer_id );
|
const CBVHCONTAINER2D *containerLayer2d =
|
||||||
const float zLayerMax = m_boardAdapter.GetLayerTopZpos3DU( layer_id );
|
static_cast<const CBVHCONTAINER2D *>(ii->second);
|
||||||
|
|
||||||
// Get the outline board objects
|
// Only get the Solder mask layers
|
||||||
const LIST_OBJECT2D &listObjects = m_outlineBoard2dObjects->GetList();
|
if( !((layer_id == B_Mask) || (layer_id == F_Mask)) )
|
||||||
|
continue;
|
||||||
|
|
||||||
for( LIST_OBJECT2D::const_iterator object2d_iterator = listObjects.begin();
|
SFVEC3F layerColor;
|
||||||
object2d_iterator != listObjects.end();
|
if( m_boardAdapter.GetFlag( FL_USE_REALISTIC_MODE ) )
|
||||||
++object2d_iterator )
|
|
||||||
{
|
|
||||||
const COBJECT2D *object2d_A = static_cast<const COBJECT2D *>(*object2d_iterator);
|
|
||||||
|
|
||||||
std::vector<const COBJECT2D *> *object2d_B = new std::vector<const COBJECT2D *>();
|
|
||||||
|
|
||||||
// Check if there are any THT that intersects this outline object part
|
|
||||||
if( !m_boardAdapter.GetThroughHole_Outer().GetList().empty() )
|
|
||||||
{
|
{
|
||||||
|
if( layer_id == B_Mask )
|
||||||
CONST_LIST_OBJECT2D intersectionList;
|
layerColor = m_boardAdapter.m_SolderMaskColorBot;
|
||||||
|
else
|
||||||
m_boardAdapter.GetThroughHole_Outer().GetListObjectsIntersects(
|
layerColor = m_boardAdapter.m_SolderMaskColorTop;
|
||||||
object2d_A->GetBBox(),
|
|
||||||
intersectionList );
|
|
||||||
|
|
||||||
if( !intersectionList.empty() )
|
|
||||||
{
|
|
||||||
for( CONST_LIST_OBJECT2D::const_iterator hole = intersectionList.begin();
|
|
||||||
hole != intersectionList.end();
|
|
||||||
++hole )
|
|
||||||
{
|
|
||||||
const COBJECT2D *hole2d = static_cast<const COBJECT2D *>(*hole);
|
|
||||||
|
|
||||||
if( object2d_A->Intersects( hole2d->GetBBox() ) )
|
|
||||||
//if( object2d_A->GetBBox().Intersects( hole2d->GetBBox() ) )
|
|
||||||
object2d_B->push_back( hole2d );
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Check if there are any objects in the layer to subtract with the
|
|
||||||
// corrent object
|
|
||||||
if( !containerLayer2d->GetList().empty() )
|
|
||||||
{
|
|
||||||
CONST_LIST_OBJECT2D intersectionList;
|
|
||||||
|
|
||||||
containerLayer2d->GetListObjectsIntersects( object2d_A->GetBBox(),
|
|
||||||
intersectionList );
|
|
||||||
|
|
||||||
if( !intersectionList.empty() )
|
|
||||||
{
|
|
||||||
for( CONST_LIST_OBJECT2D::const_iterator obj = intersectionList.begin();
|
|
||||||
obj != intersectionList.end();
|
|
||||||
++obj )
|
|
||||||
{
|
|
||||||
const COBJECT2D *obj2d = static_cast<const COBJECT2D *>(*obj);
|
|
||||||
|
|
||||||
//if( object2d_A->Intersects( obj2d->GetBBox() ) )
|
|
||||||
//if( object2d_A->GetBBox().Intersects( obj2d->GetBBox() ) )
|
|
||||||
object2d_B->push_back( obj2d );
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if( object2d_B->empty() )
|
|
||||||
{
|
|
||||||
delete object2d_B;
|
|
||||||
object2d_B = CSGITEM_EMPTY;
|
|
||||||
}
|
|
||||||
|
|
||||||
if( object2d_B == CSGITEM_EMPTY )
|
|
||||||
{
|
|
||||||
#if 0
|
|
||||||
create_3d_object_from( m_object_container,
|
|
||||||
object2d_A,
|
|
||||||
zLayerMin,
|
|
||||||
zLayerMax,
|
|
||||||
materialLayer,
|
|
||||||
layerColor );
|
|
||||||
#else
|
|
||||||
CLAYERITEM *objPtr = new CLAYERITEM( object2d_A,
|
|
||||||
zLayerMin,
|
|
||||||
zLayerMax );
|
|
||||||
|
|
||||||
objPtr->SetMaterial( materialLayer );
|
|
||||||
objPtr->SetColor( ConvertSRGBToLinear( layerColor ) );
|
|
||||||
|
|
||||||
m_object_container.Add( objPtr );
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
layerColor = m_boardAdapter.GetLayerColor( layer_id );
|
||||||
|
|
||||||
|
const float zLayerMin = m_boardAdapter.GetLayerBottomZpos3DU( layer_id );
|
||||||
|
const float zLayerMax = m_boardAdapter.GetLayerTopZpos3DU( layer_id );
|
||||||
|
|
||||||
|
// Get the outline board objects
|
||||||
|
const LIST_OBJECT2D &listObjects = m_outlineBoard2dObjects->GetList();
|
||||||
|
|
||||||
|
for( LIST_OBJECT2D::const_iterator object2d_iterator = listObjects.begin();
|
||||||
|
object2d_iterator != listObjects.end();
|
||||||
|
++object2d_iterator )
|
||||||
{
|
{
|
||||||
CITEMLAYERCSG2D *itemCSG2d = new CITEMLAYERCSG2D( object2d_A,
|
const COBJECT2D *object2d_A = static_cast<const COBJECT2D *>(*object2d_iterator);
|
||||||
object2d_B,
|
|
||||||
CSGITEM_FULL,
|
|
||||||
object2d_A->GetBoardItem() );
|
|
||||||
|
|
||||||
m_containerWithObjectsToDelete.Add( itemCSG2d );
|
std::vector<const COBJECT2D *> *object2d_B = new std::vector<const COBJECT2D *>();
|
||||||
|
|
||||||
CLAYERITEM *objPtr = new CLAYERITEM( itemCSG2d,
|
// Check if there are any THT that intersects this outline object part
|
||||||
zLayerMin,
|
if( !m_boardAdapter.GetThroughHole_Outer().GetList().empty() )
|
||||||
zLayerMax );
|
{
|
||||||
objPtr->SetMaterial( materialLayer );
|
|
||||||
objPtr->SetColor( ConvertSRGBToLinear( layerColor ) );
|
|
||||||
|
|
||||||
m_object_container.Add( objPtr );
|
CONST_LIST_OBJECT2D intersectionList;
|
||||||
|
|
||||||
|
m_boardAdapter.GetThroughHole_Outer().GetListObjectsIntersects(
|
||||||
|
object2d_A->GetBBox(),
|
||||||
|
intersectionList );
|
||||||
|
|
||||||
|
if( !intersectionList.empty() )
|
||||||
|
{
|
||||||
|
for( CONST_LIST_OBJECT2D::const_iterator hole = intersectionList.begin();
|
||||||
|
hole != intersectionList.end();
|
||||||
|
++hole )
|
||||||
|
{
|
||||||
|
const COBJECT2D *hole2d = static_cast<const COBJECT2D *>(*hole);
|
||||||
|
|
||||||
|
if( object2d_A->Intersects( hole2d->GetBBox() ) )
|
||||||
|
//if( object2d_A->GetBBox().Intersects( hole2d->GetBBox() ) )
|
||||||
|
object2d_B->push_back( hole2d );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check if there are any objects in the layer to subtract with the
|
||||||
|
// corrent object
|
||||||
|
if( !containerLayer2d->GetList().empty() )
|
||||||
|
{
|
||||||
|
CONST_LIST_OBJECT2D intersectionList;
|
||||||
|
|
||||||
|
containerLayer2d->GetListObjectsIntersects( object2d_A->GetBBox(),
|
||||||
|
intersectionList );
|
||||||
|
|
||||||
|
if( !intersectionList.empty() )
|
||||||
|
{
|
||||||
|
for( CONST_LIST_OBJECT2D::const_iterator obj = intersectionList.begin();
|
||||||
|
obj != intersectionList.end();
|
||||||
|
++obj )
|
||||||
|
{
|
||||||
|
const COBJECT2D *obj2d = static_cast<const COBJECT2D *>(*obj);
|
||||||
|
|
||||||
|
//if( object2d_A->Intersects( obj2d->GetBBox() ) )
|
||||||
|
//if( object2d_A->GetBBox().Intersects( obj2d->GetBBox() ) )
|
||||||
|
object2d_B->push_back( obj2d );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if( object2d_B->empty() )
|
||||||
|
{
|
||||||
|
delete object2d_B;
|
||||||
|
object2d_B = CSGITEM_EMPTY;
|
||||||
|
}
|
||||||
|
|
||||||
|
if( object2d_B == CSGITEM_EMPTY )
|
||||||
|
{
|
||||||
|
#if 0
|
||||||
|
create_3d_object_from( m_object_container,
|
||||||
|
object2d_A,
|
||||||
|
zLayerMin,
|
||||||
|
zLayerMax,
|
||||||
|
materialLayer,
|
||||||
|
layerColor );
|
||||||
|
#else
|
||||||
|
CLAYERITEM *objPtr = new CLAYERITEM( object2d_A,
|
||||||
|
zLayerMin,
|
||||||
|
zLayerMax );
|
||||||
|
|
||||||
|
objPtr->SetMaterial( materialLayer );
|
||||||
|
objPtr->SetColor( ConvertSRGBToLinear( layerColor ) );
|
||||||
|
|
||||||
|
m_object_container.Add( objPtr );
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
CITEMLAYERCSG2D *itemCSG2d = new CITEMLAYERCSG2D( object2d_A,
|
||||||
|
object2d_B,
|
||||||
|
CSGITEM_FULL,
|
||||||
|
object2d_A->GetBoardItem() );
|
||||||
|
|
||||||
|
m_containerWithObjectsToDelete.Add( itemCSG2d );
|
||||||
|
|
||||||
|
CLAYERITEM *objPtr = new CLAYERITEM( itemCSG2d,
|
||||||
|
zLayerMin,
|
||||||
|
zLayerMax );
|
||||||
|
objPtr->SetMaterial( materialLayer );
|
||||||
|
objPtr->SetColor( ConvertSRGBToLinear( layerColor ) );
|
||||||
|
|
||||||
|
m_object_container.Add( objPtr );
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
add_3D_vias_and_pads_to_container();
|
add_3D_vias_and_pads_to_container();
|
||||||
|
}
|
||||||
|
|
||||||
#ifdef PRINT_STATISTICS_3D_VIEWER
|
#ifdef PRINT_STATISTICS_3D_VIEWER
|
||||||
unsigned stats_endConvertTime = GetRunningMicroSecs();
|
unsigned stats_endConvertTime = GetRunningMicroSecs();
|
||||||
|
@ -871,136 +885,138 @@ void C3D_RENDER_RAYTRACING::reload( REPORTER* aStatusReporter, REPORTER* aWarnin
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
load_3D_models( false );
|
load_3D_models( m_object_container, aOnlyLoadCopperAndShapes );
|
||||||
|
|
||||||
|
|
||||||
#ifdef PRINT_STATISTICS_3D_VIEWER
|
#ifdef PRINT_STATISTICS_3D_VIEWER
|
||||||
unsigned stats_endLoad3DmodelsTime = GetRunningMicroSecs();
|
unsigned stats_endLoad3DmodelsTime = GetRunningMicroSecs();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// Add floor
|
if( !aOnlyLoadCopperAndShapes )
|
||||||
// /////////////////////////////////////////////////////////////////////////
|
|
||||||
if( m_boardAdapter.GetFlag( FL_RENDER_RAYTRACING_BACKFLOOR ) )
|
|
||||||
{
|
{
|
||||||
CBBOX boardBBox = m_boardAdapter.GetBBox3DU();
|
// Add floor
|
||||||
|
// /////////////////////////////////////////////////////////////////////////
|
||||||
if( boardBBox.IsInitialized() )
|
if( m_boardAdapter.GetFlag( FL_RENDER_RAYTRACING_BACKFLOOR ) )
|
||||||
{
|
{
|
||||||
boardBBox.Scale( 3.0f );
|
CBBOX boardBBox = m_boardAdapter.GetBBox3DU();
|
||||||
|
|
||||||
if( m_object_container.GetList().size() > 0 )
|
if( boardBBox.IsInitialized() )
|
||||||
{
|
{
|
||||||
CBBOX containerBBox = m_object_container.GetBBox();
|
boardBBox.Scale( 3.0f );
|
||||||
|
|
||||||
containerBBox.Scale( 1.3f );
|
if( m_object_container.GetList().size() > 0 )
|
||||||
|
{
|
||||||
|
CBBOX containerBBox = m_object_container.GetBBox();
|
||||||
|
|
||||||
const SFVEC3F centerBBox = containerBBox.GetCenter();
|
containerBBox.Scale( 1.3f );
|
||||||
|
|
||||||
// Floor triangles
|
const SFVEC3F centerBBox = containerBBox.GetCenter();
|
||||||
const float minZ = glm::min( containerBBox.Min().z,
|
|
||||||
boardBBox.Min().z );
|
|
||||||
|
|
||||||
const SFVEC3F v1 = SFVEC3F( -RANGE_SCALE_3D * 4.0f,
|
// Floor triangles
|
||||||
-RANGE_SCALE_3D * 4.0f,
|
const float minZ = glm::min( containerBBox.Min().z,
|
||||||
minZ ) +
|
boardBBox.Min().z );
|
||||||
SFVEC3F( centerBBox.x,
|
|
||||||
centerBBox.y,
|
|
||||||
0.0f );
|
|
||||||
|
|
||||||
const SFVEC3F v3 = SFVEC3F( +RANGE_SCALE_3D * 4.0f,
|
const SFVEC3F v1 = SFVEC3F( -RANGE_SCALE_3D * 4.0f,
|
||||||
+RANGE_SCALE_3D * 4.0f,
|
-RANGE_SCALE_3D * 4.0f,
|
||||||
minZ ) +
|
minZ ) +
|
||||||
SFVEC3F( centerBBox.x,
|
SFVEC3F( centerBBox.x,
|
||||||
centerBBox.y,
|
centerBBox.y,
|
||||||
0.0f );
|
0.0f );
|
||||||
|
|
||||||
const SFVEC3F v2 = SFVEC3F( v1.x, v3.y, v1.z );
|
const SFVEC3F v3 = SFVEC3F( +RANGE_SCALE_3D * 4.0f,
|
||||||
const SFVEC3F v4 = SFVEC3F( v3.x, v1.y, v1.z );
|
+RANGE_SCALE_3D * 4.0f,
|
||||||
|
minZ ) +
|
||||||
|
SFVEC3F( centerBBox.x,
|
||||||
|
centerBBox.y,
|
||||||
|
0.0f );
|
||||||
|
|
||||||
SFVEC3F backgroundColor =
|
const SFVEC3F v2 = SFVEC3F( v1.x, v3.y, v1.z );
|
||||||
ConvertSRGBToLinear( static_cast<SFVEC3F>( m_boardAdapter.m_BgColorTop ) );
|
const SFVEC3F v4 = SFVEC3F( v3.x, v1.y, v1.z );
|
||||||
|
|
||||||
CTRIANGLE *newTriangle1 = new CTRIANGLE( v1, v2, v3 );
|
SFVEC3F backgroundColor =
|
||||||
CTRIANGLE *newTriangle2 = new CTRIANGLE( v3, v4, v1 );
|
ConvertSRGBToLinear( static_cast<SFVEC3F>( m_boardAdapter.m_BgColorTop ) );
|
||||||
|
|
||||||
m_object_container.Add( newTriangle1 );
|
CTRIANGLE *newTriangle1 = new CTRIANGLE( v1, v2, v3 );
|
||||||
m_object_container.Add( newTriangle2 );
|
CTRIANGLE *newTriangle2 = new CTRIANGLE( v3, v4, v1 );
|
||||||
|
|
||||||
newTriangle1->SetMaterial( (const CMATERIAL *)&m_materials.m_Floor );
|
m_object_container.Add( newTriangle1 );
|
||||||
newTriangle2->SetMaterial( (const CMATERIAL *)&m_materials.m_Floor );
|
m_object_container.Add( newTriangle2 );
|
||||||
|
|
||||||
newTriangle1->SetColor( backgroundColor );
|
newTriangle1->SetMaterial( (const CMATERIAL *)&m_materials.m_Floor );
|
||||||
newTriangle2->SetColor( backgroundColor );
|
newTriangle2->SetMaterial( (const CMATERIAL *)&m_materials.m_Floor );
|
||||||
|
|
||||||
// Ceiling triangles
|
newTriangle1->SetColor( backgroundColor );
|
||||||
const float maxZ = glm::max( containerBBox.Max().z,
|
newTriangle2->SetColor( backgroundColor );
|
||||||
boardBBox.Max().z );
|
|
||||||
|
|
||||||
const SFVEC3F v5 = SFVEC3F( v1.x, v1.y, maxZ );
|
// Ceiling triangles
|
||||||
const SFVEC3F v6 = SFVEC3F( v2.x, v2.y, maxZ );
|
const float maxZ = glm::max( containerBBox.Max().z,
|
||||||
const SFVEC3F v7 = SFVEC3F( v3.x, v3.y, maxZ );
|
boardBBox.Max().z );
|
||||||
const SFVEC3F v8 = SFVEC3F( v4.x, v4.y, maxZ );
|
|
||||||
|
|
||||||
CTRIANGLE *newTriangle3 = new CTRIANGLE( v7, v6, v5 );
|
const SFVEC3F v5 = SFVEC3F( v1.x, v1.y, maxZ );
|
||||||
CTRIANGLE *newTriangle4 = new CTRIANGLE( v5, v8, v7 );
|
const SFVEC3F v6 = SFVEC3F( v2.x, v2.y, maxZ );
|
||||||
|
const SFVEC3F v7 = SFVEC3F( v3.x, v3.y, maxZ );
|
||||||
|
const SFVEC3F v8 = SFVEC3F( v4.x, v4.y, maxZ );
|
||||||
|
|
||||||
m_object_container.Add( newTriangle3 );
|
CTRIANGLE *newTriangle3 = new CTRIANGLE( v7, v6, v5 );
|
||||||
m_object_container.Add( newTriangle4 );
|
CTRIANGLE *newTriangle4 = new CTRIANGLE( v5, v8, v7 );
|
||||||
|
|
||||||
newTriangle3->SetMaterial( (const CMATERIAL *)&m_materials.m_Floor );
|
m_object_container.Add( newTriangle3 );
|
||||||
newTriangle4->SetMaterial( (const CMATERIAL *)&m_materials.m_Floor );
|
m_object_container.Add( newTriangle4 );
|
||||||
|
|
||||||
newTriangle3->SetColor( backgroundColor );
|
newTriangle3->SetMaterial( (const CMATERIAL *)&m_materials.m_Floor );
|
||||||
newTriangle4->SetColor( backgroundColor );
|
newTriangle4->SetMaterial( (const CMATERIAL *)&m_materials.m_Floor );
|
||||||
|
|
||||||
|
newTriangle3->SetColor( backgroundColor );
|
||||||
|
newTriangle4->SetColor( backgroundColor );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// Init initial lights
|
||||||
|
// /////////////////////////////////////////////////////////////////////////
|
||||||
|
m_lights.Clear();
|
||||||
|
|
||||||
|
auto IsColorZero = [] ( const SFVEC3F& aSource )
|
||||||
|
{
|
||||||
|
return ( ( aSource.r < ( 1.0f / 255.0f ) ) &&
|
||||||
|
( aSource.g < ( 1.0f / 255.0f ) ) &&
|
||||||
|
( aSource.b < ( 1.0f / 255.0f ) ) );
|
||||||
|
};
|
||||||
|
|
||||||
|
m_camera_light = new CDIRECTIONALLIGHT( SFVEC3F( 0.0f, 0.0f, 0.0f ),
|
||||||
|
m_boardAdapter.m_raytrace_lightColorCamera );
|
||||||
|
m_camera_light->SetCastShadows( false );
|
||||||
|
|
||||||
|
if( !IsColorZero( m_boardAdapter.m_raytrace_lightColorCamera ) )
|
||||||
|
m_lights.Add( m_camera_light );
|
||||||
|
|
||||||
|
const SFVEC3F& boardCenter = m_boardAdapter.GetBBox3DU().GetCenter();
|
||||||
|
|
||||||
|
if( !IsColorZero( m_boardAdapter.m_raytrace_lightColorTop ) )
|
||||||
|
m_lights.Add( new CPOINTLIGHT( SFVEC3F( boardCenter.x, boardCenter.y, +RANGE_SCALE_3D * 2.0f ),
|
||||||
|
m_boardAdapter.m_raytrace_lightColorTop ) );
|
||||||
|
|
||||||
|
if( !IsColorZero( m_boardAdapter.m_raytrace_lightColorBottom ) )
|
||||||
|
m_lights.Add( new CPOINTLIGHT( SFVEC3F( boardCenter.x, boardCenter.y, -RANGE_SCALE_3D * 2.0f ),
|
||||||
|
m_boardAdapter.m_raytrace_lightColorBottom ) );
|
||||||
|
|
||||||
|
wxASSERT( m_boardAdapter.m_raytrace_lightColor.size()
|
||||||
|
== m_boardAdapter.m_raytrace_lightSphericalCoords.size() );
|
||||||
|
|
||||||
|
for( size_t i = 0; i < m_boardAdapter.m_raytrace_lightColor.size(); ++i )
|
||||||
|
{
|
||||||
|
if( !IsColorZero( m_boardAdapter.m_raytrace_lightColor[i] ) )
|
||||||
|
{
|
||||||
|
const SFVEC2F sc = m_boardAdapter.m_raytrace_lightSphericalCoords[i];
|
||||||
|
|
||||||
|
m_lights.Add( new CDIRECTIONALLIGHT( SphericalToCartesian( glm::pi<float>() * sc.x,
|
||||||
|
glm::pi<float>() * sc.y ),
|
||||||
|
m_boardAdapter.m_raytrace_lightColor[i] ) );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// Init initial lights
|
|
||||||
// /////////////////////////////////////////////////////////////////////////
|
|
||||||
m_lights.Clear();
|
|
||||||
|
|
||||||
auto IsColorZero = [] ( const SFVEC3F& aSource )
|
|
||||||
{
|
|
||||||
return ( ( aSource.r < ( 1.0f / 255.0f ) ) &&
|
|
||||||
( aSource.g < ( 1.0f / 255.0f ) ) &&
|
|
||||||
( aSource.b < ( 1.0f / 255.0f ) ) );
|
|
||||||
};
|
|
||||||
|
|
||||||
m_camera_light = new CDIRECTIONALLIGHT( SFVEC3F( 0.0f, 0.0f, 0.0f ),
|
|
||||||
m_boardAdapter.m_raytrace_lightColorCamera );
|
|
||||||
m_camera_light->SetCastShadows( false );
|
|
||||||
|
|
||||||
if( !IsColorZero( m_boardAdapter.m_raytrace_lightColorCamera ) )
|
|
||||||
m_lights.Add( m_camera_light );
|
|
||||||
|
|
||||||
const SFVEC3F& boardCenter = m_boardAdapter.GetBBox3DU().GetCenter();
|
|
||||||
|
|
||||||
if( !IsColorZero( m_boardAdapter.m_raytrace_lightColorTop ) )
|
|
||||||
m_lights.Add( new CPOINTLIGHT( SFVEC3F( boardCenter.x, boardCenter.y, +RANGE_SCALE_3D * 2.0f ),
|
|
||||||
m_boardAdapter.m_raytrace_lightColorTop ) );
|
|
||||||
|
|
||||||
if( !IsColorZero( m_boardAdapter.m_raytrace_lightColorBottom ) )
|
|
||||||
m_lights.Add( new CPOINTLIGHT( SFVEC3F( boardCenter.x, boardCenter.y, -RANGE_SCALE_3D * 2.0f ),
|
|
||||||
m_boardAdapter.m_raytrace_lightColorBottom ) );
|
|
||||||
|
|
||||||
wxASSERT( m_boardAdapter.m_raytrace_lightColor.size()
|
|
||||||
== m_boardAdapter.m_raytrace_lightSphericalCoords.size() );
|
|
||||||
|
|
||||||
for( size_t i = 0; i < m_boardAdapter.m_raytrace_lightColor.size(); ++i )
|
|
||||||
{
|
|
||||||
if( !IsColorZero( m_boardAdapter.m_raytrace_lightColor[i] ) )
|
|
||||||
{
|
|
||||||
const SFVEC2F sc = m_boardAdapter.m_raytrace_lightSphericalCoords[i];
|
|
||||||
|
|
||||||
m_lights.Add( new CDIRECTIONALLIGHT( SphericalToCartesian( glm::pi<float>() * sc.x,
|
|
||||||
glm::pi<float>() * sc.y ),
|
|
||||||
m_boardAdapter.m_raytrace_lightColor[i] ) );
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// Create an accelerator
|
// Create an accelerator
|
||||||
// /////////////////////////////////////////////////////////////////////////
|
// /////////////////////////////////////////////////////////////////////////
|
||||||
if( m_accelerator )
|
if( m_accelerator )
|
||||||
|
@ -1250,7 +1266,7 @@ void C3D_RENDER_RAYTRACING::add_3D_vias_and_pads_to_container()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void C3D_RENDER_RAYTRACING::load_3D_models( bool aSkipMaterialInformation )
|
void C3D_RENDER_RAYTRACING::load_3D_models( CCONTAINER &aDstContainer, bool aSkipMaterialInformation )
|
||||||
{
|
{
|
||||||
// Go for all modules
|
// Go for all modules
|
||||||
for( auto module : m_boardAdapter.GetBoard()->Modules() )
|
for( auto module : m_boardAdapter.GetBoard()->Modules() )
|
||||||
|
@ -1297,6 +1313,7 @@ void C3D_RENDER_RAYTRACING::load_3D_models( bool aSkipMaterialInformation )
|
||||||
modelunit_to_3d_units_factor,
|
modelunit_to_3d_units_factor,
|
||||||
modelunit_to_3d_units_factor ) );
|
modelunit_to_3d_units_factor ) );
|
||||||
|
|
||||||
|
BOARD_ITEM* boardItem = dynamic_cast<BOARD_ITEM*>( module );
|
||||||
|
|
||||||
// Get the list of model files for this model
|
// Get the list of model files for this model
|
||||||
S3D_CACHE* cacheMgr = m_boardAdapter.Get3DCacheManager();
|
S3D_CACHE* cacheMgr = m_boardAdapter.Get3DCacheManager();
|
||||||
|
@ -1341,7 +1358,12 @@ void C3D_RENDER_RAYTRACING::load_3D_models( bool aSkipMaterialInformation )
|
||||||
sM->m_Scale.y,
|
sM->m_Scale.y,
|
||||||
sM->m_Scale.z ) );
|
sM->m_Scale.z ) );
|
||||||
|
|
||||||
add_3D_models( modelPtr, modelMatrix, (float)sM->m_Opacity, aSkipMaterialInformation );
|
add_3D_models( aDstContainer,
|
||||||
|
modelPtr,
|
||||||
|
modelMatrix,
|
||||||
|
(float)sM->m_Opacity,
|
||||||
|
aSkipMaterialInformation,
|
||||||
|
boardItem );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1462,10 +1484,12 @@ MODEL_MATERIALS *C3D_RENDER_RAYTRACING::get_3D_model_material( const S3DMODEL *a
|
||||||
return materialVector;
|
return materialVector;
|
||||||
}
|
}
|
||||||
|
|
||||||
void C3D_RENDER_RAYTRACING::add_3D_models( const S3DMODEL *a3DModel,
|
void C3D_RENDER_RAYTRACING::add_3D_models( CCONTAINER &aDstContainer,
|
||||||
|
const S3DMODEL *a3DModel,
|
||||||
const glm::mat4 &aModelMatrix,
|
const glm::mat4 &aModelMatrix,
|
||||||
float aModuleOpacity,
|
float aModuleOpacity,
|
||||||
bool aSkipMaterialInformation )
|
bool aSkipMaterialInformation,
|
||||||
|
BOARD_ITEM *aBoardItem )
|
||||||
{
|
{
|
||||||
|
|
||||||
// Validate a3DModel pointers
|
// Validate a3DModel pointers
|
||||||
|
@ -1562,7 +1586,9 @@ void C3D_RENDER_RAYTRACING::add_3D_models( const S3DMODEL *a3DModel,
|
||||||
CTRIANGLE *newTriangle = new CTRIANGLE( vt0, vt2, vt1,
|
CTRIANGLE *newTriangle = new CTRIANGLE( vt0, vt2, vt1,
|
||||||
nt0, nt2, nt1 );
|
nt0, nt2, nt1 );
|
||||||
|
|
||||||
m_object_container.Add( newTriangle );
|
newTriangle->SetBoardItem( aBoardItem );
|
||||||
|
|
||||||
|
aDstContainer.Add( newTriangle );
|
||||||
|
|
||||||
if( !aSkipMaterialInformation )
|
if( !aSkipMaterialInformation )
|
||||||
{
|
{
|
||||||
|
|
|
@ -179,7 +179,7 @@ bool C3D_RENDER_RAYTRACING::Redraw(
|
||||||
|
|
||||||
//aIsMoving = true;
|
//aIsMoving = true;
|
||||||
requestRedraw = true;
|
requestRedraw = true;
|
||||||
reload( aStatusReporter, aWarningReporter );
|
Reload( aStatusReporter, aWarningReporter, false );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -2079,3 +2079,18 @@ void C3D_RENDER_RAYTRACING::initialize_block_positions()
|
||||||
|
|
||||||
opengl_init_pbo();
|
opengl_init_pbo();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
BOARD_ITEM *C3D_RENDER_RAYTRACING::IntersectBoardItem( const RAY &aRay )
|
||||||
|
{
|
||||||
|
HITINFO hitInfo;
|
||||||
|
hitInfo.m_tHit = std::numeric_limits<float>::infinity();
|
||||||
|
|
||||||
|
if( m_accelerator )
|
||||||
|
if( m_accelerator->Intersect( aRay, hitInfo ) )
|
||||||
|
{
|
||||||
|
if( hitInfo.pHitObject )
|
||||||
|
return hitInfo.pHitObject->GetBoardItem();
|
||||||
|
}
|
||||||
|
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
|
|
@ -69,12 +69,15 @@ public:
|
||||||
|
|
||||||
int GetWaitForEditingTimeOut() override;
|
int GetWaitForEditingTimeOut() override;
|
||||||
|
|
||||||
|
void Reload( REPORTER* aStatusReporter, REPORTER* aWarningReporter, bool aOnlyLoadCopperAndShapes );
|
||||||
|
|
||||||
|
BOARD_ITEM *IntersectBoardItem( const RAY &aRay );
|
||||||
|
|
||||||
private:
|
private:
|
||||||
bool initializeOpenGL();
|
bool initializeOpenGL();
|
||||||
void initializeNewWindowSize();
|
void initializeNewWindowSize();
|
||||||
void opengl_init_pbo();
|
void opengl_init_pbo();
|
||||||
void opengl_delete_pbo();
|
void opengl_delete_pbo();
|
||||||
void reload( REPORTER* aStatusReporter, REPORTER* aWarningReporter );
|
|
||||||
void createItemsFromContainer( const CBVHCONTAINER2D *aContainer2d,
|
void createItemsFromContainer( const CBVHCONTAINER2D *aContainer2d,
|
||||||
PCB_LAYER_ID aLayer_id,
|
PCB_LAYER_ID aLayer_id,
|
||||||
const CMATERIAL *aMaterialLayer,
|
const CMATERIAL *aMaterialLayer,
|
||||||
|
@ -201,11 +204,13 @@ private:
|
||||||
void add_3D_vias_and_pads_to_container();
|
void add_3D_vias_and_pads_to_container();
|
||||||
void insert3DViaHole( const VIA* aVia );
|
void insert3DViaHole( const VIA* aVia );
|
||||||
void insert3DPadHole( const D_PAD* aPad );
|
void insert3DPadHole( const D_PAD* aPad );
|
||||||
void load_3D_models( bool aSkipMaterialInformation );
|
void load_3D_models( CCONTAINER &aDstContainer, bool aSkipMaterialInformation );
|
||||||
void add_3D_models( const S3DMODEL *a3DModel,
|
void add_3D_models( CCONTAINER &aDstContainer,
|
||||||
|
const S3DMODEL *a3DModel,
|
||||||
const glm::mat4 &aModelMatrix,
|
const glm::mat4 &aModelMatrix,
|
||||||
float aModuleOpacity,
|
float aModuleOpacity,
|
||||||
bool aSkipMaterialInformation );
|
bool aSkipMaterialInformation,
|
||||||
|
BOARD_ITEM *aBoardItem );
|
||||||
|
|
||||||
MODEL_MATERIALS *get_3D_model_material( const S3DMODEL *a3DModel );
|
MODEL_MATERIALS *get_3D_model_material( const S3DMODEL *a3DModel );
|
||||||
|
|
||||||
|
|
|
@ -42,6 +42,7 @@ COBJECT::COBJECT( OBJECT3D_TYPE aObjType )
|
||||||
COBJECT3D_STATS::Instance().AddOne( aObjType );
|
COBJECT3D_STATS::Instance().AddOne( aObjType );
|
||||||
m_material = &s_defaultMaterial;
|
m_material = &s_defaultMaterial;
|
||||||
m_modelTransparency = 0.0f;
|
m_modelTransparency = 0.0f;
|
||||||
|
m_boardItem = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -34,6 +34,7 @@
|
||||||
#include "../hitinfo.h"
|
#include "../hitinfo.h"
|
||||||
#include "../cmaterial.h"
|
#include "../cmaterial.h"
|
||||||
|
|
||||||
|
#include <class_board_item.h>
|
||||||
|
|
||||||
enum class OBJECT3D_TYPE
|
enum class OBJECT3D_TYPE
|
||||||
{
|
{
|
||||||
|
@ -55,6 +56,8 @@ protected:
|
||||||
OBJECT3D_TYPE m_obj_type;
|
OBJECT3D_TYPE m_obj_type;
|
||||||
const CMATERIAL *m_material;
|
const CMATERIAL *m_material;
|
||||||
|
|
||||||
|
BOARD_ITEM *m_boardItem;
|
||||||
|
|
||||||
// m_modelTransparency combines the material and model opacity
|
// m_modelTransparency combines the material and model opacity
|
||||||
// 0.0 full opaque, 1.0 full transparent.
|
// 0.0 full opaque, 1.0 full transparent.
|
||||||
float m_modelTransparency;
|
float m_modelTransparency;
|
||||||
|
@ -63,6 +66,9 @@ public:
|
||||||
|
|
||||||
explicit COBJECT( OBJECT3D_TYPE aObjType );
|
explicit COBJECT( OBJECT3D_TYPE aObjType );
|
||||||
|
|
||||||
|
const void SetBoardItem( BOARD_ITEM *aBoardItem ) { m_boardItem = aBoardItem; }
|
||||||
|
BOARD_ITEM *GetBoardItem() const { return m_boardItem; }
|
||||||
|
|
||||||
void SetMaterial( const CMATERIAL *aMaterial )
|
void SetMaterial( const CMATERIAL *aMaterial )
|
||||||
{
|
{
|
||||||
m_material = aMaterial;
|
m_material = aMaterial;
|
||||||
|
|
|
@ -380,9 +380,13 @@ void CCAMERA::MakeRay( const SFVEC2F &aWindowPos, SFVEC3F &aOutOrigin, SFVEC3F &
|
||||||
void CCAMERA::MakeRayAtCurrrentMousePosition( SFVEC3F &aOutOrigin,
|
void CCAMERA::MakeRayAtCurrrentMousePosition( SFVEC3F &aOutOrigin,
|
||||||
SFVEC3F &aOutDirection ) const
|
SFVEC3F &aOutDirection ) const
|
||||||
{
|
{
|
||||||
MakeRay( SFVEC2I( m_lastPosition.x,
|
const SFVEC2I windowPos = SFVEC2I( m_lastPosition.x,
|
||||||
m_windowSize.y - m_lastPosition.y ),
|
m_windowSize.y - m_lastPosition.y );
|
||||||
aOutOrigin, aOutDirection );
|
|
||||||
|
if( ( windowPos.x < m_windowSize.x ) &&
|
||||||
|
( windowPos.y < m_windowSize.y ) )
|
||||||
|
MakeRay( windowPos,
|
||||||
|
aOutOrigin, aOutDirection );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -275,7 +275,7 @@ void EDA_3D_VIEWER::Redraw()
|
||||||
{
|
{
|
||||||
// Only update in OpenGL for an interactive interaction
|
// Only update in OpenGL for an interactive interaction
|
||||||
if( m_boardAdapter.RenderEngineGet() == RENDER_ENGINE::OPENGL_LEGACY )
|
if( m_boardAdapter.RenderEngineGet() == RENDER_ENGINE::OPENGL_LEGACY )
|
||||||
m_canvas->Refresh();
|
m_canvas->Request_refresh( true );
|
||||||
}
|
}
|
||||||
|
|
||||||
void EDA_3D_VIEWER::Exit3DFrame( wxCommandEvent &event )
|
void EDA_3D_VIEWER::Exit3DFrame( wxCommandEvent &event )
|
||||||
|
|
Loading…
Reference in New Issue