Compare commits

..

1 Commits

Author SHA1 Message Date
Wayne Stambaugh 76e224e0af Begin version 8 development. 2023-02-11 11:03:39 -05:00
686 changed files with 59760 additions and 83630 deletions
-20
View File
@@ -1,20 +0,0 @@
<!-- --------Before Creating a New Issue-----------
* Limit report to a single issue.
* Search the issue tracker to verify the issue has not already been reported.
* Complete all instructions between `template comment markers <>.
* Keep report contents limited to the necessary information required to fix the issue.
* When creating an issue against the stable version of KiCad, make sure the latest available stable version is installed as issues may have already been resolved in later stable versions. -->
# Description
<!-- What is the current behavior and what is the expected behavior? -->
<!-- If the issue is visual/graphical, please attach screenshots of the problem. -->
<!-- Add the issue details below this line and before the "Steps to reproduce" heading. -->
# Steps to reproduce
<!-- If there are multiple steps to reproduce it or it is a visual issue, then providing a screen recording as an attachment to this report is recommended. -->
<!-- If this issue is specific to a project, please attach the necessary files to this issue. -->
<!-- Add the steps to reproduce using the numbers below -->
<!-- Add new step numbers before the "KiCad Version" heading. -->
1.
# KiCad Version
+2 -3
View File
@@ -2,7 +2,7 @@
* This program source code file is part of KiCad, a free EDA CAD application.
*
* Copyright (C) 2015-2022 Mario Luzeiro <mrluzeiro@ua.pt>
* Copyright (C) 1992-2023 KiCad Developers, see AUTHORS.txt for contributors.
* Copyright (C) 1992-2022 KiCad Developers, see AUTHORS.txt for contributors.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@@ -671,8 +671,7 @@ bool BOARD_ADAPTER::createBoardPolygon( wxString* aErrorMsg )
return false;
}
// max dist from one endPt to next startPt
int chainingEpsilon = m_board->GetOutlinesChainingEpsilon();
int chainingEpsilon = pcbIUScale.mmToIU( 0.02 ); // max dist from one endPt to next startPt
success = BuildFootprintPolygonOutlines( m_board, m_board_poly,
m_board->GetDesignSettings().m_MaxError,
+2 -1
View File
@@ -342,7 +342,8 @@ private:
OBJECT_2D* createPadWithDrill( const PAD* aPad, int aInflateValue );
void addPads( const FOOTPRINT* aFootprint, CONTAINER_2D_BASE* aDstContainer,
PCB_LAYER_ID aLayerId, bool aSkipPlatedPads, bool aSkipNonPlatedPads );
PCB_LAYER_ID aLayerId, bool aSkipNPTHPadsWihNoCopper, bool aSkipPlatedPads,
bool aSkipNonPlatedPads );
void addFootprintShapes( const FOOTPRINT* aFootprint, CONTAINER_2D_BASE* aDstContainer,
PCB_LAYER_ID aLayerId );
@@ -145,7 +145,7 @@ void BOARD_ADAPTER::addText( const EDA_TEXT* aText, CONTAINER_2D_BASE* aContaine
void BOARD_ADAPTER::addShape( const PCB_DIMENSION_BASE* aDimension, CONTAINER_2D_BASE* aContainer,
const BOARD_ITEM* aOwner )
{
addText( aDimension, aContainer, aDimension );
addText( &aDimension->Text(), aContainer, aDimension );
const int linewidth = aDimension->GetLineThickness();
@@ -275,10 +275,6 @@ void BOARD_ADAPTER::createTrack( const PCB_TRACK* aTrack, CONTAINER_2D_BASE* aDs
int arcsegcount = GetArcToSegmentCount( radius, ARC_HIGH_DEF, arc_angle );
int circlesegcount;
// Avoid arcs that cannot be drawn
if( radius < std::numeric_limits<double>::min() || arc_angle.IsZero() )
break;
// We need a circle to segment count. However, the arc angle can be small, and the
// radius very big. so we calculate a reasonable value for circlesegcount.
if( arcsegcount <= 1 ) // The arc will be approximated by a segment
@@ -492,24 +488,41 @@ OBJECT_2D* BOARD_ADAPTER::createPadWithDrill( const PAD* aPad, int aInflateValue
void BOARD_ADAPTER::addPads( const FOOTPRINT* aFootprint, CONTAINER_2D_BASE* aContainer,
PCB_LAYER_ID aLayerId, bool aSkipPlatedPads, bool aSkipNonPlatedPads )
PCB_LAYER_ID aLayerId, bool aSkipNPTHPadsWihNoCopper,
bool aSkipPlatedPads, bool aSkipNonPlatedPads )
{
for( PAD* pad : aFootprint->Pads() )
{
if( !pad->IsOnLayer( aLayerId ) )
continue;
if( IsCopperLayer( aLayerId ) )
{
// Skip pad annulus when there isn't one (note: this is more discerning than
// pad->IsOnLayer(), which doesn't check for NPTH pads with holes that consume
// the entire pad).
if( !pad->IsOnCopperLayer() )
continue;
// Skip pad annulus when not connected on this layer (if removing is enabled)
if( !pad->FlashLayer( aLayerId ) && IsCopperLayer( aLayerId ) )
continue;
// Skip pad annulus when not connected on this layer (if removing is enabled)
if( !pad->FlashLayer( aLayerId ) )
continue;
// NPTH pads are not drawn on layers if the shape size and pos is the same as their hole:
if( aSkipNPTHPadsWihNoCopper && ( pad->GetAttribute() == PAD_ATTRIB::NPTH ) )
{
if( pad->GetDrillSize() == pad->GetSize() && pad->GetOffset() == wxPoint( 0, 0 ) )
{
switch( pad->GetShape() )
{
case PAD_SHAPE::CIRCLE:
if( pad->GetDrillShape() == PAD_DRILL_SHAPE_CIRCLE )
continue;
break;
case PAD_SHAPE::OVAL:
if( pad->GetDrillShape() != PAD_DRILL_SHAPE_CIRCLE )
continue;
break;
default:
break;
}
}
}
VECTOR2I margin( 0, 0 );
+6 -4
View File
@@ -525,7 +525,9 @@ void BOARD_ADAPTER::createLayers( REPORTER* aStatusReporter )
// ADD PADS
for( FOOTPRINT* footprint : m_board->Footprints() )
{
addPads( footprint, layerContainer, layer, renderPlatedPadsAsPlated, false );
// Note: NPTH pads are not drawn on copper layers when the pad has the same shape
// as its hole
addPads( footprint, layerContainer, layer, true, renderPlatedPadsAsPlated, false );
// Micro-wave footprints may have items on copper layers
addFootprintShapes( footprint, layerContainer, layer );
@@ -537,8 +539,8 @@ void BOARD_ADAPTER::createLayers( REPORTER* aStatusReporter )
// ADD PLATED PADS
for( FOOTPRINT* footprint : m_board->Footprints() )
{
addPads( footprint, m_platedPadsFront, F_Cu, false, true );
addPads( footprint, m_platedPadsBack, B_Cu, false, true );
addPads( footprint, m_platedPadsFront, F_Cu, true, false, true );
addPads( footprint, m_platedPadsBack, B_Cu, true, false, true );
}
m_platedPadsFront->BuildBVH();
@@ -993,7 +995,7 @@ void BOARD_ADAPTER::createLayers( REPORTER* aStatusReporter )
}
else
{
addPads( footprint, layerContainer, layer, false, false );
addPads( footprint, layerContainer, layer, false, false, false );
}
addFootprintShapes( footprint, layerContainer, layer );
-9
View File
@@ -383,15 +383,6 @@ void EDA_3D_CANVAS::DoRePaint()
if( m_glRC == nullptr )
m_glRC = GL_CONTEXT_MANAGER::Get().CreateCtx( this );
// CreateCtx could and does fail per sentry crash events, lets be graceful
if( m_glRC == nullptr )
{
warningReporter.Report( _( "OpenGL context creation error" ), RPT_SEVERITY_ERROR );
warningReporter.Finalize();
m_is_currently_painting.clear();
return;
}
GL_CONTEXT_MANAGER::Get().LockCtx( m_glRC, this );
// Set the OpenGL viewport according to the client size of this canvas.
@@ -257,13 +257,6 @@ void EDA_3D_MODEL_VIEWER::OnPaint( wxPaintEvent& event )
if( m_glRC == nullptr )
m_glRC = GL_CONTEXT_MANAGER::Get().CreateCtx( this );
// CreateCtx could and does fail per sentry crash events, lets be graceful
if( m_glRC == nullptr )
{
wxLogTrace( m_logTrace, wxT( "EDA_3D_MODEL_VIEWER::OnPaint creating gl context failed" ) );
return;
}
GL_CONTEXT_MANAGER::Get().LockCtx( m_glRC, this );
// Set the OpenGL viewport according to the client size of this canvas.
@@ -330,16 +323,8 @@ void EDA_3D_MODEL_VIEWER::OnPaint( wxPaintEvent& event )
m_ogl_3dmodel->BeginDrawMulti( true );
m_ogl_3dmodel->DrawOpaque( false );
glDepthMask( GL_FALSE );
glEnable( GL_BLEND );
glBlendFunc( GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA );
m_ogl_3dmodel->DrawTransparent( 1.0f, false );
glDisable( GL_BLEND );
glDepthMask( GL_TRUE );
m_ogl_3dmodel->EndDrawMulti();
glPopMatrix();
+14 -97
View File
@@ -27,14 +27,13 @@
* @file c_ogl_3dmodel.cpp
* @brief
*/
#include <algorithm>
#include <stdexcept>
#include <gal/opengl/kiglew.h> // Must be included first
#include "3d_model.h"
#include "opengl_utils.h"
#include "../common_ogl/ogl_utils.h"
#include "../3d_math.h"
#include <utility>
#include <wx/debug.h>
#include <wx/log.h>
#include <chrono>
@@ -178,11 +177,9 @@ MODEL_3D::MODEL_3D( const S3DMODEL& a3DModel, MATERIAL_MODE aMaterialMode )
// use material color for mesh bounding box or some sort of average vertex color.
glm::vec3 avg_color = material.m_Diffuse;
BBOX_3D &mesh_bbox = m_meshes_bbox[mesh_i];
for( unsigned int vtx_i = 0; vtx_i < mesh.m_VertexSize; ++vtx_i )
{
mesh_bbox.Union( mesh.m_Positions[vtx_i] );
m_meshes_bbox[mesh_i].Union( mesh.m_Positions[vtx_i] );
VERTEX& vtx_out = mesh_group.m_vertices[vtx_offset + vtx_i];
@@ -225,19 +222,16 @@ MODEL_3D::MODEL_3D( const S3DMODEL& a3DModel, MATERIAL_MODE aMaterialMode )
}
}
if( mesh_bbox.IsInitialized() )
if( m_meshes_bbox[mesh_i].IsInitialized() )
{
// generate geometry for the bounding box
MakeBbox( mesh_bbox, ( mesh_i + 1 ) * bbox_vtx_count,
MakeBbox( m_meshes_bbox[mesh_i], ( mesh_i + 1 ) * bbox_vtx_count,
&bbox_tmp_vertices[( mesh_i + 1 ) * bbox_vtx_count],
&bbox_tmp_indices[( mesh_i + 1 ) * bbox_idx_count],
{ avg_color, 1.0f } );
// bump the outer bounding box
m_model_bbox.Union( mesh_bbox );
// add to the material group
material.m_bbox.Union( mesh_bbox );
m_model_bbox.Union( m_meshes_bbox[mesh_i] );
}
@@ -416,9 +410,7 @@ void MODEL_3D::EndDrawMulti()
void MODEL_3D::Draw( bool aTransparent, float aOpacity, bool aUseSelectedMaterial,
const SFVEC3F& aSelectionColor,
const glm::mat4 *aModelWorldMatrix,
const SFVEC3F *aCameraWorldPos ) const
SFVEC3F& aSelectionColor ) const
{
if( aOpacity <= FLT_EPSILON )
return;
@@ -447,102 +439,27 @@ void MODEL_3D::Draw( bool aTransparent, float aOpacity, bool aUseSelectedMateria
glTexEnvfv( GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, (const float*)&param.x );
std::vector<const MODEL_3D::MATERIAL *> materialsToRender;
materialsToRender.reserve( m_materials.size() );
if( aModelWorldMatrix && aCameraWorldPos )
for( const MODEL_3D::MATERIAL& mat : m_materials )
{
// Sort Material groups
std::vector<std::pair<const MODEL_3D::MATERIAL*, float>> materialsSorted;
// Calculate the distance to the camera for each material group
for( const MODEL_3D::MATERIAL& mat : m_materials )
{
if( mat.m_render_idx_count == 0 )
{
continue;
}
if( ( mat.IsTransparent() != aTransparent )
if( ( mat.IsTransparent() != aTransparent )
&& ( aOpacity >= 1.0f )
&& m_materialMode != MATERIAL_MODE::DIFFUSE_ONLY )
{
continue;
}
const BBOX_3D& bBox = mat.m_bbox;
const SFVEC3F& bBoxCenter = bBox.GetCenter();
const SFVEC3F bBoxWorld = *aModelWorldMatrix * glm::vec4( bBoxCenter, 1.0f );
const float distanceToCamera = glm::length( *aCameraWorldPos - bBoxWorld );
materialsSorted.emplace_back( &mat, distanceToCamera );
}
// Sort from back to front
std::sort( materialsSorted.begin(), materialsSorted.end(),
[&]( std::pair<const MODEL_3D::MATERIAL*, float>& a,
std::pair<const MODEL_3D::MATERIAL*, float>& b ) {
// If A is inside B, then A is rendered first
if( b.first->m_bbox.Inside( a.first->m_bbox ) )
{
return true;
}
else
{
if( a.first->m_bbox.Inside( b.first->m_bbox ) )
{
return false;
}
}
return a.second > b.second;
} );
for( const std::pair<const MODEL_3D::MATERIAL*, float>& mat : materialsSorted )
{
materialsToRender.push_back( mat.first );
continue;
}
}
else
{
for( const MODEL_3D::MATERIAL& mat : m_materials )
{
// There is at least one default material created in case a mesh has no declared materials.
// Most meshes have a material, so usually the first material will have nothing to render and is skip.
// See S3D::GetModel for more details.
if( mat.m_render_idx_count == 0 )
{
continue;
}
if( ( mat.IsTransparent() != aTransparent )
&& ( aOpacity >= 1.0f )
&& m_materialMode != MATERIAL_MODE::DIFFUSE_ONLY )
{
continue;
}
materialsToRender.push_back( &mat );
}
}
for( const MODEL_3D::MATERIAL* mat : materialsToRender )
{
switch( m_materialMode )
{
case MATERIAL_MODE::NORMAL:
OglSetMaterial( *mat, aOpacity, aUseSelectedMaterial, aSelectionColor );
OglSetMaterial( mat, aOpacity, aUseSelectedMaterial, aSelectionColor );
break;
case MATERIAL_MODE::DIFFUSE_ONLY:
OglSetDiffuseMaterial( mat->m_Diffuse, aOpacity, aUseSelectedMaterial, aSelectionColor );
OglSetDiffuseMaterial( mat.m_Diffuse, aOpacity, aUseSelectedMaterial, aSelectionColor );
break;
case MATERIAL_MODE::CAD_MODE:
OglSetDiffuseMaterial( MaterialDiffuseToColorCAD( mat->m_Diffuse ), aOpacity,
OglSetDiffuseMaterial( MaterialDiffuseToColorCAD( mat.m_Diffuse ), aOpacity,
aUseSelectedMaterial, aSelectionColor );
break;
@@ -550,9 +467,9 @@ void MODEL_3D::Draw( bool aTransparent, float aOpacity, bool aUseSelectedMateria
break;
}
glDrawElements( GL_TRIANGLES, mat->m_render_idx_count, m_index_buffer_type,
glDrawElements( GL_TRIANGLES, mat.m_render_idx_count, m_index_buffer_type,
reinterpret_cast<const void*>(
static_cast<uintptr_t>( mat->m_render_idx_buffer_offset ) ) );
static_cast<uintptr_t>( mat.m_render_idx_buffer_offset ) ) );
}
}
+5 -14
View File
@@ -54,7 +54,7 @@ public:
*/
void DrawOpaque( bool aUseSelectedMaterial, SFVEC3F aSelectionColor = SFVEC3F( 0.0f ) ) const
{
Draw( false, 1.0f, aUseSelectedMaterial, aSelectionColor, nullptr, nullptr );
Draw( false, 1.0f, aUseSelectedMaterial, aSelectionColor );
}
/**
@@ -63,19 +63,9 @@ public:
void DrawTransparent( float aOpacity, bool aUseSelectedMaterial,
SFVEC3F aSelectionColor = SFVEC3F( 0.0f ) ) const
{
Draw( true, aOpacity, aUseSelectedMaterial, aSelectionColor, nullptr, nullptr );
Draw( true, aOpacity, aUseSelectedMaterial, aSelectionColor );
}
/**
* Render the model into the current context.
* if aModelWorldMatrix and aCameraWorldPos is provided,
* it renders the material groups sorted.
*/
void Draw( bool aTransparent, float aOpacity, bool aUseSelectedMaterial,
const SFVEC3F& aSelectionColor,
const glm::mat4 *aModelWorldMatrix,
const SFVEC3F *aCameraWorldPos ) const;
/**
* Return true if have opaque meshes to render.
*/
@@ -146,8 +136,6 @@ private:
unsigned int m_render_idx_buffer_offset = 0;
unsigned int m_render_idx_count = 0;
BBOX_3D m_bbox; ///< bounding box for this material group, used for transparent material ordering
MATERIAL( const SMATERIAL& aOther ) : SMATERIAL( aOther ) { }
bool IsTransparent() const { return m_Transparency > FLT_EPSILON; }
};
@@ -171,6 +159,9 @@ private:
static void MakeBbox( const BBOX_3D& aBox, unsigned int aIdxOffset, VERTEX* aVtxOut,
GLuint* aIdxOut, const glm::vec4& aColor );
void Draw( bool aTransparent, float aOpacity, bool aUseSelectedMaterial,
SFVEC3F& aSelectionColor ) const;
};
#endif // _MODEL_3D_H_
@@ -912,8 +912,7 @@ void RENDER_3D_OPENGL::load3dModels( REPORTER* aStatusReporter )
if( !m_boardAdapter.GetBoard() )
return;
if( !m_boardAdapter.m_IsPreviewer
&& !m_boardAdapter.m_Cfg->m_Render.show_footprints_normal
if( !m_boardAdapter.m_Cfg->m_Render.show_footprints_normal
&& !m_boardAdapter.m_Cfg->m_Render.show_footprints_insert
&& !m_boardAdapter.m_Cfg->m_Render.show_footprints_virtual )
{
@@ -22,19 +22,14 @@
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include <cstdint>
#include <gal/opengl/kiglew.h> // Must be included first
#include "plugins/3dapi/xv3d_types.h"
#include "render_3d_opengl.h"
#include "opengl_utils.h"
#include "common_ogl/ogl_utils.h"
#include <footprint.h>
#include <3d_math.h>
#include <glm/geometric.hpp>
#include <math/util.h> // for KiROUND
#include <utility>
#include <vector>
#include <wx/log.h>
#include <base_units.h>
@@ -863,12 +858,9 @@ bool RENDER_3D_OPENGL::Redraw( bool aIsMoving, REPORTER* aStatusReporter,
glPopMatrix();
}
glm::mat4 cameraViewMatrix;
glGetFloatv( GL_MODELVIEW_MATRIX, glm::value_ptr( cameraViewMatrix ) );
// Render 3D Models (Non-transparent)
renderOpaqueModels( cameraViewMatrix );
render3dModels( false, false );
render3dModels( true, false );
// Display board body
if( m_boardAdapter.m_Cfg->m_Render.show_board_body )
@@ -930,7 +922,8 @@ bool RENDER_3D_OPENGL::Redraw( bool aIsMoving, REPORTER* aStatusReporter,
glTexEnvi( GL_TEXTURE_ENV, GL_SRC1_ALPHA, GL_CONSTANT );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_ALPHA, GL_SRC_ALPHA );
renderTransparentModels( cameraViewMatrix );
render3dModels( false, true );
render3dModels( true, true );
glDisable( GL_BLEND );
OglResetTextureState();
@@ -1150,15 +1143,14 @@ void RENDER_3D_OPENGL::renderSolderMaskLayer( PCB_LAYER_ID aLayerID, float aZPos
}
void RENDER_3D_OPENGL::get3dModelsSelected( std::list<MODELTORENDER> &aDstRenderList,
bool aGetTop, bool aGetBot, bool aRenderTransparentOnly,
bool aRenderSelectedOnly )
void RENDER_3D_OPENGL::render3dModelsSelected( bool aRenderTopOrBot, bool aRenderTransparentOnly,
bool aRenderSelectedOnly )
{
wxASSERT( ( aGetTop == true ) || ( aGetBot == true ) );
if( !m_boardAdapter.GetBoard() )
return;
MODEL_3D::BeginDrawMulti( !aRenderSelectedOnly );
// Go for all footprints
for( FOOTPRINT* fp : m_boardAdapter.GetBoard()->Footprints() )
{
@@ -1183,52 +1175,54 @@ void RENDER_3D_OPENGL::get3dModelsSelected( std::list<MODELTORENDER> &aDstRender
{
if( m_boardAdapter.IsFootprintShown( (FOOTPRINT_ATTR_T) fp->GetAttributes() ) )
{
const bool isFlipped = fp->IsFlipped();
if( ( aGetTop == !isFlipped ) ||
( aGetBot == isFlipped ) )
get3dModelsFromFootprint( aDstRenderList, fp, aRenderTransparentOnly, highlight );
if( aRenderTopOrBot == !fp->IsFlipped() )
renderFootprint( fp, aRenderTransparentOnly, highlight );
}
}
}
MODEL_3D::EndDrawMulti();
}
void RENDER_3D_OPENGL::get3dModelsFromFootprint( std::list<MODELTORENDER> &aDstRenderList,
const FOOTPRINT* aFootprint, bool aRenderTransparentOnly,
bool aIsSelected )
void RENDER_3D_OPENGL::render3dModels( bool aRenderTopOrBot, bool aRenderTransparentOnly )
{
if( m_boardAdapter.m_IsBoardView )
render3dModelsSelected( aRenderTopOrBot, aRenderTransparentOnly, true );
render3dModelsSelected( aRenderTopOrBot, aRenderTransparentOnly, false );
}
void RENDER_3D_OPENGL::renderFootprint( const FOOTPRINT* aFootprint, bool aRenderTransparentOnly,
bool aIsSelected )
{
if( !aFootprint->Models().empty() )
{
const double zpos = m_boardAdapter.GetFootprintZPos( aFootprint->IsFlipped() );
SFVEC3F selColor = m_boardAdapter.GetColor( m_boardAdapter.m_Cfg->m_Render.opengl_selection_color );
glPushMatrix();
VECTOR2I pos = aFootprint->GetPosition();
glm::mat4 fpMatrix( 1.0f );
fpMatrix = glm::translate( fpMatrix,
SFVEC3F( pos.x * m_boardAdapter.BiuTo3dUnits(),
-pos.y * m_boardAdapter.BiuTo3dUnits(),
zpos ) );
glTranslatef( pos.x * m_boardAdapter.BiuTo3dUnits(), -pos.y * m_boardAdapter.BiuTo3dUnits(),
zpos );
if( !aFootprint->GetOrientation().IsZero() )
{
fpMatrix = glm::rotate( fpMatrix,
(float) aFootprint->GetOrientation().AsRadians(),
SFVEC3F( 0.0f, 0.0f, 1.0f ) );
}
glRotated( aFootprint->GetOrientation().AsDegrees(), 0.0, 0.0, 1.0 );
if( aFootprint->IsFlipped() )
{
fpMatrix = glm::rotate( fpMatrix, glm::pi<float>(), SFVEC3F( 0.0f, 1.0f, 0.0f ) );
fpMatrix = glm::rotate( fpMatrix, glm::pi<float>(), SFVEC3F( 0.0f, 0.0f, 1.0f ) );
glRotatef( 180.0f, 0.0f, 1.0f, 0.0f );
glRotatef( 180.0f, 0.0f, 0.0f, 1.0f );
}
const double modelunit_to_3d_units_factor = m_boardAdapter.BiuTo3dUnits() *
UNITS3D_TO_UNITSPCB;
double modelunit_to_3d_units_factor = m_boardAdapter.BiuTo3dUnits() * UNITS3D_TO_UNITSPCB;
fpMatrix = glm::scale( fpMatrix,
SFVEC3F( modelunit_to_3d_units_factor ) );
glScaled( modelunit_to_3d_units_factor, modelunit_to_3d_units_factor,
modelunit_to_3d_units_factor );
// Get the list of model files for this model
for( const FP_3DMODEL& sM : aFootprint->Models() )
@@ -1249,232 +1243,66 @@ void RENDER_3D_OPENGL::get3dModelsFromFootprint( std::list<MODELTORENDER> &aDstR
if( ( !aRenderTransparentOnly && modelPtr->HasOpaqueMeshes() && opaque ) ||
( aRenderTransparentOnly && ( modelPtr->HasTransparentMeshes() || !opaque ) ) )
{
glm::mat4 modelworldMatrix = fpMatrix;
glPushMatrix();
const SFVEC3F offset = SFVEC3F( sM.m_Offset.x, sM.m_Offset.y, sM.m_Offset.z );
const SFVEC3F rotation = SFVEC3F( sM.m_Rotation.x, sM.m_Rotation.y, sM.m_Rotation.z );
const SFVEC3F scale = SFVEC3F( sM.m_Scale.x, sM.m_Scale.y, sM.m_Scale.z );
std::vector<float> key = { offset.x, offset.y, offset.z,
rotation.x, rotation.y, rotation.z,
scale.x, scale.y, scale.z };
std::vector<double> key = { sM.m_Offset.x, sM.m_Offset.y, sM.m_Offset.z,
sM.m_Rotation.x, sM.m_Rotation.y, sM.m_Rotation.z,
sM.m_Scale.x, sM.m_Scale.y, sM.m_Scale.z };
auto it = m_3dModelMatrixMap.find( key );
if( it != m_3dModelMatrixMap.end() )
{
modelworldMatrix *= it->second;
glMultMatrixf( glm::value_ptr( it->second ) );
}
else
{
glm::mat4 mtx( 1.0f );
mtx = glm::translate( mtx, offset );
mtx = glm::rotate( mtx, glm::radians( -rotation.z ), { 0.0f, 0.0f, 1.0f } );
mtx = glm::rotate( mtx, glm::radians( -rotation.y ), { 0.0f, 1.0f, 0.0f } );
mtx = glm::rotate( mtx, glm::radians( -rotation.x ), { 1.0f, 0.0f, 0.0f } );
mtx = glm::scale( mtx, scale );
glm::mat4 mtx( 1 );
mtx = glm::translate( mtx, { sM.m_Offset.x, sM.m_Offset.y, sM.m_Offset.z } );
mtx = glm::rotate( mtx, glm::radians( (float) -sM.m_Rotation.z ), { 0.0f, 0.0f, 1.0f } );
mtx = glm::rotate( mtx, glm::radians( (float) -sM.m_Rotation.y ), { 0.0f, 1.0f, 0.0f } );
mtx = glm::rotate( mtx, glm::radians( (float) -sM.m_Rotation.x ), { 1.0f, 0.0f, 0.0f } );
mtx = glm::scale( mtx, { sM.m_Scale.x, sM.m_Scale.y, sM.m_Scale.z } );
m_3dModelMatrixMap[ key ] = mtx;
modelworldMatrix *= mtx;
glMultMatrixf( glm::value_ptr( mtx ) );
}
if( aRenderTransparentOnly )
{
aDstRenderList.emplace_back( modelworldMatrix,
modelPtr,
sM.m_Opacity,
true,
aFootprint->IsSelected() || aIsSelected );
modelPtr->DrawTransparent( sM.m_Opacity,
aFootprint->IsSelected() || aIsSelected,
selColor );
}
else
{
aDstRenderList.emplace_back( modelworldMatrix,
modelPtr,
1.0f,
false,
aFootprint->IsSelected() || aIsSelected );
modelPtr->DrawOpaque( aFootprint->IsSelected() || aIsSelected, selColor );
}
}
}
}
}
}
if( m_boardAdapter.m_Cfg->m_Render.opengl_show_model_bbox )
{
glEnable( GL_BLEND );
glBlendFunc( GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA );
void RENDER_3D_OPENGL::renderOpaqueModels( const glm::mat4 &aCameraViewMatrix )
{
const SFVEC3F selColor = m_boardAdapter.GetColor( m_boardAdapter.m_Cfg->m_Render.opengl_selection_color );
glDisable( GL_LIGHTING );
glPushMatrix();
glLineWidth( 1 );
modelPtr->DrawBboxes();
std::list<MODELTORENDER> renderList;
glLineWidth( 4 );
modelPtr->DrawBbox();
if( m_boardAdapter.m_IsBoardView )
{
renderList.clear();
glEnable( GL_LIGHTING );
glDisable( GL_BLEND );
}
get3dModelsSelected( renderList, true, true, false, true );
if( !renderList.empty() )
{
MODEL_3D::BeginDrawMulti( false );
for( const MODELTORENDER& mtr : renderList )
{
renderModel( aCameraViewMatrix, mtr, selColor, nullptr );
}
MODEL_3D::EndDrawMulti();
}
}
renderList.clear();
get3dModelsSelected( renderList, true, true, false, false );
if( !renderList.empty() )
{
MODEL_3D::BeginDrawMulti( true );
for( const MODELTORENDER& mtr : renderList )
{
renderModel( aCameraViewMatrix, mtr, selColor, nullptr );
}
MODEL_3D::EndDrawMulti();
}
glPopMatrix();
}
void RENDER_3D_OPENGL::renderTransparentModels( const glm::mat4 &aCameraViewMatrix )
{
const SFVEC3F selColor = m_boardAdapter.GetColor( m_boardAdapter.m_Cfg->m_Render.opengl_selection_color );
std::list<MODELTORENDER> renderListModels; // do not clear it until this function returns
if( m_boardAdapter.m_IsBoardView )
{
// Get Transparent Selected
get3dModelsSelected( renderListModels, true, true, true, true );
}
// Get Transparent Not Selected
get3dModelsSelected( renderListModels, true, true, true, false );
if( renderListModels.empty() )
return;
std::vector<std::pair<const MODELTORENDER *, float>> transparentModelList;
transparentModelList.reserve( renderListModels.size() );
// Calculate the distance to the camera for each model
const SFVEC3F &cameraPos = m_camera.GetPos();
for( const MODELTORENDER& mtr : renderListModels )
{
const BBOX_3D& bBox = mtr.m_model->GetBBox();
const SFVEC3F& bBoxCenter = bBox.GetCenter();
const SFVEC3F bBoxWorld = mtr.m_modelWorldMat * glm::vec4( bBoxCenter, 1.0f );
const float distanceToCamera = glm::length( cameraPos - bBoxWorld );
transparentModelList.emplace_back( &mtr, distanceToCamera );
}
// Sort from back to front
std::sort( transparentModelList.begin(), transparentModelList.end(),
[&]( std::pair<const MODELTORENDER *, float>& a,
std::pair<const MODELTORENDER *, float>& b ) {
return a.second > b.second;
} );
// Start rendering calls
glPushMatrix();
bool isUsingColorInformation = !( transparentModelList.begin()->first->m_isSelected &&
m_boardAdapter.m_IsBoardView );
MODEL_3D::BeginDrawMulti( isUsingColorInformation );
for( const std::pair<const MODELTORENDER *, float>& mtr : transparentModelList )
{
if( m_boardAdapter.m_IsBoardView )
{
// Toggle between using model color or the select color
if( !isUsingColorInformation && !mtr.first->m_isSelected )
{
isUsingColorInformation = true;
glEnableClientState( GL_COLOR_ARRAY );
glEnableClientState( GL_TEXTURE_COORD_ARRAY );
glEnable( GL_COLOR_MATERIAL );
}
else
{
if( isUsingColorInformation && mtr.first->m_isSelected )
{
isUsingColorInformation = false;
glDisableClientState( GL_COLOR_ARRAY );
glDisableClientState( GL_TEXTURE_COORD_ARRAY );
glDisable( GL_COLOR_MATERIAL );
glPopMatrix();
}
}
}
// Render model, sort each individuall material group
// by passing cameraPos
renderModel( aCameraViewMatrix, *mtr.first, selColor, &cameraPos );
}
MODEL_3D::EndDrawMulti();
glPopMatrix();
}
void RENDER_3D_OPENGL::renderModel( const glm::mat4 &aCameraViewMatrix,
const MODELTORENDER &aModelToRender,
const SFVEC3F &aSelColor,
const SFVEC3F *aCameraWorldPos )
{
const glm::mat4 modelviewMatrix = aCameraViewMatrix * aModelToRender.m_modelWorldMat;
glLoadMatrixf( glm::value_ptr( modelviewMatrix ) );
aModelToRender.m_model->Draw( aModelToRender.m_isTransparent,
aModelToRender.m_opacity,
aModelToRender.m_isSelected,
aSelColor,
&aModelToRender.m_modelWorldMat,
aCameraWorldPos );
if( m_boardAdapter.m_Cfg->m_Render.opengl_show_model_bbox )
{
const bool wasBlendEnabled = glIsEnabled( GL_BLEND );
if( !wasBlendEnabled )
{
glEnable( GL_BLEND );
glBlendFunc( GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA );
}
glDisable( GL_LIGHTING );
glLineWidth( 1 );
aModelToRender.m_model->DrawBboxes();
glLineWidth( 4 );
aModelToRender.m_model->DrawBbox();
glEnable( GL_LIGHTING );
if( !wasBlendEnabled )
{
glDisable( GL_BLEND );
}
glPopMatrix();
}
}
@@ -129,44 +129,18 @@ private:
*/
void load3dModels( REPORTER* aStatusReporter );
struct MODELTORENDER
{
glm::mat4 m_modelWorldMat;
const MODEL_3D* m_model;
float m_opacity;
bool m_isTransparent;
bool m_isSelected;
/**
* @param aRenderTopOrBot true will render Top, false will render bottom
* @param aRenderTransparentOnly true will render only the transparent objects, false will
* render opaque
*/
void render3dModels( bool aRenderTopOrBot, bool aRenderTransparentOnly );
MODELTORENDER( glm::mat4 aModelWorldMat,
const MODEL_3D* aNodel,
float aOpacity,
bool aIsTransparent,
bool aIsSelected ) :
m_modelWorldMat( std::move( aModelWorldMat ) ),
m_model( aNodel ),
m_opacity( aOpacity ),
m_isTransparent( aIsTransparent ),
m_isSelected( aIsSelected )
{
}
};
void render3dModelsSelected( bool aRenderTopOrBot, bool aRenderTransparentOnly,
bool aRenderSelectedOnly );
void renderOpaqueModels( const glm::mat4 &aCameraViewMatrix );
void renderTransparentModels( const glm::mat4 &aCameraViewMatrix );
void renderModel( const glm::mat4 &aCameraViewMatrix,
const MODELTORENDER &aModelToRender,
const SFVEC3F &aSelColor,
const SFVEC3F *aCameraWorldPos );
void get3dModelsSelected( std::list<MODELTORENDER> &aDstRenderList,
bool aGetTop, bool aGetBot, bool aRenderTransparentOnly,
bool aRenderSelectedOnly );
void get3dModelsFromFootprint( std::list<MODELTORENDER> &aDstRenderList,
const FOOTPRINT* aFootprint, bool aRenderTransparentOnly,
bool aIsSelected );
void renderFootprint( const FOOTPRINT* aFootprint, bool aRenderTransparentOnly,
bool aIsSelected );
void setLightFront( bool enabled );
void setLightTop( bool enabled );
@@ -236,7 +210,7 @@ private:
// Caches
std::map< wxString, MODEL_3D* > m_3dModelMap;
std::map< std::vector<float>, glm::mat4 > m_3dModelMatrixMap;
std::map< std::vector<double>, glm::mat4 > m_3dModelMatrixMap;
BOARD_ITEM* m_currentRollOverItem;
@@ -1202,8 +1202,7 @@ void RENDER_3D_RAYTRACE::load3DModels( CONTAINER_3D& aDstContainer, bool aSkipMa
if( !m_boardAdapter.GetBoard() )
return;
if( !m_boardAdapter.m_IsPreviewer
&& !m_boardAdapter.m_Cfg->m_Render.show_footprints_normal
if( !m_boardAdapter.m_Cfg->m_Render.show_footprints_normal
&& !m_boardAdapter.m_Cfg->m_Render.show_footprints_insert
&& !m_boardAdapter.m_Cfg->m_Render.show_footprints_virtual )
{
@@ -229,16 +229,6 @@ bool BBOX_2D::Inside( const SFVEC2F& aPoint ) const
}
bool BBOX_2D::Inside( const BBOX_2D& aBBox ) const
{
wxASSERT( IsInitialized() );
wxASSERT( aBBox.IsInitialized() );
return Inside( aBBox.Min() ) &&
Inside( aBBox.Max() );
}
float BBOX_2D::Area() const
{
SFVEC2F extent = GetExtent();
@@ -132,14 +132,6 @@ public:
*/
bool Inside( const SFVEC2F& aPoint ) const;
/**
* Check if a bounding box is inside this bounding box.
*
* @param aBBox the bounding box to test if it is inside
* @return true if aBBox is smaller and all points are inside
*/
bool Inside( const BBOX_2D& aBBox ) const;
/**
* Calculate the area of a bounding box.
*
@@ -238,16 +238,6 @@ bool BBOX_3D::Inside( const SFVEC3F& aPoint ) const
}
bool BBOX_3D::Inside( const BBOX_3D& aBBox ) const
{
wxASSERT( IsInitialized() );
wxASSERT( aBBox.IsInitialized() );
return Inside( aBBox.Min() ) &&
Inside( aBBox.Max() );
}
float BBOX_3D::Volume() const
{
wxASSERT( IsInitialized() );
@@ -125,14 +125,6 @@ public:
*/
bool Inside( const SFVEC3F& aPoint ) const;
/**
* Check if a bounding box is inside this bounding box.
*
* @param aBBox the bounding box to test if it is inside
* @return true if aBBox is smaller and all points are inside
*/
bool Inside( const BBOX_3D& aBBox ) const;
/**
* Apply a transformation matrix to the box points.
*
@@ -70,8 +70,6 @@ PANEL_PREVIEW_3D_MODEL::PANEL_PREVIEW_3D_MODEL( wxWindow* aParent, PCB_BASE_FRAM
m_selected = -1;
m_previewLabel->SetFont( KIUI::GetStatusFont( this ) );
// Set the bitmap of 3D view buttons:
m_bpvTop->SetBitmap( KiBitmap( BITMAPS::axis3d_top ) );
m_bpvFront->SetBitmap( KiBitmap( BITMAPS::axis3d_front ) );
@@ -142,9 +140,6 @@ PANEL_PREVIEW_3D_MODEL::PANEL_PREVIEW_3D_MODEL( wxWindow* aParent, PCB_BASE_FRAM
this );
}
aFrame->Connect( UNITS_CHANGED, wxCommandEventHandler( PANEL_PREVIEW_3D_MODEL::onUnitsChanged ),
nullptr, this );
#ifdef __WXOSX__
// Call layout once to get the proper button sizes after the bitmaps have been set
Layout();
@@ -543,29 +538,6 @@ void PANEL_PREVIEW_3D_MODEL::onMouseWheelOffset( wxMouseEvent& event )
}
void PANEL_PREVIEW_3D_MODEL::onUnitsChanged( wxCommandEvent& aEvent )
{
double xoff_mm = EDA_UNIT_UTILS::UI::DoubleValueFromString( pcbIUScale, m_userUnits,
xoff->GetValue() )
/ pcbIUScale.IU_PER_MM;
double yoff_mm = EDA_UNIT_UTILS::UI::DoubleValueFromString( pcbIUScale, m_userUnits,
yoff->GetValue() )
/ pcbIUScale.IU_PER_MM;
double zoff_mm = EDA_UNIT_UTILS::UI::DoubleValueFromString( pcbIUScale, m_userUnits,
zoff->GetValue() )
/ pcbIUScale.IU_PER_MM;
PCB_BASE_FRAME* frame = static_cast<PCB_BASE_FRAME*>( aEvent.GetClientData() );
m_userUnits = frame->GetUserUnits();
xoff->SetValue( formatOffsetValue( xoff_mm ) );
yoff->SetValue( formatOffsetValue( yoff_mm ) );
zoff->SetValue( formatOffsetValue( zoff_mm ) );
aEvent.Skip();
}
void PANEL_PREVIEW_3D_MODEL::UpdateDummyFootprint( bool aReloadRequired )
{
m_dummyFootprint->Models().clear();
@@ -141,8 +141,6 @@ private:
void doIncrementRotation( wxSpinEvent& aEvent, double aSign );
void doIncrementOffset( wxSpinEvent& aEvent, double aSign );
void onUnitsChanged( wxCommandEvent& aEvent );
wxString formatScaleValue( double aValue );
wxString formatRotationValue( double aValue );
wxString formatOffsetValue( double aValue );
@@ -183,11 +183,12 @@ PANEL_PREVIEW_3D_MODEL_BASE::PANEL_PREVIEW_3D_MODEL_BASE( wxWindow* parent, wxWi
wxBoxSizer* bSizer6;
bSizer6 = new wxBoxSizer( wxHORIZONTAL );
m_previewLabel = new wxStaticText( this, wxID_ANY, _("Preview"), wxDefaultPosition, wxDefaultSize, 0 );
m_previewLabel->Wrap( -1 );
m_previewLabel->SetFont( wxFont( 11, wxFONTFAMILY_DEFAULT, wxFONTSTYLE_NORMAL, wxFONTWEIGHT_NORMAL, false, wxEmptyString ) );
wxStaticText* staticPreviewLabel;
staticPreviewLabel = new wxStaticText( this, wxID_ANY, _("Preview"), wxDefaultPosition, wxDefaultSize, 0 );
staticPreviewLabel->Wrap( -1 );
staticPreviewLabel->SetFont( wxFont( 11, wxFONTFAMILY_DEFAULT, wxFONTSTYLE_NORMAL, wxFONTWEIGHT_NORMAL, false, wxEmptyString ) );
bSizer6->Add( m_previewLabel, 1, wxEXPAND|wxLEFT|wxRIGHT, 10 );
bSizer6->Add( staticPreviewLabel, 0, wxEXPAND|wxLEFT|wxRIGHT, 10 );
bSizerRight->Add( bSizer6, 0, wxEXPAND, 5 );
@@ -206,7 +207,7 @@ PANEL_PREVIEW_3D_MODEL_BASE::PANEL_PREVIEW_3D_MODEL_BASE( wxWindow* parent, wxWi
m_bpvISO = new wxBitmapButton( this, wxID_ANY, wxNullBitmap, wxDefaultPosition, wxSize( -1,-1 ), wxBU_AUTODRAW|0 );
m_bpvISO->SetToolTip( _("Enable/disable orthographic projection") );
bSizer3DButtons->Add( m_bpvISO, 0, wxTOP, 14 );
bSizer3DButtons->Add( m_bpvISO, 0, wxTOP|wxBOTTOM, 5 );
bSizer3DButtons->Add( 0, 0, 1, wxEXPAND, 5 );
@@ -2089,7 +2089,7 @@
<object class="sizeritem" expanded="1">
<property name="border">10</property>
<property name="flag">wxEXPAND|wxLEFT|wxRIGHT</property>
<property name="proportion">1</property>
<property name="proportion">0</property>
<object class="wxStaticText" expanded="1">
<property name="BottomDockable">1</property>
<property name="LeftDockable">1</property>
@@ -2127,11 +2127,11 @@
<property name="minimize_button">0</property>
<property name="minimum_size"></property>
<property name="moveable">1</property>
<property name="name">m_previewLabel</property>
<property name="name">staticPreviewLabel</property>
<property name="pane_border">1</property>
<property name="pane_position"></property>
<property name="pane_size"></property>
<property name="permission">protected</property>
<property name="permission">none</property>
<property name="pin_button">1</property>
<property name="pos"></property>
<property name="resize">Resizable</property>
@@ -2172,8 +2172,8 @@
<property name="orient">wxVERTICAL</property>
<property name="permission">none</property>
<object class="sizeritem" expanded="1">
<property name="border">14</property>
<property name="flag">wxTOP</property>
<property name="border">5</property>
<property name="flag">wxTOP|wxBOTTOM</property>
<property name="proportion">0</property>
<object class="wxBitmapButton" expanded="1">
<property name="BottomDockable">1</property>
@@ -68,7 +68,6 @@ class PANEL_PREVIEW_3D_MODEL_BASE : public wxPanel
wxSlider* m_opacity;
wxTextCtrl* m_boardThicknessCtrl;
wxStaticText* m_boardThicknessUnits;
wxStaticText* m_previewLabel;
wxBoxSizer* m_SizerPanelView;
wxBitmapButton* m_bpvISO;
wxBitmapButton* m_bpvLeft;
+2 -6
View File
@@ -350,16 +350,12 @@ endif(USE_DISTCC)
# Set flags for GCC, or treat llvm as GCC
#================================================
if( CMAKE_COMPILER_IS_GNUCXX )
if( CMAKE_COMPILER_IS_GNUCXX OR CMAKE_CXX_COMPILER_ID MATCHES "Clang" )
# Set 32-bit flag for GCC to prevent excess precision
# clang des not know this flag, so keep this separate
if( CMAKE_SIZEOF_VOID_P EQUAL 4 )
set( CMAKE_CXX_FLAGS "-ffloat-store ${CMAKE_CXX_FLAGS}" )
endif()
endif( CMAKE_COMPILER_IS_GNUCXX )
if( CMAKE_COMPILER_IS_GNUCXX OR CMAKE_CXX_COMPILER_ID MATCHES "Clang" )
# Link flags in Debug: -g1 and -ggdb1 or -g1 and -ggdb3 can be used.
# Level 1 produces minimal information, enough for making basic backtraces.
+1 -1
View File
@@ -66,7 +66,7 @@ macro( create_git_version_header _git_src_path )
# Check to make sure 'git' command did not fail. Otherwise fallback
# to KiCadVersion.cmake as the revision level.
if( _git_describe_result EQUAL 0 )
set( KICAD_VERSION "${_git_DESCRIBE}" )
set( KICAD_VERSION "(${_git_DESCRIBE})" )
endif()
if( _git_rev_parse_head_result EQUAL 0 )
+2 -11
View File
@@ -926,17 +926,8 @@ if(wxWidgets_FOUND)
"\\2" wxWidgets_VERSION_MINOR "${_wx_version_h}" )
string(REGEX REPLACE "^(.*\n)?#define +wxRELEASE_NUMBER +([0-9]+).*"
"\\2" wxWidgets_VERSION_PATCH "${_wx_version_h}" )
string(REGEX REPLACE "^(.*\n)?#define +wxSUBRELEASE_NUMBER +([0-9]+).*"
"\\2" wxWidgets_VERSION_SUBRELEASE "${_wx_version_h}" )
if( ${wxWidgets_VERSION_SUBRELEASE} GREATER 0 )
set(wxWidgets_VERSION_STRING
"${wxWidgets_VERSION_MAJOR}.${wxWidgets_VERSION_MINOR}.${wxWidgets_VERSION_PATCH}.${wxWidgets_VERSION_SUBRELEASE}" )
else()
set(wxWidgets_VERSION_STRING
"${wxWidgets_VERSION_MAJOR}.${wxWidgets_VERSION_MINOR}.${wxWidgets_VERSION_PATCH}" )
endif()
set(wxWidgets_VERSION_STRING
"${wxWidgets_VERSION_MAJOR}.${wxWidgets_VERSION_MINOR}.${wxWidgets_VERSION_PATCH}" )
DBG_MSG("wxWidgets_VERSION_STRING: ${wxWidgets_VERSION_STRING}")
endif()
+1 -1
View File
@@ -37,7 +37,7 @@
# KiCad.
#
# Note: This version string should follow the semantic versioning system
set( KICAD_SEMANTIC_VERSION "7.0.2" )
set( KICAD_SEMANTIC_VERSION "7.99.0-unknown" )
# Default the version to the semantic version.
# This is overridden by the git repository tag though (if using git)
-1
View File
@@ -45,7 +45,6 @@
#include <eda_base_frame.h>
#include <eda_draw_frame.h>
#include <paths.h>
#include <kiplatform/ui.h>
static std::unique_ptr<BITMAP_STORE> s_BitmapStore;
+11 -18
View File
@@ -75,7 +75,6 @@ void BITMAP_BASE::SetImage( wxImage* aImage )
delete m_originalImage;
m_originalImage = new wxImage( *aImage );
rebuildBitmap();
updatePPI();
}
@@ -91,21 +90,6 @@ void BITMAP_BASE::rebuildBitmap( bool aResetID )
}
void BITMAP_BASE::updatePPI()
{
// Todo: eventually we need to support dpi / scaling in both dimensions
int dpiX = m_originalImage->GetOptionInt( wxIMAGE_OPTION_RESOLUTIONX );
if( dpiX > 1 )
{
if( m_originalImage->GetOptionInt( wxIMAGE_OPTION_RESOLUTIONUNIT ) == wxIMAGE_RESOLUTION_CM )
m_ppi = KiROUND( dpiX * 2.54 );
else
m_ppi = dpiX;
}
}
void BITMAP_BASE::ImportData( BITMAP_BASE* aItem )
{
*m_image = *aItem->m_image;
@@ -132,7 +116,6 @@ bool BITMAP_BASE::ReadImageFile( wxInputStream& aInStream )
delete m_originalImage;
m_originalImage = new wxImage( *m_image );
rebuildBitmap();
updatePPI();
return true;
}
@@ -153,7 +136,17 @@ bool BITMAP_BASE::ReadImageFile( const wxString& aFullFilename )
delete m_originalImage;
m_originalImage = new wxImage( *m_image );
rebuildBitmap();
updatePPI();
// Todo: eventually we need to support dpi / scaling in both dimensions
int dpiX = m_originalImage->GetOptionInt( wxIMAGE_OPTION_RESOLUTIONX );
if( dpiX > 1 )
{
if( m_originalImage->GetOptionInt( wxIMAGE_OPTION_RESOLUTIONUNIT ) == wxIMAGE_RESOLUTION_CM )
m_ppi = KiROUND( dpiX * 2.54 );
else
m_ppi = dpiX;
}
return true;
}
+5 -13
View File
@@ -177,20 +177,12 @@ wxString GetVersionInfoData( const wxString& aTitle, bool aHtml, bool aBrief )
aMsg << eol;
wxString osDescription;
#if __LINUX__
osDescription = wxGetLinuxDistributionInfo().Description;
#endif
// Linux uses the lsb-release program to get the description of the OS, if lsb-release
// isn't installed, then the string will be empty and we fallback to the method used on
// the other platforms (to at least get the kernel/uname info).
if( osDescription.empty() )
osDescription = wxGetOsDescription();
aMsg << "Platform: "
<< osDescription << ", "
#if __LINUX__
<< wxGetLinuxDistributionInfo().Description << ", "
#else
<< wxGetOsDescription() << ", "
#endif
<< GetPlatformGetBitnessName() << ", "
<< platform.GetEndiannessName() << ", "
<< platform.GetPortIdName();
+21 -4
View File
@@ -31,13 +31,30 @@
#include <dialogs/html_message_box.h>
#include <functional>
#include <unordered_map>
#include <pgm_base.h>
#include "cli/cli_names.h"
// Set of dialogs that have been chosen not to be shown again
static std::unordered_map<unsigned long, int> doNotShowAgainDlgs;
bool IsGUI()
{
if( !wxTheApp )
return false;
#if wxCHECK_VERSION( 3, 1, 6 )
return wxTheApp->IsGUI();
#else
// wxWidgets older than version 3.1.6 do not have a way to know if the app
// has a GUI or is a console application.
// So the trick is to set the App class name when starting kicad-cli, and when
// the app class name is the kicad-cli class name the app is a console app
bool run_gui = wxTheApp->GetClassName() != KICAD_CLI_APP_NAME;
return run_gui;
#endif
}
KIDIALOG::KIDIALOG( wxWindow* aParent, const wxString& aMessage, const wxString& aCaption,
long aStyle )
: wxRichMessageDialog( aParent, aMessage, aCaption, aStyle | wxCENTRE | wxSTAY_ON_TOP ),
@@ -288,7 +305,7 @@ void DisplayError( wxWindow* aParent, const wxString& aText, int aDisplayTime )
return;
}
if( !Pgm().IsGUI() )
if( !IsGUI() )
{
wxFprintf( stderr, aText );
return;
@@ -313,7 +330,7 @@ void DisplayErrorMessage( wxWindow* aParent, const wxString& aText, const wxStri
return;
}
if( !Pgm().IsGUI() )
if( !IsGUI() )
{
wxFprintf( stderr, aText );
return;
@@ -340,7 +357,7 @@ void DisplayInfoMessage( wxWindow* aParent, const wxString& aMessage, const wxSt
return;
}
if( !Pgm().IsGUI() )
if( !IsGUI() )
{
wxFprintf( stdout, "%s %s", aMessage, aExtraInfo );
return;
+2 -10
View File
@@ -2,7 +2,7 @@
* This program source code file is part of KiCad, a free EDA CAD application.
*
* Copyright (C) 2022 Jon Evans <jon@craftyjon.com>
* Copyright (C) 2022-2023 KiCad Developers, see AUTHORS.txt for contributors.
* Copyright (C) 2022 KiCad Developers, see AUTHORS.txt for contributors.
*
* This program is free software: you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
@@ -178,15 +178,7 @@ bool DATABASE_CONNECTION::Disconnect()
return false;
}
try
{
m_conn->disconnect();
}
catch( boost::locale::conv::conversion_error& exc )
{
wxLogTrace( traceDatabase, wxT( "Disconnect() error \"%s\" occured." ), exc.what() );
return false;
}
m_conn->disconnect();
return !m_conn->connected();
}
+1 -53
View File
@@ -659,10 +659,6 @@ static void buildKicadAboutBanner( EDA_BASE_FRAME* aParent, ABOUT_APP_INFO& aInf
wxEmptyString,
wxEmptyString,
wxS( "Greek (el_GR)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxS( "aris-kimi" ),
wxEmptyString,
wxEmptyString,
wxS( "Greek (el_GR)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxT( "Adolfo Jayme Barrientos" ),
wxEmptyString,
@@ -692,10 +688,6 @@ static void buildKicadAboutBanner( EDA_BASE_FRAME* aParent, ABOUT_APP_INFO& aInf
wxEmptyString,
wxEmptyString,
wxS( "Spanish (ES)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxT( "VicSanRoPe" ),
wxEmptyString,
wxEmptyString,
wxS( "Spanish - Latin American (ES)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxT( "Ulices Avila Hernandez" ),
wxEmptyString,
@@ -830,46 +822,14 @@ static void buildKicadAboutBanner( EDA_BASE_FRAME* aParent, ABOUT_APP_INFO& aInf
wxEmptyString,
wxEmptyString,
wxS( "Korean (KO)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxT( "김낙환" ),
wxEmptyString,
wxEmptyString,
wxS( "Korean (KO)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxT( "이기형" ),
wxEmptyString,
wxEmptyString,
wxS( "Korean (KO)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxT( "남우근" ),
wxEmptyString,
wxEmptyString,
wxS( "Korean (KO)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxT( "강명구" ),
wxEmptyString,
wxEmptyString,
wxS( "Korean (KO)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxT( "김용재" ),
wxEmptyString,
wxEmptyString,
wxS( "Korean (KO)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxT( "서범기" ),
wxEmptyString,
wxEmptyString,
wxS( "Korean (KO)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxT( "김세영" ),
wxEmptyString,
wxEmptyString,
wxS( "Korean (KO)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxT( "이윤성" ),
wxEmptyString,
wxEmptyString,
wxS( "Korean (KO)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxT( "KwonHyeokbeom" ),
wxEmptyString,
wxEmptyString,
wxS( "Korean (KO)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxT( "Minsu Kim (0xGabriel)" ),
wxEmptyString,
wxEmptyString,
wxS( "Korean (KO)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxT( "Henrik Kauhanen" ),
wxEmptyString,
@@ -900,14 +860,6 @@ static void buildKicadAboutBanner( EDA_BASE_FRAME* aParent, ABOUT_APP_INFO& aInf
wxEmptyString,
wxEmptyString,
wxS( "Dutch (NL)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxT( "Tom Niesse" ),
wxEmptyString,
wxEmptyString,
wxS( "Dutch (NL)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxT( "Christiaan Nieuwlaat" ),
wxEmptyString,
wxEmptyString,
wxS( "Dutch (NL)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxT( "Jarl Gjessing" ),
wxEmptyString,
@@ -980,10 +932,6 @@ static void buildKicadAboutBanner( EDA_BASE_FRAME* aParent, ABOUT_APP_INFO& aInf
wxEmptyString,
wxEmptyString,
wxS( "Portuguese (PT)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxT( "ssantos" ),
wxEmptyString,
wxEmptyString,
wxS( "Portuguese (PT)" ) ) );
aInfo.AddTranslator( new CONTRIBUTOR( wxT( "Igor Plyatov" ),
wxEmptyString,
@@ -1181,7 +1129,7 @@ static void buildKicadAboutBanner( EDA_BASE_FRAME* aParent, ABOUT_APP_INFO& aInf
#define SYMBOL_LIB_CONTRIBUTION _( "Symbols by" )
aInfo.AddLibrarian( new CONTRIBUTOR( wxS( "GitLab contributors" ),
wxEmptyString,
wxS( "https://gitlab.com/kicad/libraries/kicad-symbols/-/graphs/master" ),
wxS( "https://gitlab.com/kicad/libraries/kicad-symbols/-/graphs/v7" ),
SYMBOL_LIB_CONTRIBUTION,
aInfo.CreateKiBitmap( BITMAPS::add_component ) ) );
+4 -4
View File
@@ -223,7 +223,7 @@ bool DIALOG_PAGES_SETTINGS::TransferDataFromWindow()
m_screen->SetContentModified();
if( LocalPrjConfigChanged() )
m_parent->OnModify();
m_parent->SaveProjectSettings();
// Call the post processing (if any) after changes
m_parent->OnPageSettingsChange();
@@ -674,9 +674,9 @@ void DIALOG_PAGES_SETTINGS::UpdateDrawingSheetExample()
GRFilledRect( &memDC, VECTOR2I( 0, 0 ), m_layout_size, 0, bgColor, bgColor );
PrintDrawingSheet( &renderSettings, pageDUMMY, emptyString, emptyString, emptyString,
m_tb, nullptr, m_screen->GetPageCount(), m_screen->GetPageNumber(),
1, &Prj(), wxEmptyString, m_screen->GetVirtualPageNumber() == 1 );
PrintDrawingSheet( &renderSettings, pageDUMMY, emptyString, emptyString, m_tb,
nullptr, m_screen->GetPageCount(), m_screen->GetPageNumber(), 1,
&Prj(), wxEmptyString, m_screen->GetVirtualPageNumber() == 1 );
memDC.SelectObject( wxNullBitmap );
m_PageLayoutExampleBitmap->SetBitmap( *m_pageBitmap );
+7 -19
View File
@@ -117,7 +117,8 @@ void PANEL_COLOR_SETTINGS::OnThemeChanged( wxCommandEvent& event )
if( idx == static_cast<int>( m_cbTheme->GetCount() ) - 2 )
{
m_cbTheme->SetStringSelection( GetSettingsDropdownName( m_currentSettings ) );
// separator; re-select active theme
m_cbTheme->SetStringSelection( m_currentSettings->GetName() );
return;
}
@@ -216,7 +217,10 @@ void PANEL_COLOR_SETTINGS::createThemeList( const wxString& aCurrent )
for( COLOR_SETTINGS* settings : Pgm().GetSettingsManager().GetColorSettingsList() )
{
wxString name = GetSettingsDropdownName( settings );
wxString name = settings->GetName();
if( settings->IsReadOnly() )
name += wxS( " " ) + _( "(read-only)" );
int pos = m_cbTheme->Append( name, static_cast<void*>( settings ) );
@@ -258,11 +262,8 @@ void PANEL_COLOR_SETTINGS::createSwatch( int aLayer, const wxString& aName )
defaultColor, SWATCH_MEDIUM );
swatch->SetForegroundColour( wxSystemSettings::GetColour( wxSYS_COLOUR_WINDOW ) );
// Display the swatches in the left column and the layer name in the right column
// The right column is sometimes (depending on the translation) truncated for long texts.
// We cannot allow swatches to be truncated or not shown
m_colorsGridSizer->Add( swatch, 0, wxALIGN_CENTER_VERTICAL | wxALL, 3 );
m_colorsGridSizer->Add( label, 0, wxALIGN_CENTER_VERTICAL | wxALIGN_LEFT | wxLEFT, 5 );
m_colorsGridSizer->Add( swatch, 0, wxALIGN_CENTER_VERTICAL | wxALL, 3 );
m_labels[aLayer] = label;
m_swatches[aLayer] = swatch;
@@ -282,8 +283,6 @@ void PANEL_COLOR_SETTINGS::ShowColorContextMenu( wxMouseEvent& aEvent, int aLaye
auto selected =
static_cast<COLOR_SETTINGS*>( m_cbTheme->GetClientData( m_cbTheme->GetSelection() ) );
wxCHECK_RET( selected, wxT( "Invalid color theme selected" ) );
COLOR4D current = m_currentSettings->GetColor( aLayer );
COLOR4D saved = selected->GetColor( aLayer );
bool readOnly = m_currentSettings->IsReadOnly();
@@ -377,14 +376,3 @@ bool PANEL_COLOR_SETTINGS::saveCurrentTheme( bool aValidate )
return true;
}
wxString PANEL_COLOR_SETTINGS::GetSettingsDropdownName(COLOR_SETTINGS* aSettings)
{
wxString name = aSettings->GetName();
if( aSettings->IsReadOnly() )
name += wxS( " " ) + _( "(read-only)" );
return name;
}
+6 -13
View File
@@ -2,7 +2,7 @@
* This program source code file is part of KICAD, a free EDA CAD application.
*
* Copyright (C) 2018 jean-pierre.charras
* Copyright (C) 2011-2023 Kicad Developers, see AUTHORS.txt for contributors.
* Copyright (C) 2011-2020 Kicad Developers, see AUTHORS.txt for contributors.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@@ -110,19 +110,12 @@ bool PANEL_IMAGE_EDITOR::TransferDataFromWindow()
void PANEL_IMAGE_EDITOR::OnRedrawPanel( wxPaintEvent& event )
{
wxPaintDC dc( m_panelDraw );
wxSize display_size = m_panelDraw->GetClientSize();
wxSize size = m_panelDraw->GetClientSize();
dc.SetDeviceOrigin( size.x / 2, size.y / 2 );
double img_scale = 1.0 / m_workingImage->GetScalingFactor();
VECTOR2I img_size_pixels = m_workingImage->GetSizePixels();
// Adjust the display scale to use the full available display area
double scale_X = (double)display_size.x/img_size_pixels.x;
double scale_Y = (double)display_size.y/img_size_pixels.y;
double display_scale = img_scale * std::min( scale_X, scale_Y );
dc.SetUserScale( display_scale, display_scale );
m_workingImage->DrawBitmap( &dc, VECTOR2I( m_workingImage->GetSize()/2 ) );
double scale = 1.0 / m_workingImage->GetScalingFactor();
dc.SetUserScale( scale, scale );
m_workingImage->DrawBitmap( &dc, wxPoint( 0, 0 ) );
}
+1 -1
View File
@@ -1,5 +1,5 @@
///////////////////////////////////////////////////////////////////////////
// C++ code generated with wxFormBuilder (version 3.10.1-282-g1fa54006)
// C++ code generated with wxFormBuilder (version 3.10.1-133-g388db8e4)
// http://www.wxformbuilder.org/
//
// PLEASE DO *NOT* EDIT THIS FILE!
-368
View File
@@ -1,368 +0,0 @@
<?xml version="1.0" encoding="UTF-8" standalone="yes" ?>
<wxFormBuilder_Project>
<FileVersion major="1" minor="16" />
<object class="Project" expanded="1">
<property name="class_decoration"></property>
<property name="code_generation">C++</property>
<property name="disconnect_events">1</property>
<property name="disconnect_mode">source_name</property>
<property name="disconnect_php_events">0</property>
<property name="disconnect_python_events">0</property>
<property name="embedded_files_path">res</property>
<property name="encoding">UTF-8</property>
<property name="event_generation">connect</property>
<property name="file">panel_image_editor_base</property>
<property name="first_id">1000</property>
<property name="help_provider">none</property>
<property name="image_path_wrapper_function_name"></property>
<property name="indent_with_spaces"></property>
<property name="internationalize">1</property>
<property name="name">panel_image_editor_base</property>
<property name="namespace"></property>
<property name="path">.</property>
<property name="precompiled_header"></property>
<property name="relative_path">1</property>
<property name="skip_lua_events">1</property>
<property name="skip_php_events">1</property>
<property name="skip_python_events">1</property>
<property name="ui_table">UI</property>
<property name="use_array_enum">0</property>
<property name="use_enum">0</property>
<property name="use_microsoft_bom">0</property>
<object class="Panel" expanded="1">
<property name="aui_managed">0</property>
<property name="aui_manager_style">wxAUI_MGR_DEFAULT</property>
<property name="bg"></property>
<property name="context_help"></property>
<property name="context_menu">1</property>
<property name="drag_accept_files">0</property>
<property name="enabled">1</property>
<property name="event_handler">impl_virtual</property>
<property name="fg"></property>
<property name="font"></property>
<property name="hidden">0</property>
<property name="id">wxID_ANY</property>
<property name="maximum_size"></property>
<property name="minimum_size"></property>
<property name="name">PANEL_IMAGE_EDITOR_BASE</property>
<property name="pos"></property>
<property name="size">500,300</property>
<property name="subclass">; ; forward_declare</property>
<property name="tooltip"></property>
<property name="two_step_creation">0</property>
<property name="window_extra_style"></property>
<property name="window_name"></property>
<property name="window_style">wxTAB_TRAVERSAL</property>
<object class="wxBoxSizer" expanded="1">
<property name="minimum_size"></property>
<property name="name">bSizerMain</property>
<property name="orient">wxVERTICAL</property>
<property name="permission">none</property>
<object class="sizeritem" expanded="1">
<property name="border">5</property>
<property name="flag">wxEXPAND</property>
<property name="proportion">1</property>
<object class="wxBoxSizer" expanded="1">
<property name="minimum_size"></property>
<property name="name">bUpperSizer</property>
<property name="orient">wxVERTICAL</property>
<property name="permission">none</property>
<object class="sizeritem" expanded="1">
<property name="border">5</property>
<property name="flag">wxEXPAND</property>
<property name="proportion">1</property>
<object class="wxBoxSizer" expanded="1">
<property name="minimum_size"></property>
<property name="name">bSizerLeft</property>
<property name="orient">wxHORIZONTAL</property>
<property name="permission">none</property>
<object class="sizeritem" expanded="1">
<property name="border">5</property>
<property name="flag">wxEXPAND | wxALL</property>
<property name="proportion">1</property>
<object class="wxPanel" expanded="1">
<property name="BottomDockable">1</property>
<property name="LeftDockable">1</property>
<property name="RightDockable">1</property>
<property name="TopDockable">1</property>
<property name="aui_layer"></property>
<property name="aui_name"></property>
<property name="aui_position"></property>
<property name="aui_row"></property>
<property name="best_size"></property>
<property name="bg"></property>
<property name="caption"></property>
<property name="caption_visible">1</property>
<property name="center_pane">0</property>
<property name="close_button">1</property>
<property name="context_help"></property>
<property name="context_menu">1</property>
<property name="default_pane">0</property>
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="drag_accept_files">0</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>
<property name="font"></property>
<property name="gripper">0</property>
<property name="hidden">0</property>
<property name="id">wxID_ANY</property>
<property name="max_size"></property>
<property name="maximize_button">0</property>
<property name="maximum_size"></property>
<property name="min_size"></property>
<property name="minimize_button">0</property>
<property name="minimum_size">256,256</property>
<property name="moveable">1</property>
<property name="name">m_panelDraw</property>
<property name="pane_border">1</property>
<property name="pane_position"></property>
<property name="pane_size"></property>
<property name="permission">protected</property>
<property name="pin_button">1</property>
<property name="pos"></property>
<property name="resize">Resizable</property>
<property name="show">1</property>
<property name="size"></property>
<property name="subclass"></property>
<property name="toolbar_pane">0</property>
<property name="tooltip"></property>
<property name="window_extra_style"></property>
<property name="window_name"></property>
<property name="window_style">wxFULL_REPAINT_ON_RESIZE|wxTAB_TRAVERSAL|wxBORDER_SIMPLE</property>
<event name="OnPaint">OnRedrawPanel</event>
</object>
</object>
<object class="sizeritem" expanded="1">
<property name="border">5</property>
<property name="flag">wxEXPAND|wxALL</property>
<property name="proportion">0</property>
<object class="wxBoxSizer" expanded="1">
<property name="minimum_size"></property>
<property name="name">bSizerRight</property>
<property name="orient">wxVERTICAL</property>
<property name="permission">none</property>
<object class="sizeritem" expanded="1">
<property name="border">5</property>
<property name="flag">wxEXPAND|wxTOP|wxRIGHT|wxLEFT</property>
<property name="proportion">0</property>
<object class="wxButton" expanded="1">
<property name="BottomDockable">1</property>
<property name="LeftDockable">1</property>
<property name="RightDockable">1</property>
<property name="TopDockable">1</property>
<property name="aui_layer"></property>
<property name="aui_name"></property>
<property name="aui_position"></property>
<property name="aui_row"></property>
<property name="auth_needed">0</property>
<property name="best_size"></property>
<property name="bg"></property>
<property name="bitmap"></property>
<property name="caption"></property>
<property name="caption_visible">1</property>
<property name="center_pane">0</property>
<property name="close_button">1</property>
<property name="context_help"></property>
<property name="context_menu">1</property>
<property name="current"></property>
<property name="default">0</property>
<property name="default_pane">0</property>
<property name="disabled"></property>
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="drag_accept_files">0</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>
<property name="focus"></property>
<property name="font"></property>
<property name="gripper">0</property>
<property name="hidden">0</property>
<property name="id">wxID_ANY</property>
<property name="label">Grey</property>
<property name="margins"></property>
<property name="markup">0</property>
<property name="max_size"></property>
<property name="maximize_button">0</property>
<property name="maximum_size"></property>
<property name="min_size"></property>
<property name="minimize_button">0</property>
<property name="minimum_size"></property>
<property name="moveable">1</property>
<property name="name">m_buttonGrey</property>
<property name="pane_border">1</property>
<property name="pane_position"></property>
<property name="pane_size"></property>
<property name="permission">protected</property>
<property name="pin_button">1</property>
<property name="pos"></property>
<property name="position"></property>
<property name="pressed"></property>
<property name="resize">Resizable</property>
<property name="show">1</property>
<property name="size"></property>
<property name="style"></property>
<property name="subclass"></property>
<property name="toolbar_pane">0</property>
<property name="tooltip"></property>
<property name="validator_data_type"></property>
<property name="validator_style">wxFILTER_NONE</property>
<property name="validator_type">wxDefaultValidator</property>
<property name="validator_variable"></property>
<property name="window_extra_style"></property>
<property name="window_name"></property>
<property name="window_style"></property>
<event name="OnButtonClick">OnGreyScaleConvert</event>
</object>
</object>
<object class="sizeritem" expanded="1">
<property name="border">10</property>
<property name="flag">wxEXPAND|wxTOP|wxBOTTOM</property>
<property name="proportion">0</property>
<object class="spacer" expanded="1">
<property name="height">0</property>
<property name="permission">protected</property>
<property name="width">0</property>
</object>
</object>
<object class="sizeritem" expanded="1">
<property name="border">5</property>
<property name="flag">wxTOP|wxRIGHT|wxLEFT</property>
<property name="proportion">0</property>
<object class="wxStaticText" expanded="1">
<property name="BottomDockable">1</property>
<property name="LeftDockable">1</property>
<property name="RightDockable">1</property>
<property name="TopDockable">1</property>
<property name="aui_layer"></property>
<property name="aui_name"></property>
<property name="aui_position"></property>
<property name="aui_row"></property>
<property name="best_size"></property>
<property name="bg"></property>
<property name="caption"></property>
<property name="caption_visible">1</property>
<property name="center_pane">0</property>
<property name="close_button">1</property>
<property name="context_help"></property>
<property name="context_menu">1</property>
<property name="default_pane">0</property>
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="drag_accept_files">0</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>
<property name="font"></property>
<property name="gripper">0</property>
<property name="hidden">0</property>
<property name="id">wxID_ANY</property>
<property name="label">Image Scale:</property>
<property name="markup">0</property>
<property name="max_size"></property>
<property name="maximize_button">0</property>
<property name="maximum_size"></property>
<property name="min_size"></property>
<property name="minimize_button">0</property>
<property name="minimum_size"></property>
<property name="moveable">1</property>
<property name="name">m_staticTextScale</property>
<property name="pane_border">1</property>
<property name="pane_position"></property>
<property name="pane_size"></property>
<property name="permission">protected</property>
<property name="pin_button">1</property>
<property name="pos"></property>
<property name="resize">Resizable</property>
<property name="show">1</property>
<property name="size"></property>
<property name="style"></property>
<property name="subclass"></property>
<property name="toolbar_pane">0</property>
<property name="tooltip"></property>
<property name="window_extra_style"></property>
<property name="window_name"></property>
<property name="window_style"></property>
<property name="wrap">-1</property>
</object>
</object>
<object class="sizeritem" expanded="1">
<property name="border">5</property>
<property name="flag">wxBOTTOM|wxRIGHT|wxLEFT|wxEXPAND</property>
<property name="proportion">0</property>
<object class="wxTextCtrl" expanded="1">
<property name="BottomDockable">1</property>
<property name="LeftDockable">1</property>
<property name="RightDockable">1</property>
<property name="TopDockable">1</property>
<property name="aui_layer"></property>
<property name="aui_name"></property>
<property name="aui_position"></property>
<property name="aui_row"></property>
<property name="best_size"></property>
<property name="bg"></property>
<property name="caption"></property>
<property name="caption_visible">1</property>
<property name="center_pane">0</property>
<property name="close_button">1</property>
<property name="context_help"></property>
<property name="context_menu">1</property>
<property name="default_pane">0</property>
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="drag_accept_files">0</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>
<property name="font"></property>
<property name="gripper">0</property>
<property name="hidden">0</property>
<property name="id">wxID_ANY</property>
<property name="max_size"></property>
<property name="maximize_button">0</property>
<property name="maximum_size"></property>
<property name="maxlength">0</property>
<property name="min_size"></property>
<property name="minimize_button">0</property>
<property name="minimum_size"></property>
<property name="moveable">1</property>
<property name="name">m_textCtrlScale</property>
<property name="pane_border">1</property>
<property name="pane_position"></property>
<property name="pane_size"></property>
<property name="permission">protected</property>
<property name="pin_button">1</property>
<property name="pos"></property>
<property name="resize">Resizable</property>
<property name="show">1</property>
<property name="size"></property>
<property name="style"></property>
<property name="subclass"></property>
<property name="toolbar_pane">0</property>
<property name="tooltip"></property>
<property name="validator_data_type"></property>
<property name="validator_style">wxFILTER_NONE</property>
<property name="validator_type">wxDefaultValidator</property>
<property name="validator_variable"></property>
<property name="value"></property>
<property name="window_extra_style"></property>
<property name="window_name"></property>
<property name="window_style"></property>
</object>
</object>
</object>
</object>
</object>
</object>
</object>
</object>
</object>
</object>
</object>
</wxFormBuilder_Project>
+1 -1
View File
@@ -1,5 +1,5 @@
///////////////////////////////////////////////////////////////////////////
// C++ code generated with wxFormBuilder (version 3.10.1-282-g1fa54006)
// C++ code generated with wxFormBuilder (version 3.10.1-133-g388db8e4)
// http://www.wxformbuilder.org/
//
// PLEASE DO *NOT* EDIT THIS FILE!
+11 -10
View File
@@ -58,13 +58,7 @@ EDA_DRAW_PANEL_GAL::EDA_DRAW_PANEL_GAL( wxWindow* aParentWindow, wxWindowID aWin
const wxPoint& aPosition, const wxSize& aSize,
KIGFX::GAL_DISPLAY_OPTIONS& aOptions, GAL_TYPE aGalType ) :
wxScrolledCanvas( aParentWindow, aWindowId, aPosition, aSize ),
m_MouseCapturedLost( false ),
m_parent( aParentWindow ),
m_edaFrame( nullptr ),
m_lastRefresh( 0 ),
m_pendingRefresh( false ),
m_drawing( false ),
m_drawingEnabled( false ),
m_gal( nullptr ),
m_view( nullptr ),
m_painter( nullptr ),
@@ -76,9 +70,10 @@ EDA_DRAW_PANEL_GAL::EDA_DRAW_PANEL_GAL( wxWindow* aParentWindow, wxWindowID aWin
m_stealsFocus( true ),
m_statusPopup( nullptr )
{
m_PaintEventCounter = std::make_unique<PROF_COUNTER>( "Draw panel paint events" );
m_parent = aParentWindow;
m_MouseCapturedLost = false;
m_minRefreshPeriod = 13; // 77 FPS (minus render time) by default
m_PaintEventCounter = std::make_unique<PROF_COUNTER>( "Draw panel paint events" );
SetLayoutDirection( wxLayout_LeftToRight );
@@ -151,6 +146,12 @@ EDA_DRAW_PANEL_GAL::EDA_DRAW_PANEL_GAL( wxWindow* aParentWindow, wxWindowID aWin
Connect( eventType, wxEventHandler( EDA_DRAW_PANEL_GAL::OnEvent ), nullptr,
m_eventDispatcher );
m_pendingRefresh = false;
m_drawing = false;
m_drawingEnabled = false;
m_minRefreshPeriod = 13; // 77 FPS (minus render time) by default
// Set up timer that prevents too frequent redraw commands
m_refreshTimer.SetOwner( this );
Connect( m_refreshTimer.GetId(), wxEVT_TIMER,
@@ -211,7 +212,7 @@ void EDA_DRAW_PANEL_GAL::DoRePaint()
if( !m_drawingEnabled )
return;
if( !m_gal->IsInitialized() || !m_gal->IsVisible() )
if( !m_gal->IsVisible() )
return;
m_pendingRefresh = false;
@@ -626,7 +627,7 @@ void EDA_DRAW_PANEL_GAL::onRefreshTimer( wxTimerEvent& aEvent )
void EDA_DRAW_PANEL_GAL::onShowTimer( wxTimerEvent& aEvent )
{
if( m_gal && m_gal->IsInitialized() && m_gal->IsVisible() )
if( m_gal && m_gal->IsVisible() )
{
m_onShowTimer.Stop();
OnShow();
+1 -5
View File
@@ -219,10 +219,6 @@ void EDA_BASE_FRAME::windowClosing( wxCloseEvent& event )
if( canCloseWindow( event ) )
{
m_isClosing = true;
if( m_infoBar )
m_infoBar->Dismiss();
APP_SETTINGS_BASE* cfg = config();
if( cfg )
@@ -1234,7 +1230,7 @@ bool EDA_BASE_FRAME::IsWritable( const wxFileName& aFileName, bool aVerbose )
void EDA_BASE_FRAME::CheckForAutoSaveFile( const wxFileName& aFileName )
{
if( !Pgm().IsGUI() )
if( !IsGUI() )
return;
wxCHECK_RET( aFileName.IsOk(), wxT( "Invalid file name!" ) );
+13 -27
View File
@@ -3,7 +3,7 @@
*
* Copyright (C) 2004-2017 Jean-Pierre Charras, jp.charras at wanadoo.fr
* Copyright (C) 2008 Wayne Stambaugh <stambaughw@gmail.com>
* Copyright (C) 2004-2023 KiCad Developers, see AUTHORS.txt for contributors.
* Copyright (C) 2004-2022 KiCad Developers, see AUTHORS.txt for contributors.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@@ -78,16 +78,12 @@ BEGIN_EVENT_TABLE( EDA_DRAW_FRAME, KIWAY_PLAYER )
EVT_ACTIVATE( EDA_DRAW_FRAME::onActivate )
END_EVENT_TABLE()
bool EDA_DRAW_FRAME::m_openGLFailureOccured = false;
EDA_DRAW_FRAME::EDA_DRAW_FRAME( KIWAY* aKiway, wxWindow* aParent, FRAME_T aFrameType,
const wxString& aTitle, const wxPoint& aPos, const wxSize& aSize,
long aStyle, const wxString& aFrameName,
const EDA_IU_SCALE& aIuScale ) :
KIWAY_PLAYER( aKiway, aParent, aFrameType, aTitle, aPos, aSize, aStyle, aFrameName, aIuScale ),
m_socketServer( nullptr )
long aStyle, const wxString& aFrameName, const EDA_IU_SCALE& aIuScale ) :
KIWAY_PLAYER( aKiway, aParent, aFrameType, aTitle, aPos, aSize, aStyle, aFrameName, aIuScale )
{
m_socketServer = nullptr;
m_mainToolBar = nullptr;
@@ -175,8 +171,8 @@ EDA_DRAW_FRAME::EDA_DRAW_FRAME( KIWAY* aKiway, wxWindow* aParent, FRAME_T aFrame
OnMove( dummy );
// we need to kludge the msg panel to the correct size again
// especially important even for first launches as the constructor of the window
// here usually doesn't have the correct dpi awareness yet
// especially important even for first launches as the constructor of the window here usually doesn't
// have the correct dpi awareness yet
m_frameSize.y += m_msgFrameHeight;
m_msgFrameHeight = EDA_MSG_PANEL::GetRequiredHeight( this );
m_frameSize.y -= m_msgFrameHeight;
@@ -289,7 +285,7 @@ void EDA_DRAW_FRAME::ToggleUserUnits()
else
{
SetUserUnits( GetUserUnits() == EDA_UNITS::INCHES ? EDA_UNITS::MILLIMETRES
: EDA_UNITS::INCHES );
: EDA_UNITS::INCHES );
unitsChangeRefresh();
wxCommandEvent e( UNITS_CHANGED );
@@ -613,8 +609,7 @@ void EDA_DRAW_FRAME::DisplayGridMsg()
{
wxString msg;
msg.Printf( _( "grid %s" ), MessageTextFromValue( GetCanvas()->GetGAL()->GetGridSize().x,
false ) );
msg.Printf( wxS( "grid %s" ), MessageTextFromValue( GetCanvas()->GetGAL()->GetGridSize().x, false ) );
SetStatusText( msg, 4 );
}
@@ -990,8 +985,8 @@ static const wxString productName = wxT( "KiCad E.D.A. " );
void PrintDrawingSheet( const RENDER_SETTINGS* aSettings, const PAGE_INFO& aPageInfo,
const wxString& aSheetName, const wxString& aSheetPath,
const wxString& aFileName, const TITLE_BLOCK& aTitleBlock,
const wxString& aFullSheetName, const wxString& aFileName,
const TITLE_BLOCK& aTitleBlock,
const std::map<wxString, wxString>* aProperties, int aSheetCount,
const wxString& aPageNumber, double aMils2Iu, const PROJECT* aProject,
const wxString& aSheetLayer, bool aIsFirstPage )
@@ -1003,8 +998,7 @@ void PrintDrawingSheet( const RENDER_SETTINGS* aSettings, const PAGE_INFO& aPage
drawList.SetPageNumber( aPageNumber );
drawList.SetSheetCount( aSheetCount );
drawList.SetFileName( aFileName );
drawList.SetSheetName( aSheetName );
drawList.SetSheetPath( aSheetPath );
drawList.SetSheetName( aFullSheetName );
drawList.SetSheetLayer( aSheetLayer );
drawList.SetProject( aProject );
drawList.SetIsFirstPage( aIsFirstPage );
@@ -1034,10 +1028,9 @@ void EDA_DRAW_FRAME::PrintDrawingSheet( const RENDER_SETTINGS* aSettings, BASE_S
DC->SetAxisOrientation( true, false );
}
::PrintDrawingSheet( aSettings, GetPageSettings(), GetScreenDesc(), GetFullScreenDesc(),
aFilename, GetTitleBlock(), aProperties, aScreen->GetPageCount(),
aScreen->GetPageNumber(), aMils2Iu, &Prj(), aSheetLayer,
aScreen->GetVirtualPageNumber() == 1 );
::PrintDrawingSheet( aSettings, GetPageSettings(), GetScreenDesc(), aFilename, GetTitleBlock(),
aProperties, aScreen->GetPageCount(), aScreen->GetPageNumber(), aMils2Iu,
&Prj(), aSheetLayer, aScreen->GetVirtualPageNumber() == 1 );
if( origin.y > 0 )
{
@@ -1054,13 +1047,6 @@ wxString EDA_DRAW_FRAME::GetScreenDesc() const
}
wxString EDA_DRAW_FRAME::GetFullScreenDesc() const
{
// Virtual function. Base class implementation returns an empty string.
return wxEmptyString;
}
bool EDA_DRAW_FRAME::LibraryFileBrowser( bool doOpen, wxFileName& aFilename,
const wxString& wildcard, const wxString& ext,
bool isDirectory, bool aIsGlobal,
+4 -3
View File
@@ -392,9 +392,10 @@ static struct EDA_ITEM_DESC
PROPERTY_MANAGER& propMgr = PROPERTY_MANAGER::Instance();
REGISTER_TYPE( EDA_ITEM );
propMgr.AddProperty( new PROPERTY_ENUM<EDA_ITEM, KICAD_T>( wxS( "Type" ),
NO_SETTER( EDA_ITEM, KICAD_T ), &EDA_ITEM::Type ) )
.SetIsHiddenFromPropertiesManager();
auto typeProp = new PROPERTY_ENUM<EDA_ITEM, KICAD_T>( wxS( "Type" ),
NO_SETTER( EDA_ITEM, KICAD_T ), &EDA_ITEM::Type );
typeProp->SetIsInternal( true );
propMgr.AddProperty( typeProp );
}
} _EDA_ITEM_DESC;
+5 -30
View File
@@ -1687,36 +1687,21 @@ static struct EDA_SHAPE_DESC
PROPERTY_MANAGER& propMgr = PROPERTY_MANAGER::Instance();
REGISTER_TYPE( EDA_SHAPE );
auto isNotPolygon =
[]( INSPECTABLE* aItem ) -> bool
{
// Polygons, unlike other shapes, have no meaningful start or end coordinates
if( EDA_SHAPE* shape = dynamic_cast<EDA_SHAPE*>( aItem ) )
return shape->GetShape() != SHAPE_T::POLY;
return false;
};
auto shape = new PROPERTY_ENUM<EDA_SHAPE, SHAPE_T>( _HKI( "Shape" ),
NO_SETTER( EDA_SHAPE, SHAPE_T ), &EDA_SHAPE::GetShape );
propMgr.AddProperty( shape );
propMgr.AddProperty( new PROPERTY<EDA_SHAPE, int>( _HKI( "Start X" ),
&EDA_SHAPE::SetStartX, &EDA_SHAPE::GetStartX, PROPERTY_DISPLAY::PT_COORD,
ORIGIN_TRANSFORMS::ABS_X_COORD ) )
.SetAvailableFunc( isNotPolygon );
ORIGIN_TRANSFORMS::ABS_X_COORD ) );
propMgr.AddProperty( new PROPERTY<EDA_SHAPE, int>( _HKI( "Start Y" ),
&EDA_SHAPE::SetStartY, &EDA_SHAPE::GetStartY, PROPERTY_DISPLAY::PT_COORD,
ORIGIN_TRANSFORMS::ABS_Y_COORD ) )
.SetAvailableFunc( isNotPolygon );
ORIGIN_TRANSFORMS::ABS_Y_COORD ) );
propMgr.AddProperty( new PROPERTY<EDA_SHAPE, int>( _HKI( "End X" ),
&EDA_SHAPE::SetEndX, &EDA_SHAPE::GetEndX, PROPERTY_DISPLAY::PT_COORD,
ORIGIN_TRANSFORMS::ABS_X_COORD ) )
.SetAvailableFunc( isNotPolygon );
ORIGIN_TRANSFORMS::ABS_X_COORD ) );
propMgr.AddProperty( new PROPERTY<EDA_SHAPE, int>( _HKI( "End Y" ),
&EDA_SHAPE::SetEndY, &EDA_SHAPE::GetEndY, PROPERTY_DISPLAY::PT_COORD,
ORIGIN_TRANSFORMS::ABS_Y_COORD ) )
.SetAvailableFunc( isNotPolygon );
ORIGIN_TRANSFORMS::ABS_Y_COORD ) );
// TODO: m_arcCenter, m_bezierC1, m_bezierC2, m_poly
propMgr.AddProperty( new PROPERTY<EDA_SHAPE, int>( _HKI( "Line Width" ),
&EDA_SHAPE::SetWidth, &EDA_SHAPE::GetWidth, PROPERTY_DISPLAY::PT_SIZE ) );
@@ -1736,17 +1721,7 @@ static struct EDA_SHAPE_DESC
filled->SetAvailableFunc(
[=]( INSPECTABLE* aItem ) -> bool
{
SHAPE_T itemShape;
try
{
itemShape = aItem->Get<SHAPE_T>( shape );
}
catch( std::runtime_error& err )
{
wxFAIL_MSG( err.what() );
return false;
}
SHAPE_T itemShape = aItem->Get<SHAPE_T>( shape );
switch( itemShape )
{
+1 -1
View File
@@ -2,7 +2,7 @@
* This program source code file is part of KiCad, a free EDA CAD application.
*
* Copyright (C) 2016 Jean-Pierre Charras, jp.charras at wanadoo.fr
* Copyright (C) 2004-2023 KiCad Developers, see change_log.txt for contributors.
* Copyright (C) 2004-2022 KiCad Developers, see change_log.txt for contributors.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
+1 -4
View File
@@ -65,7 +65,7 @@ int EDA_UNIT_UTILS::Mils2mm( double aVal )
}
bool EDA_UNIT_UTILS::FetchUnitsFromString( const wxString& aTextValue, EDA_UNITS& aUnits )
void EDA_UNIT_UTILS::FetchUnitsFromString( const wxString& aTextValue, EDA_UNITS& aUnits )
{
wxString buf( aTextValue.Strip( wxString::both ) );
unsigned brk_point = 0;
@@ -92,9 +92,6 @@ bool EDA_UNIT_UTILS::FetchUnitsFromString( const wxString& aTextValue, EDA_UNITS
aUnits = EDA_UNITS::INCHES;
else if( unit == wxT( "de" ) || unit == wxT( "ra" ) ) // "deg" or "rad"
aUnits = EDA_UNITS::DEGREES;
else
return false;
return true;
}
+33 -148
View File
@@ -18,25 +18,23 @@
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include <fontconfig/fontconfig.h>
#include <font/fontconfig.h>
#include <pgm_base.h>
#include <wx/log.h>
#include <trace_helpers.h>
#include <string_utils.h>
#include <macros.h>
#include <font/fontconfig.h>
using namespace fontconfig;
static FONTCONFIG* g_config = nullptr;
/**
* A simple wrapper to avoid exporing fontconfig in the header
*/
struct fontconfig::FONTCONFIG_PAT
inline static FcChar8* wxStringToFcChar8( const wxString& str )
{
FcPattern* pat;
};
wxScopedCharBuffer const fcBuffer = str.ToUTF8();
return (FcChar8*) fcBuffer.data();
}
wxString FONTCONFIG::Version()
@@ -63,112 +61,19 @@ FONTCONFIG* Fontconfig()
}
bool FONTCONFIG::isLanguageMatch( const wxString& aSearchLang, const wxString& aSupportedLang )
{
if( aSearchLang.Lower() == aSupportedLang.Lower() )
return true;
if( aSupportedLang.empty() )
return false;
if( aSearchLang.empty() )
return false;
wxArrayString supportedLangBits;
wxStringSplit( aSupportedLang.Lower(), supportedLangBits, wxS( '-' ) );
wxArrayString searhcLangBits;
wxStringSplit( aSearchLang.Lower(), searhcLangBits, wxS( '-' ) );
// if either side of the comparison have only one section, then its a broad match but fine
// i.e. the haystack is declaring broad support or the search language is broad
if( searhcLangBits.size() == 1 || supportedLangBits.size() == 1 )
{
return searhcLangBits[0] == supportedLangBits[0];
}
// the full two part comparison should have passed the initial shortcut
return false;
}
std::string FONTCONFIG::getFcString( FONTCONFIG_PAT& aPat, const char* aObj, int aIdx )
{
FcChar8* str;
std::string res;
if( FcPatternGetString( aPat.pat, aObj, aIdx, &str ) == FcResultMatch )
res = std::string( reinterpret_cast<char*>( str ) );
return res;
}
void FONTCONFIG::getAllFamilyStrings( FONTCONFIG_PAT& aPat,
std::unordered_map<std::string, std::string>& aFamStringMap )
{
std::string famLang;
std::string fam;
int langIdx = 0;
do
{
famLang = getFcString( aPat, FC_FAMILYLANG, langIdx );
if( famLang.empty() && langIdx != 0 )
break;
else
{
fam = getFcString( aPat, FC_FAMILY, langIdx );
aFamStringMap.insert_or_assign( famLang, fam );
}
} while( langIdx++ < std::numeric_limits<
int8_t>::max() ); //arbitrary to avoid getting stuck for any reason
}
std::string FONTCONFIG::getFamilyStringByLang( FONTCONFIG_PAT& aPat, const wxString& aDesiredLang )
{
std::unordered_map<std::string, std::string> famStrings;
getAllFamilyStrings( aPat, famStrings );
if( famStrings.empty() )
return "";
for( auto const& [key, val] : famStrings )
{
if( isLanguageMatch( aDesiredLang, FROM_UTF8( key.c_str() ) ) )
{
return val;
}
}
// fall back to the first and maybe only available name
// most fonts by review don't even bother declaring more than one font family name
// and they don't even bother declare the language tag either, they just leave it blank
return famStrings.begin()->second;
}
FONTCONFIG::FF_RESULT FONTCONFIG::FindFont( const wxString &aFontName, wxString &aFontFile,
int& aFaceIndex, bool aBold, bool aItalic )
bool aBold, bool aItalic )
{
FF_RESULT retval = FF_RESULT::FF_ERROR;
wxString qualifiedFontName = aFontName;
wxScopedCharBuffer const fcBuffer = qualifiedFontName.ToUTF8();
FcPattern* pat = FcPatternCreate();
if( aBold )
FcPatternAddString( pat, FC_STYLE, (const FcChar8*) "Bold" );
qualifiedFontName << wxS( ":Bold" );
if( aItalic )
FcPatternAddString( pat, FC_STYLE, (const FcChar8*) "Italic" );
FcPatternAddString( pat, FC_FAMILY, (FcChar8*) fcBuffer.data() );
qualifiedFontName << wxS( ":Italic" );
FcPattern* pat = FcNameParse( wxStringToFcChar8( qualifiedFontName ) );
FcConfigSubstitute( nullptr, pat, FcMatchPattern );
FcDefaultSubstitute( pat );
@@ -184,23 +89,14 @@ FONTCONFIG::FF_RESULT FONTCONFIG::FindFont( const wxString &aFontName, wxString
if( FcPatternGetString( font, FC_FILE, 0, &file ) == FcResultMatch )
{
aFontFile = wxString::FromUTF8( (char*) file );
aFaceIndex = 0;
wxString styleStr;
FcChar8* family = nullptr;
FcChar8* style = nullptr;
retval = FF_RESULT::FF_SUBSTITUTE;
std::unordered_map<std::string, std::string> famStrings;
FONTCONFIG_PAT patHolder{ font };
getAllFamilyStrings( patHolder, famStrings );
if( FcPatternGetString( font, FC_FAMILY, 0, &family ) == FcResultMatch )
{
FcPatternGetInteger( font, FC_INDEX, 0, &aFaceIndex );
fontName = wxString::FromUTF8( (char*) family );
if( FcPatternGetString( font, FC_STYLE, 0, &style ) == FcResultMatch )
@@ -233,26 +129,18 @@ FONTCONFIG::FF_RESULT FONTCONFIG::FindFont( const wxString &aFontName, wxString
has_ital = true;
}
for( auto const& [key, val] : famStrings )
if( fontName.Lower().StartsWith( aFontName.Lower() ) )
{
wxString searchFont;
searchFont = wxString::FromUTF8( (char*) val.data() );
if( searchFont.Lower().StartsWith( aFontName.Lower() ) )
{
if( ( aBold && !has_bold ) && ( aItalic && !has_ital ) )
retval = FF_RESULT::FF_MISSING_BOLD_ITAL;
else if( aBold && !has_bold )
retval = FF_RESULT::FF_MISSING_BOLD;
else if( aItalic && !has_ital )
retval = FF_RESULT::FF_MISSING_ITAL;
else if( ( aBold != has_bold ) || ( aItalic != has_ital ) )
retval = FF_RESULT::FF_SUBSTITUTE;
else
retval = FF_RESULT::FF_OK;
break;
}
if( ( aBold && !has_bold ) && ( aItalic && !has_ital ) )
retval = FF_RESULT::FF_MISSING_BOLD_ITAL;
else if( aBold && !has_bold )
retval = FF_RESULT::FF_MISSING_BOLD;
else if( aItalic && !has_ital )
retval = FF_RESULT::FF_MISSING_ITAL;
else if( ( aBold != has_bold ) || ( aItalic != has_ital ) )
retval = FF_RESULT::FF_SUBSTITUTE;
else
retval = FF_RESULT::FF_OK;
}
}
}
@@ -270,14 +158,13 @@ FONTCONFIG::FF_RESULT FONTCONFIG::FindFont( const wxString &aFontName, wxString
}
void FONTCONFIG::ListFonts( std::vector<std::string>& aFonts, const std::string& aDesiredLang )
void FONTCONFIG::ListFonts( std::vector<std::string>& aFonts )
{
// be sure to cache bust if the language changed
if( m_fontInfoCache.empty() || m_fontCacheLastLang != aDesiredLang )
if( m_fonts.empty() )
{
FcPattern* pat = FcPatternCreate();
FcObjectSet* os = FcObjectSetBuild( FC_FAMILY, FC_FAMILYLANG, FC_STYLE, FC_LANG, FC_FILE,
FC_OUTLINE, nullptr );
FcObjectSet* os = FcObjectSetBuild( FC_FAMILY, FC_STYLE, FC_LANG, FC_FILE, FC_OUTLINE,
nullptr );
FcFontSet* fs = FcFontList( nullptr, pat, os );
for( int i = 0; fs && i < fs->nfont; ++i )
@@ -285,10 +172,12 @@ void FONTCONFIG::ListFonts( std::vector<std::string>& aFonts, const std::string&
FcPattern* font = fs->fonts[i];
FcChar8* file;
FcChar8* style;
FcChar8* family;
FcLangSet* langSet;
FcBool outline;
if( FcPatternGetString( font, FC_FILE, 0, &file ) == FcResultMatch
&& FcPatternGetString( font, FC_FAMILY, 0, &family ) == FcResultMatch
&& FcPatternGetString( font, FC_STYLE, 0, &style ) == FcResultMatch
&& FcPatternGetLangSet( font, FC_LANG, 0, &langSet ) == FcResultMatch
&& FcPatternGetBool( font, FC_OUTLINE, 0, &outline ) == FcResultMatch )
@@ -296,9 +185,7 @@ void FONTCONFIG::ListFonts( std::vector<std::string>& aFonts, const std::string&
if( !outline )
continue;
FONTCONFIG_PAT patHolder{ font };
std::string theFamily =
getFamilyStringByLang( patHolder, FROM_UTF8( aDesiredLang.c_str() ) );
std::string theFamily( reinterpret_cast<char *>( family ) );
#ifdef __WXMAC__
// On Mac (at least) some of the font names are in their own language. If
@@ -351,10 +238,10 @@ void FONTCONFIG::ListFonts( std::vector<std::string>& aFonts, const std::string&
if( theFamily.length() > 0 && theFamily.front() == '.' )
continue;
std::map<std::string, FONTINFO>::iterator it = m_fontInfoCache.find( theFamily );
std::map<std::string, FONTINFO>::iterator it = m_fonts.find( theFamily );
if( it == m_fontInfoCache.end() )
m_fontInfoCache.emplace( theFamily, fontInfo );
if( it == m_fonts.end() )
m_fonts.emplace( theFamily, fontInfo );
else
it->second.Children().push_back( fontInfo );
}
@@ -362,10 +249,8 @@ void FONTCONFIG::ListFonts( std::vector<std::string>& aFonts, const std::string&
if( fs )
FcFontSetDestroy( fs );
m_fontCacheLastLang = aDesiredLang;
}
for( const std::pair<const std::string, FONTINFO>& entry : m_fontInfoCache )
for( const std::pair<const std::string, FONTINFO>& entry : m_fonts )
aFonts.push_back( entry.second.Family() );
}
+9 -35
View File
@@ -44,7 +44,6 @@ using namespace KIFONT;
FT_Library OUTLINE_FONT::m_freeType = nullptr;
std::mutex OUTLINE_FONT::m_freeTypeMutex;
OUTLINE_FONT::OUTLINE_FONT() :
m_face(NULL),
@@ -52,8 +51,6 @@ OUTLINE_FONT::OUTLINE_FONT() :
m_fakeBold( false ),
m_fakeItal( false )
{
std::lock_guard<std::mutex> guard( m_freeTypeMutex );
if( !m_freeType )
FT_Init_FreeType( &m_freeType );
}
@@ -61,8 +58,6 @@ OUTLINE_FONT::OUTLINE_FONT() :
wxString OUTLINE_FONT::FreeTypeVersion()
{
std::lock_guard<std::mutex> guard( m_freeTypeMutex );
if( !m_freeType )
FT_Init_FreeType( &m_freeType );
@@ -95,16 +90,12 @@ wxString OUTLINE_FONT::FontLibraryVersion()
OUTLINE_FONT* OUTLINE_FONT::LoadFont( const wxString& aFontName, bool aBold, bool aItalic )
{
std::unique_ptr<OUTLINE_FONT> font = std::make_unique<OUTLINE_FONT>();
OUTLINE_FONT* font = new OUTLINE_FONT();
wxString fontFile;
int faceIndex;
using fc = fontconfig::FONTCONFIG;
fc::FF_RESULT retval = Fontconfig()->FindFont( aFontName, fontFile, faceIndex, aBold, aItalic );
if( retval == fc::FF_RESULT::FF_ERROR )
return nullptr;
fc::FF_RESULT retval = Fontconfig()->FindFont( aFontName, fontFile, aBold, aItalic );
if( retval == fc::FF_RESULT::FF_MISSING_BOLD || retval == fc::FF_RESULT::FF_MISSING_BOLD_ITAL )
font->SetFakeBold();
@@ -112,23 +103,21 @@ OUTLINE_FONT* OUTLINE_FONT::LoadFont( const wxString& aFontName, bool aBold, boo
if( retval == fc::FF_RESULT::FF_MISSING_ITAL || retval == fc::FF_RESULT::FF_MISSING_BOLD_ITAL )
font->SetFakeItal();
if( font->loadFace( fontFile, faceIndex ) != 0 )
return nullptr;
if( retval != fc::FF_RESULT::FF_ERROR )
(void) font->loadFace( fontFile );
font->m_fontName = aFontName; // Keep asked-for name, even if we substituted.
font->m_fontFileName = fontFile;
return font.release();
return font;
}
FT_Error OUTLINE_FONT::loadFace( const wxString& aFontFileName, int aFaceIndex )
FT_Error OUTLINE_FONT::loadFace( const wxString& aFontFileName )
{
std::lock_guard<std::mutex> guard( m_freeTypeMutex );
// TODO: check that going from wxString to char* with UTF-8
// conversion for filename makes sense on any/all platforms
FT_Error e = FT_New_Face( m_freeType, aFontFileName.mb_str( wxConvUTF8 ), aFaceIndex, &m_face );
FT_Error e = FT_New_Face( m_freeType, aFontFileName.mb_str( wxConvUTF8 ), 0, &m_face );
if( !e )
{
@@ -334,18 +323,6 @@ VECTOR2I OUTLINE_FONT::getTextAsGlyphs( BOX2I* aBBox, std::vector<std::unique_pt
const VECTOR2I& aPosition, const EDA_ANGLE& aAngle,
bool aMirror, const VECTOR2I& aOrigin,
TEXT_STYLE_FLAGS aTextStyle ) const
{
std::lock_guard<std::mutex> guard( m_freeTypeMutex );
return getTextAsGlyphsUnlocked( aBBox, aGlyphs, aText, aSize, aPosition, aAngle, aMirror,
aOrigin, aTextStyle );
}
VECTOR2I OUTLINE_FONT::getTextAsGlyphsUnlocked( BOX2I* aBBox, std::vector<std::unique_ptr<GLYPH>>* aGlyphs,
const wxString& aText, const VECTOR2I& aSize,
const VECTOR2I& aPosition, const EDA_ANGLE& aAngle,
bool aMirror, const VECTOR2I& aOrigin,
TEXT_STYLE_FLAGS aTextStyle ) const
{
VECTOR2D glyphSize = aSize;
FT_Face face = m_face;
@@ -389,7 +366,7 @@ VECTOR2I OUTLINE_FONT::getTextAsGlyphsUnlocked( BOX2I* aBBox, std::vector<std::u
{
FT_Matrix matrix;
// Create a 12 degree slant
const float angle = (float)( -M_PI * 12.0f ) / 180.0f;
const float angle = ( -M_PI * 12 ) / 180.0f;
matrix.xx = (FT_Fixed) ( cos( angle ) * 0x10000L );
matrix.xy = (FT_Fixed) ( -sin( angle ) * 0x10000L );
matrix.yx = (FT_Fixed) ( 0 * 0x10000L ); // Don't rotate in the y direction
@@ -489,7 +466,7 @@ VECTOR2I OUTLINE_FONT::getTextAsGlyphsUnlocked( BOX2I* aBBox, std::vector<std::u
{
std::vector<std::unique_ptr<GLYPH>> underscoreGlyphs;
getTextAsGlyphsUnlocked( nullptr, &underscoreGlyphs, wxT( "_" ), aSize, { 0, 0 }, ANGLE_0, false,
getTextAsGlyphs( nullptr, &underscoreGlyphs, wxT( "_" ), aSize, { 0, 0 }, ANGLE_0, false,
{ 0, 0 }, aTextStyle & ~TEXT_STYLE::OVERBAR );
OUTLINE_GLYPH* underscoreGlyph = static_cast<OUTLINE_GLYPH*>( underscoreGlyphs[0].get() );
@@ -575,9 +552,6 @@ void OUTLINE_FONT::RenderToOpenGLCanvas( KIGFX::OPENGL_GAL& aGal, const wxString
unsigned int glyphCount;
hb_glyph_info_t* glyphInfo = hb_buffer_get_glyph_infos( buf, &glyphCount );
hb_glyph_position_t* glyphPos = hb_buffer_get_glyph_positions( buf, &glyphCount );
std::lock_guard<std::mutex> guard( m_freeTypeMutex );
hb_font_t* referencedFont = hb_ft_font_create_referenced( m_face );
hb_ft_font_set_funcs( referencedFont );
+10 -20
View File
@@ -52,8 +52,7 @@ static constexpr double UNDERLINE_POSITION_FACTOR = -0.16;
///< Scale factor for a glyph
static constexpr double STROKE_FONT_SCALE = 1.0 / 21.0;
///< Offset (in stroke font units) to move the origin to the baseline.
static constexpr int FONT_OFFSET = -8;
static constexpr int FONT_OFFSET = -10;
bool g_defaultFontInitialized = false;
@@ -226,8 +225,11 @@ VECTOR2I STROKE_FONT::GetTextAsGlyphs( BOX2I* aBBox, std::vector<std::unique_ptr
bool aMirror, const VECTOR2I& aOrigin,
TEXT_STYLE_FLAGS aTextStyle ) const
{
constexpr int TAB_WIDTH = 4;
constexpr double SPACE_WIDTH = 0.6;
constexpr double INTER_CHAR = 0.2;
constexpr double TAB_WIDTH = 4 * 0.82; // Not quite as wide as 5.1/6.0 tab formatting, but
// a better match for Scintilla, and closer to the
// nominal SPACE_WIDTH + INTER_CHAR
constexpr double SUPER_SUB_SIZE_MULTIPLIER = 0.7;
constexpr double SUPER_HEIGHT_OFFSET = 0.5;
constexpr double SUB_HEIGHT_OFFSET = 0.3;
@@ -235,8 +237,6 @@ VECTOR2I STROKE_FONT::GetTextAsGlyphs( BOX2I* aBBox, std::vector<std::unique_ptr
VECTOR2I cursor( aPosition );
VECTOR2D glyphSize( aSize );
double tilt = ( aTextStyle & TEXT_STYLE::ITALIC ) ? ITALIC_TILT : 0.0;
double space_width = m_glyphBoundingBoxes->front().GetWidth(); // First char is space
int char_count = 0;
if( aTextStyle & TEXT_STYLE::SUBSCRIPT || aTextStyle & TEXT_STYLE::SUPERSCRIPT )
{
@@ -250,26 +250,18 @@ VECTOR2I STROKE_FONT::GetTextAsGlyphs( BOX2I* aBBox, std::vector<std::unique_ptr
for( wxUniChar c : aText )
{
// Handle tabs as locked to the next 4th column (in base-widths).
// Handle tabs as locked to the nearest 4th column (in space-widths).
if( c == '\t' )
{
char_count = ( char_count / TAB_WIDTH + 1 ) * TAB_WIDTH - 1;
int tabWidth = KiROUND( glyphSize.x * TAB_WIDTH );
int currentIntrusion = ( cursor.x - aOrigin.x ) % tabWidth;
int new_cursor = aPosition.x + aSize.x * char_count
+ aSize.x * space_width;
while( new_cursor <= cursor.x )
{
char_count += TAB_WIDTH;
new_cursor += aSize.x * TAB_WIDTH;
}
cursor.x = new_cursor;
cursor.x += tabWidth - currentIntrusion;
}
else if( c == ' ' )
{
// 'space' character - draw nothing, advance cursor position
cursor.x += KiROUND( glyphSize.x * space_width );
cursor.x += KiROUND( glyphSize.x * SPACE_WIDTH );
}
else
{
@@ -300,8 +292,6 @@ VECTOR2I STROKE_FONT::GetTextAsGlyphs( BOX2I* aBBox, std::vector<std::unique_ptr
cursor.x += KiROUND( glyphExtents.x );
}
++char_count;
}
VECTOR2D barOffset( 0.0, 0.0 );
-1
View File
@@ -596,7 +596,6 @@ bool FP_LIB_TABLE::LoadGlobalTable( FP_LIB_TABLE& aTable )
}
}
aTable.Clear();
aTable.Load( fn.GetFullPath() );
SETTINGS_MANAGER& mgr = Pgm().GetSettingsManager();
+13 -47
View File
@@ -57,6 +57,11 @@ static std::optional<double> getKiCadConfiguredScale( const COMMON_SETTINGS& aCo
scale = canvas_scale;
}
if( scale )
{
wxLogTrace( traceHiDpi, wxS( "Scale factor (configured): %f" ), *scale );
}
return scale;
}
@@ -78,6 +83,11 @@ static std::optional<double> getEnvironmentScale()
scale = ENV_VAR::GetEnvVar<double>( wxS( "GDK_SCALE" ) );
}
if( scale )
{
wxLogTrace( traceHiDpi, wxS( "Scale factor (environment): %f" ), *scale );
}
return scale;
}
@@ -91,18 +101,15 @@ DPI_SCALING::DPI_SCALING( COMMON_SETTINGS* aConfig, const wxWindow* aWindow )
double DPI_SCALING::GetScaleFactor() const
{
std::optional<double> val;
wxString src;
if( m_config )
{
val = getKiCadConfiguredScale( *m_config );
src = wxS( "config" );
}
if( !val )
{
val = getEnvironmentScale();
src = wxS( "env" );
}
if( !val && m_window )
@@ -110,58 +117,17 @@ double DPI_SCALING::GetScaleFactor() const
// Use the native WX reporting.
// On Linux, this will not work until WX 3.2 and GTK >= 3.10
// Otherwise it returns 1.0
val = KIPLATFORM::UI::GetPixelScaleFactor( m_window );
src = wxS( "platform" );
val = KIPLATFORM::UI::GetSystemScaleFactor( m_window );
wxLogTrace( traceHiDpi, wxS( "Scale factor (WX): %f" ), *val );
}
if( !val )
{
// Nothing else we can do, give it a default value
val = GetDefaultScaleFactor();
src = wxS( "default" );
wxLogTrace( traceHiDpi, wxS( "Scale factor (default): %f" ), *val );
}
wxLogTrace( traceHiDpi, wxS( "Scale factor (%s): %f" ), src, *val );
return *val;
}
double DPI_SCALING::GetContentScaleFactor() const
{
std::optional<double> val;
wxString src;
if( m_config )
{
val = getKiCadConfiguredScale( *m_config );
src = wxS( "config" );
}
if( !val )
{
val = getEnvironmentScale();
src = wxS( "env" );
}
if( !val && m_window )
{
// Use the native WX reporting.
// On Linux, this will not work until WX 3.2 and GTK >= 3.10
// Otherwise it returns 1.0
val = KIPLATFORM::UI::GetContentScaleFactor( m_window );
src = wxS( "platform" );
}
if( !val )
{
// Nothing else we can do, give it a default value
val = GetDefaultScaleFactor();
src = wxS( "default" );
}
wxLogTrace( traceHiDpi, wxS( "Content scale factor (%s): %f" ), src, *val );
return *val;
}
+12 -3
View File
@@ -169,6 +169,14 @@ GLuint GL_BITMAP_CACHE::cacheBitmap( const BITMAP_BASE* aBitmap )
bmp.w = imgData.GetSize().x;
bmp.h = imgData.GetSize().y;
// The bitmap size needs to be a multiple of 4.
// This is easiest to achieve by ensuring that each row
// has a multiple of 4 pixels
int extra_w = bmp.w % 4;
if( extra_w )
extra_w = 4 - extra_w;
GLuint textureID;
if( m_freedTextureIds.empty() )
@@ -181,14 +189,15 @@ GLuint GL_BITMAP_CACHE::cacheBitmap( const BITMAP_BASE* aBitmap )
m_freedTextureIds.pop_front();
}
bmp.size = bmp.w * bmp.h * 4;
// make_unique initializes this to 0, so extra pixels are transparent
bmp.size = ( bmp.w + extra_w ) * bmp.h * 4;
auto buf = std::make_unique<uint8_t[]>( bmp.size );
for( int y = 0; y < bmp.h; y++ )
{
for( int x = 0; x < bmp.w; x++ )
{
uint8_t* p = buf.get() + ( bmp.w * y + x ) * 4;
uint8_t* p = buf.get() + ( ( bmp.w + extra_w ) * y + x ) * 4;
p[0] = imgData.GetRed( x, y );
p[1] = imgData.GetGreen( x, y );
@@ -205,7 +214,7 @@ GLuint GL_BITMAP_CACHE::cacheBitmap( const BITMAP_BASE* aBitmap )
}
glBindTexture( GL_TEXTURE_2D, textureID );
glTexImage2D( GL_TEXTURE_2D, 0, GL_RGBA8, bmp.w, bmp.h, 0, GL_RGBA, GL_UNSIGNED_BYTE,
glTexImage2D( GL_TEXTURE_2D, 0, GL_RGBA8, bmp.w + extra_w, bmp.h, 0, GL_RGBA, GL_UNSIGNED_BYTE,
buf.get() );
glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST );
-5
View File
@@ -91,11 +91,6 @@ void GRSetColorPen( wxDC* DC, const COLOR4D& Color, int width, wxPenStyle style
if( s_ForceBlackPen )
color = COLOR4D::BLACK;
// wxWidgets will enforce a minimum pen width when printing, so we have to make the pen
// transparent when we don't want the object stroked.
if( width == 0 )
color = COLOR4D::UNSPECIFIED;
const wxPen& curr_pen = DC->GetPen();
if( !curr_pen.IsOk() || curr_pen.GetColour() != color.ToColour()
-1
View File
@@ -424,7 +424,6 @@ void GRID_TRICKS::onCharHook( wxKeyEvent& ev )
{
wxCommandEvent dummy;
m_addHandler( dummy );
handled = true;
}
}
else if( ev.GetModifiers() == wxMOD_CONTROL && ev.GetKeyCode() == 'V' )
+4 -9
View File
@@ -2,7 +2,7 @@
* This program source code file is part of KiCad, a free EDA CAD application.
*
* Copyright (C) 2015 Mark Roszko <mark.roszko@gmail.com>
* Copyright (C) 2015-2023 KiCad Developers, see AUTHORS.txt for contributors.
* Copyright (C) 2015-2021 KiCad Developers, see AUTHORS.txt for contributors.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@@ -100,13 +100,12 @@ static int xferinfo( void* aProgress, curl_off_t aDLtotal, curl_off_t aDLnow, cu
return CURLE_OK;
}
#if LIBCURL_VERSION_NUM < 0x072000 // 7.32.0
static int progressinfo( void* aProgress, double aDLtotal, double aDLnow, double aULtotal, double aULnow )
{
return xferinfo( aProgress, static_cast<curl_off_t>( aDLtotal ), static_cast<curl_off_t>( aDLnow ),
static_cast<curl_off_t>( aULtotal ), static_cast<curl_off_t>( aULnow ) );
}
#endif
KICAD_CURL_EASY::KICAD_CURL_EASY() :
@@ -127,11 +126,7 @@ KICAD_CURL_EASY::KICAD_CURL_EASY() :
curl_easy_setopt( m_CURL, CURLOPT_WRITEDATA, static_cast<void*>( &m_buffer ) );
// Only allow HTTP and HTTPS protocols
#if LIBCURL_VERSION_NUM >= 0x075500 // version 7.85.0
curl_easy_setopt(m_CURL, CURLOPT_PROTOCOLS_STR, "http,https");
#else
curl_easy_setopt( m_CURL, CURLOPT_PROTOCOLS, CURLPROTO_HTTP | CURLPROTO_HTTPS );
#endif
#ifdef _WIN32
// We need this to use the Windows Certificate store
@@ -269,7 +264,7 @@ bool KICAD_CURL_EASY::SetTransferCallback( const TRANSFER_CALLBACK& aCallback, s
{
progress = std::make_unique<CURL_PROGRESS>( this, aCallback,
static_cast<curl_off_t>( aInterval ) );
#if LIBCURL_VERSION_NUM >= 0x072000 // 7.32.0
#ifdef CURLOPT_XFERINFOFUNCTION
setOption( CURLOPT_XFERINFOFUNCTION, xferinfo );
setOption( CURLOPT_XFERINFODATA, progress.get() );
#else
@@ -291,7 +286,7 @@ bool KICAD_CURL_EASY::SetOutputStream( const std::ostream* aOutput )
int KICAD_CURL_EASY::GetTransferTotal( uint64_t& aDownloadedBytes ) const
{
#if LIBCURL_VERSION_NUM >= 0x073700 // 7.55.0
#ifdef CURLINFO_SIZE_DOWNLOAD_T
curl_off_t dl;
int result = curl_easy_getinfo( m_CURL, CURLINFO_SIZE_DOWNLOAD_T, &dl );
aDownloadedBytes = static_cast<uint64_t>( dl );
+4 -6
View File
@@ -431,17 +431,15 @@ KIWAY_PLAYER* KIWAY::Player( FRAME_T aFrameType, bool doCreate, wxTopLevelWindow
}
catch( const IO_ERROR& ioe )
{
wxLogError( ioe.What() );
wxLogError( _( "Error loading editor." ) );
DisplayErrorMessage( nullptr, _( "Error loading editor." ), ioe.What() );
}
catch( const std::exception& e )
catch( const std::exception& e)
{
wxLogError( e.what() );
wxLogError( _( "Error loading editor." ) );
DisplayErrorMessage( nullptr, _( "Error loading editor." ), e.what() );
}
catch( ... )
{
wxLogError( _( "Error loading editor." ) );
DisplayErrorMessage( nullptr, _( "Error loading editor." ) );
}
}
+1 -3
View File
@@ -193,8 +193,6 @@ LIB_TABLE_ROW* LIB_TABLE::findRow( const wxString& aNickName, bool aCheckIfEnabl
{
cur->ensureIndex();
std::shared_lock<std::shared_mutex> lock( cur->m_nickIndexMutex );
for( const std::pair<const wxString, int>& entry : cur->m_nickIndex )
{
if( entry.first == aNickName )
@@ -305,7 +303,7 @@ bool LIB_TABLE::InsertRow( LIB_TABLE_ROW* aRow, bool doReplace )
{
ensureIndex();
std::lock_guard<std::shared_mutex> lock( m_nickIndexMutex );
std::lock_guard<std::mutex> lock( m_nickIndexMutex );
INDEX_CITER it = m_nickIndex.find( aRow->GetNickName() );
+5 -16
View File
@@ -1,7 +1,7 @@
/*
* This program source code file is part of KiCad, a free EDA CAD application.
*
* Copyright (C) 2017-2023 KiCad Developers, see AUTHORS.txt for contributors.
* Copyright (C) 2017-2022 KiCad Developers, see AUTHORS.txt for contributors.
*
* This program is free software: you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
@@ -24,16 +24,12 @@ LIB_TABLE_GRID_TRICKS::LIB_TABLE_GRID_TRICKS( WX_GRID* aGrid ) : GRID_TRICKS( aG
{
}
void LIB_TABLE_GRID_TRICKS::showPopupMenu( wxMenu& menu )
{
bool showActivate = false;
bool showDeactivate = false;
LIB_TABLE_GRID* tbl = static_cast<LIB_TABLE_GRID*>( m_grid->GetTable() );
// Ensure selection parameters are up to date
getSelectedArea();
for( int row = m_sel_row_start; row < m_sel_row_start + m_sel_row_count; ++row )
{
if( tbl->GetValueAsBool( row, 0 ) )
@@ -53,14 +49,10 @@ void LIB_TABLE_GRID_TRICKS::showPopupMenu( wxMenu& menu )
menu.Append( LIB_TABLE_GRID_TRICKS_ACTIVATE_SELECTED, _( "Activate selected" ) );
if( showDeactivate )
menu.Append( LIB_TABLE_GRID_TRICKS_DEACTIVATE_SELECTED, _( "Deactivate selected" ) );
if( showActivate || showDeactivate )
menu.AppendSeparator();
menu.AppendSeparator();
GRID_TRICKS::showPopupMenu( menu );
}
void LIB_TABLE_GRID_TRICKS::doPopupSelection( wxCommandEvent& event )
{
int menu_id = event.GetId();
@@ -69,13 +61,10 @@ void LIB_TABLE_GRID_TRICKS::doPopupSelection( wxCommandEvent& event )
{
LIB_TABLE_GRID* tbl = (LIB_TABLE_GRID*) m_grid->GetTable();
bool selected_state = menu_id == LIB_TABLE_GRID_TRICKS_ACTIVATE_SELECTED;
for( int row = m_sel_row_start; row < m_sel_row_start + m_sel_row_count; ++row )
tbl->SetValueAsBool( row, 0, selected_state );
// Ensure the new state (on/off) of the widgets is immediately shown:
m_grid->Refresh();
{
tbl->SetValueAsBool( row, 0, menu_id == LIB_TABLE_GRID_TRICKS_ACTIVATE_SELECTED );
}
}
else
{
+1 -1
View File
@@ -269,7 +269,7 @@ void LIB_TREE_MODEL_ADAPTER::recreateColumns()
for( const wxString& colName : m_shownColumns )
{
if( !m_colNameMap.count( colName ) )
doAddColumn( colName, colName == wxT( "Description" ) );
doAddColumn( colName, false );
}
}
+2 -3
View File
@@ -2,7 +2,7 @@
* This file is part of libeval, a simple math expression evaluator
*
* Copyright (C) 2017 Michael Geselbracht, mgeselbracht3@gmail.com
* Copyright (C) 2019-2023 KiCad Developers, see AUTHORS.txt for contributors.
* Copyright (C) 2019-2022 KiCad Developers, see AUTHORS.txt for contributors.
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -356,11 +356,10 @@ void COMPILER::newString( const wxString& aString )
m_parseFinished = false;
}
T_TOKEN COMPILER::getToken()
{
T_TOKEN rv;
rv.value = defaultTokenValue;
rv.value.str = nullptr;
bool done = false;
+1 -39
View File
@@ -110,7 +110,7 @@ LANGUAGE_DESCR LanguagesList[] =
{ wxLANGUAGE_SWEDISH, ID_LANGUAGE_SWEDISH, wxT( "Svenska" ), true },
// { wxLANGUAGE_VIETNAMESE, ID_LANGUAGE_VIETNAMESE, wxT( "Tiếng Việt" ), true },
// { wxLANGUAGE_TURKISH, ID_LANGUAGE_TURKISH, wxT( "Türkçe" ), true },
{ wxLANGUAGE_UKRAINIAN, ID_LANGUAGE_UKRANIAN, wxT( "Українська" ), true },
{ wxLANGUAGE_UKRAINIAN, ID_LANGUAGE_UKRANIAN, wxT( "Українець" ), true },
{ wxLANGUAGE_CHINESE_SIMPLIFIED, ID_LANGUAGE_CHINESE_SIMPLIFIED,
wxT( "简体中文" ), true },
{ wxLANGUAGE_CHINESE_TRADITIONAL, ID_LANGUAGE_CHINESE_TRADITIONAL,
@@ -775,26 +775,6 @@ void PGM_BASE::SetLanguageIdentifier( int menu_id )
}
wxString PGM_BASE::GetLanguageTag()
{
const wxLanguageInfo* langInfo = wxLocale::GetLanguageInfo( m_language_id );
if( !langInfo )
return "";
else
{
#if wxCHECK_VERSION( 3, 1, 6 )
wxString str = langInfo->GetCanonicalWithRegion();
#else
wxString str = langInfo->CanonicalName;
#endif
str.Replace( "_", "-" );
return str;
}
}
void PGM_BASE::SetLanguagePath()
{
wxLocale::AddCatalogLookupPathPrefix( PATHS::GetLocaleDataPath() );
@@ -857,21 +837,3 @@ ENV_VAR_MAP& PGM_BASE::GetLocalEnvVariables() const
{
return GetCommonSettings()->m_Env.vars;
}
bool PGM_BASE::IsGUI()
{
if( !wxTheApp )
return false;
#if wxCHECK_VERSION( 3, 1, 6 )
return wxTheApp->IsGUI();
#else
// wxWidgets older than version 3.1.6 do not have a way to know if the app
// has a GUI or is a console application.
// So the trick is to set the App class name when starting kicad-cli, and when
// the app class name is the kicad-cli class name the app is a console app
bool run_gui = wxTheApp->GetClassName() != KICAD_CLI_APP_NAME;
return run_gui;
#endif
}
+129 -170
View File
@@ -861,186 +861,145 @@ void DXF_PLOTTER::Text( const VECTOR2I& aPos,
}
else
{
TEXT_ATTRIBUTES attrs;
attrs.m_Halign = aH_justify;
attrs.m_Valign =aV_justify;
attrs.m_StrokeWidth = aWidth;
attrs.m_Angle = aOrient;
attrs.m_Italic = aItalic;
attrs.m_Bold = aBold;
attrs.m_Mirrored = aSize.x < 0;
attrs.m_Multiline = false;
plotOneLineOfText( aPos, aColor, aText, attrs );
}
}
/* Emit text as a text entity. This loses formatting and shape but it's
more useful as a CAD object */
VECTOR2D origin_dev = userToDeviceCoordinates( aPos );
SetColor( aColor );
wxString cname = getDXFColorName( m_currentColor );
VECTOR2D size_dev = userToDeviceSize( aSize );
int h_code = 0, v_code = 0;
void DXF_PLOTTER::PlotText( const VECTOR2I& aPos, const COLOR4D& aColor,
const wxString& aText,
const TEXT_ATTRIBUTES& aAttributes,
KIFONT::FONT* aFont,
void* aData )
{
TEXT_ATTRIBUTES attrs = aAttributes;
// Fix me: see how to use DXF text mode for multiline texts
if( attrs.m_Multiline && !aText.Contains( wxT( "\n" ) ) )
attrs.m_Multiline = false; // the text has only one line.
bool processSuperSub = aText.Contains( wxT( "^{" ) ) || aText.Contains( wxT( "_{" ) );
if( m_textAsLines || containsNonAsciiChars( aText ) || attrs.m_Multiline || processSuperSub )
{
// output text as graphics.
// Perhaps multiline texts could be handled as DXF text entity
// but I do not want spend time about that (JPC)
PLOTTER::PlotText( aPos, aColor, aText, aAttributes, aFont, aData );
}
else
plotOneLineOfText( aPos, aColor, aText, attrs );
}
void DXF_PLOTTER::plotOneLineOfText( const VECTOR2I& aPos, const COLOR4D& aColor,
const wxString& aText,
const TEXT_ATTRIBUTES& aAttributes )
{
/* Emit text as a text entity. This loses formatting and shape but it's
more useful as a CAD object */
VECTOR2D origin_dev = userToDeviceCoordinates( aPos );
SetColor( aColor );
wxString cname = getDXFColorName( m_currentColor );
VECTOR2D size_dev = userToDeviceSize( aAttributes.m_Size );
int h_code = 0, v_code = 0;
switch( aAttributes.m_Halign )
{
case GR_TEXT_H_ALIGN_LEFT: h_code = 0; break;
case GR_TEXT_H_ALIGN_CENTER: h_code = 1; break;
case GR_TEXT_H_ALIGN_RIGHT: h_code = 2; break;
}
switch( aAttributes.m_Valign )
{
case GR_TEXT_V_ALIGN_TOP: v_code = 3; break;
case GR_TEXT_V_ALIGN_CENTER: v_code = 2; break;
case GR_TEXT_V_ALIGN_BOTTOM: v_code = 1; break;
}
// Position, size, rotation and alignment
// The two alignment point usages is somewhat idiot (see the DXF ref)
// Anyway since we don't use the fit/aligned options, they're the same
fprintf( m_outputFile,
" 0\n"
"TEXT\n"
" 7\n"
"%s\n" // Text style
" 8\n"
"%s\n" // Layer name
" 10\n"
"%g\n" // First point X
" 11\n"
"%g\n" // Second point X
" 20\n"
"%g\n" // First point Y
" 21\n"
"%g\n" // Second point Y
" 40\n"
"%g\n" // Text height
" 41\n"
"%g\n" // Width factor
" 50\n"
"%g\n" // Rotation
" 51\n"
"%g\n" // Oblique angle
" 71\n"
"%d\n" // Mirror flags
" 72\n"
"%d\n" // H alignment
" 73\n"
"%d\n", // V alignment
aAttributes.m_Bold ?
(aAttributes.m_Italic ? "KICADBI" : "KICADB")
: (aAttributes.m_Italic ? "KICADI" : "KICAD"), TO_UTF8( cname ),
origin_dev.x, origin_dev.x,
origin_dev.y, origin_dev.y,
size_dev.y, fabs( size_dev.x / size_dev.y ),
aAttributes.m_Angle.AsDegrees(),
aAttributes.m_Italic ? DXF_OBLIQUE_ANGLE : 0,
aAttributes.m_Mirrored ? 2 : 0, // X mirror flag
h_code, v_code );
/* There are two issue in emitting the text:
- Our overline character (~) must be converted to the appropriate
control sequence %%O or %%o
- Text encoding in DXF is more or less unspecified since depends on
the DXF declared version, the acad version reading it *and* some
system variables to be put in the header handled only by newer acads
Also before R15 unicode simply is not supported (you need to use
bigfonts which are a massive PITA). Common denominator solution:
use Latin1 (and however someone could choke on it, anyway). Sorry
for the extended latin people. If somewant want to try fixing this
recent version seems to use UTF-8 (and not UCS2 like the rest of
Windows)
XXX Actually there is a *third* issue: older DXF formats are limited
to 255 bytes records (it was later raised to 2048); since I'm lazy
and text so long is not probable I just don't implement this rule.
If someone is interested in fixing this, you have to emit the first
partial lines with group code 3 (max 250 bytes each) and then finish
with a group code 1 (less than 250 bytes). The DXF refs explains it
in no more details...
*/
int braceNesting = 0;
int overbarDepth = -1;
fputs( " 1\n", m_outputFile );
for( unsigned int i = 0; i < aText.length(); i++ )
{
/* Here I do a bad thing: writing the output one byte at a time!
but today I'm lazy and I have no idea on how to coerce a Unicode
wxString to spit out latin1 encoded text ...
At least stdio is *supposed* to do output buffering, so there is
hope is not too slow */
wchar_t ch = aText[i];
if( ch > 255 )
switch( aH_justify )
{
// I can't encode this...
putc( '?', m_outputFile );
case GR_TEXT_H_ALIGN_LEFT: h_code = 0; break;
case GR_TEXT_H_ALIGN_CENTER: h_code = 1; break;
case GR_TEXT_H_ALIGN_RIGHT: h_code = 2; break;
}
else
switch( aV_justify )
{
if( aText[i] == '~' && i+1 < aText.length() && aText[i+1] == '{' )
{
fputs( "%%o", m_outputFile );
overbarDepth = braceNesting;
case GR_TEXT_V_ALIGN_TOP: v_code = 3; break;
case GR_TEXT_V_ALIGN_CENTER: v_code = 2; break;
case GR_TEXT_V_ALIGN_BOTTOM: v_code = 1; break;
}
// Skip the '{'
i++;
continue;
}
else if( aText[i] == '{' )
{
braceNesting++;
}
else if( aText[i] == '}' )
{
if( braceNesting > 0 )
braceNesting--;
// Position, size, rotation and alignment
// The two alignment point usages is somewhat idiot (see the DXF ref)
// Anyway since we don't use the fit/aligned options, they're the same
fprintf( m_outputFile,
" 0\n"
"TEXT\n"
" 7\n"
"%s\n" // Text style
" 8\n"
"%s\n" // Layer name
" 10\n"
"%g\n" // First point X
" 11\n"
"%g\n" // Second point X
" 20\n"
"%g\n" // First point Y
" 21\n"
"%g\n" // Second point Y
" 40\n"
"%g\n" // Text height
" 41\n"
"%g\n" // Width factor
" 50\n"
"%g\n" // Rotation
" 51\n"
"%g\n" // Oblique angle
" 71\n"
"%d\n" // Mirror flags
" 72\n"
"%d\n" // H alignment
" 73\n"
"%d\n", // V alignment
aBold ? (aItalic ? "KICADBI" : "KICADB") : (aItalic ? "KICADI" : "KICAD"),
TO_UTF8( cname ),
origin_dev.x, origin_dev.x,
origin_dev.y, origin_dev.y,
size_dev.y, fabs( size_dev.x / size_dev.y ),
aOrient.AsDegrees(),
aItalic ? DXF_OBLIQUE_ANGLE : 0,
size_dev.x < 0 ? 2 : 0, // X mirror flag
h_code, v_code );
if( braceNesting == overbarDepth )
/* There are two issue in emitting the text:
- Our overline character (~) must be converted to the appropriate
control sequence %%O or %%o
- Text encoding in DXF is more or less unspecified since depends on
the DXF declared version, the acad version reading it *and* some
system variables to be put in the header handled only by newer acads
Also before R15 unicode simply is not supported (you need to use
bigfonts which are a massive PITA). Common denominator solution:
use Latin1 (and however someone could choke on it, anyway). Sorry
for the extended latin people. If somewant want to try fixing this
recent version seems to use UTF-8 (and not UCS2 like the rest of
Windows)
XXX Actually there is a *third* issue: older DXF formats are limited
to 255 bytes records (it was later raised to 2048); since I'm lazy
and text so long is not probable I just don't implement this rule.
If someone is interested in fixing this, you have to emit the first
partial lines with group code 3 (max 250 bytes each) and then finish
with a group code 1 (less than 250 bytes). The DXF refs explains it
in no more details...
*/
int braceNesting = 0;
int overbarDepth = -1;
fputs( " 1\n", m_outputFile );
for( unsigned int i = 0; i < aText.length(); i++ )
{
/* Here I do a bad thing: writing the output one byte at a time!
but today I'm lazy and I have no idea on how to coerce a Unicode
wxString to spit out latin1 encoded text ...
At least stdio is *supposed* to do output buffering, so there is
hope is not too slow */
wchar_t ch = aText[i];
if( ch > 255 )
{
// I can't encode this...
putc( '?', m_outputFile );
}
else
{
if( aText[i] == '~' && i+1 < aText.length() && aText[i+1] == '{' )
{
fputs( "%%O", m_outputFile );
overbarDepth = -1;
fputs( "%%o", m_outputFile );
overbarDepth = braceNesting;
// Skip the '{'
i++;
continue;
}
else if( aText[i] == '{' )
{
braceNesting++;
}
else if( aText[i] == '}' )
{
if( braceNesting > 0 )
braceNesting--;
if( braceNesting == overbarDepth )
{
fputs( "%%O", m_outputFile );
overbarDepth = -1;
continue;
}
}
putc( ch, m_outputFile );
}
putc( ch, m_outputFile );
}
}
putc( '\n', m_outputFile );
putc( '\n', m_outputFile );
}
}
+25 -54
View File
@@ -154,6 +154,7 @@ void GERBER_PLOTTER::SetGerberCoordinatesFormat( int aResolution, bool aUseInche
void GERBER_PLOTTER::emitDcode( const VECTOR2D& pt, int dcode )
{
fprintf( m_outputFile, "X%dY%dD%02d*\n", KiROUND( pt.x ), KiROUND( pt.y ), dcode );
}
@@ -848,16 +849,11 @@ void GERBER_PLOTTER::plotArc( const SHAPE_ARC& aArc, bool aPlotInRegion )
LineTo( start );
VECTOR2D devEnd = userToDeviceCoordinates( end );
// devRelCenter is the position on arc center relative to the arc start, in Gerber coord.
// Warning: it is **not** userToDeviceCoordinates( center - start ) when the plotter
// has an offset.
VECTOR2D devRelCenter = userToDeviceCoordinates( center ) - userToDeviceCoordinates( start );
VECTOR2D devCenter = userToDeviceCoordinates( center - start );
// We need to know if the arc is CW or CCW in device coordinates, so build this arc.
SHAPE_ARC deviceArc( userToDeviceCoordinates( start ),
userToDeviceCoordinates( aArc.GetArcMid() ),
devEnd, 0 );
userToDeviceCoordinates( aArc.GetArcMid() ), devEnd, 0 );
fprintf( m_outputFile, "G75*\n" ); // Multiquadrant (360 degrees) mode
@@ -868,7 +864,7 @@ void GERBER_PLOTTER::plotArc( const SHAPE_ARC& aArc, bool aPlotInRegion )
fprintf( m_outputFile, "X%dY%dI%dJ%dD01*\n",
KiROUND( devEnd.x ), KiROUND( devEnd.y ),
KiROUND( devRelCenter.x ), KiROUND( devRelCenter.y ) );
KiROUND( devCenter.x ), KiROUND( devCenter.y ) );
fprintf( m_outputFile, "G01*\n" ); // Back to linear interpolate (perhaps useless here).
}
@@ -889,8 +885,7 @@ void GERBER_PLOTTER::plotArc( const VECTOR2I& aCenter, const EDA_ANGLE& aStartAn
end.x = aCenter.x + KiROUND( aRadius * aEndAngle.Cos() );
end.y = aCenter.y - KiROUND( aRadius * aEndAngle.Sin() );
VECTOR2D devEnd = userToDeviceCoordinates( end );
// devRelCenter is the position on arc center relative to the arc start, in Gerber coord.
VECTOR2D devRelCenter = userToDeviceCoordinates( aCenter ) - userToDeviceCoordinates( start );
VECTOR2D devCenter = userToDeviceCoordinates( aCenter ) - userToDeviceCoordinates( start );
fprintf( m_outputFile, "G75*\n" ); // Multiquadrant (360 degrees) mode
@@ -901,22 +896,24 @@ void GERBER_PLOTTER::plotArc( const VECTOR2I& aCenter, const EDA_ANGLE& aStartAn
fprintf( m_outputFile, "X%dY%dI%dJ%dD01*\n",
KiROUND( devEnd.x ), KiROUND( devEnd.y ),
KiROUND( devRelCenter.x ), KiROUND( devRelCenter.y ) );
KiROUND( devCenter.x ), KiROUND( devCenter.y ) );
fprintf( m_outputFile, "G01*\n" ); // Back to linear interpolate (perhaps useless here).
}
void GERBER_PLOTTER::PlotGerberRegion( const SHAPE_LINE_CHAIN& aPoly, GBR_METADATA* aGbrMetadata )
void GERBER_PLOTTER::PlotGerberRegion( const SHAPE_LINE_CHAIN& aPoly, void* aData )
{
if( aPoly.PointCount() <= 2 )
return;
GBR_METADATA* gbr_metadata = static_cast<GBR_METADATA*>( aData );
bool clearTA_AperFunction = false; // true if a TA.AperFunction is used
if( aGbrMetadata )
if( gbr_metadata )
{
std::string attrib = aGbrMetadata->m_ApertureMetadata.FormatAttribute( !m_useX2format );
std::string attrib = gbr_metadata->m_ApertureMetadata.FormatAttribute( !m_useX2format );
if( !attrib.empty() )
{
@@ -925,7 +922,7 @@ void GERBER_PLOTTER::PlotGerberRegion( const SHAPE_LINE_CHAIN& aPoly, GBR_METADA
}
}
PlotPoly( aPoly, FILL_T::FILLED_SHAPE, 0 , aGbrMetadata );
PlotPoly( aPoly, FILL_T::FILLED_SHAPE, 0 , gbr_metadata );
// Clear the TA attribute, to avoid the next item to inherit it:
if( clearTA_AperFunction )
@@ -942,17 +939,18 @@ void GERBER_PLOTTER::PlotGerberRegion( const SHAPE_LINE_CHAIN& aPoly, GBR_METADA
}
void GERBER_PLOTTER::PlotGerberRegion( const std::vector<VECTOR2I>& aCornerList,
GBR_METADATA* aGbrMetadata )
void GERBER_PLOTTER::PlotGerberRegion( const std::vector<VECTOR2I>& aCornerList, void* aData )
{
if( aCornerList.size() <= 2 )
return;
GBR_METADATA* gbr_metadata = static_cast<GBR_METADATA*>( aData );
bool clearTA_AperFunction = false; // true if a TA.AperFunction is used
if( aGbrMetadata )
if( gbr_metadata )
{
std::string attrib = aGbrMetadata->m_ApertureMetadata.FormatAttribute( !m_useX2format );
std::string attrib = gbr_metadata->m_ApertureMetadata.FormatAttribute( !m_useX2format );
if( !attrib.empty() )
{
@@ -961,7 +959,7 @@ void GERBER_PLOTTER::PlotGerberRegion( const std::vector<VECTOR2I>& aCornerList,
}
}
PlotPoly( aCornerList, FILL_T::FILLED_SHAPE, 0, aGbrMetadata );
PlotPoly( aCornerList, FILL_T::FILLED_SHAPE, 0, gbr_metadata );
// Clear the TA attribute, to avoid the next item to inherit it:
if( clearTA_AperFunction )
@@ -978,19 +976,6 @@ void GERBER_PLOTTER::PlotGerberRegion( const std::vector<VECTOR2I>& aCornerList,
}
void GERBER_PLOTTER::PlotPolyAsRegion( const SHAPE_LINE_CHAIN& aPoly, FILL_T aFill,
int aWidth, GBR_METADATA* aGbrMetadata )
{
// plot a filled polygon using Gerber region, therefore adding X2 attributes
// to the solid polygon
if( aWidth )
PlotPoly( aPoly, FILL_T::NO_FILL, aWidth, aGbrMetadata );
if( aFill != FILL_T::NO_FILL )
PlotGerberRegion( aPoly, aGbrMetadata );
}
void GERBER_PLOTTER::PlotPoly( const SHAPE_LINE_CHAIN& aPoly, FILL_T aFill, int aWidth,
void* aData )
{
@@ -1026,7 +1011,7 @@ void GERBER_PLOTTER::PlotPoly( const SHAPE_LINE_CHAIN& aPoly, FILL_T aFill, int
{
const SHAPE_ARC& arc = aPoly.Arc( arcindex );
plotArc( arc, true );
plotArc( arc, ii > 0 );
// skip points on arcs, since we plot the arc itself
while( ii+1 < aPoly.PointCount() && arcindex == aPoly.ArcIndex( ii+1 ) )
@@ -1060,7 +1045,7 @@ void GERBER_PLOTTER::PlotPoly( const SHAPE_LINE_CHAIN& aPoly, FILL_T aFill, int
{
const SHAPE_ARC& arc = aPoly.Arc( arcindex );
plotArc( arc, true );
plotArc( arc, ii > 0 );
// skip points on arcs, since we plot the arc itself
while( ii+1 < aPoly.PointCount() && arcindex == aPoly.ArcIndex( ii+1 ) )
@@ -1337,7 +1322,7 @@ void GERBER_PLOTTER::FlashPadOval( const VECTOR2I& aPos, const VECTOR2I& aSize,
if( orient.IsCardinal90() )
std::swap( size.x, size.y );
VECTOR2D pos_device = userToDeviceCoordinates( aPos );
VECTOR2I pos_device = userToDeviceCoordinates( aPos );
int aperture_attrib = gbr_metadata ? gbr_metadata->GetApertureAttrib() : 0;
selectAperture( size, 0, ANGLE_0, APERTURE::AT_OVAL, aperture_attrib );
@@ -1368,7 +1353,7 @@ void GERBER_PLOTTER::FlashPadOval( const VECTOR2I& aPos, const VECTOR2I& aSize,
orient -= ANGLE_180;
}
VECTOR2D pos_device = userToDeviceCoordinates( aPos );
VECTOR2I pos_device = userToDeviceCoordinates( aPos );
int aperture_attrib = gbr_metadata ? gbr_metadata->GetApertureAttrib() : 0;
selectAperture( size, 0, orient, APERTURE::AM_ROTATED_OVAL, aperture_attrib );
@@ -1431,7 +1416,7 @@ void GERBER_PLOTTER::FlashPadRect( const VECTOR2I& pos, const VECTOR2I& aSize,
}
else
{
VECTOR2D pos_device = userToDeviceCoordinates( pos );
VECTOR2I pos_device = userToDeviceCoordinates( pos );
int aperture_attrib = gbr_metadata ? gbr_metadata->GetApertureAttrib() : 0;
selectAperture( size, 0, ANGLE_0, APERTURE::AT_RECT, aperture_attrib );
@@ -1448,7 +1433,7 @@ void GERBER_PLOTTER::FlashPadRect( const VECTOR2I& pos, const VECTOR2I& aSize,
{
m_hasApertureRotRect = true;
VECTOR2D pos_device = userToDeviceCoordinates( pos );
VECTOR2I pos_device = userToDeviceCoordinates( pos );
int aperture_attrib = gbr_metadata ? gbr_metadata->GetApertureAttrib() : 0;
selectAperture( size, 0, aOrient, APERTURE::AM_ROT_RECT, aperture_attrib );
@@ -1770,7 +1755,7 @@ void GERBER_PLOTTER::FlashPadChamferRoundRect( const VECTOR2I& aShapePos, const
if( aData )
gbr_metadata = *static_cast<GBR_METADATA*>( aData );
VECTOR2D pos_device = userToDeviceCoordinates( aShapePos );
VECTOR2I pos_device = userToDeviceCoordinates( aShapePos );
SHAPE_POLY_SET outline;
std::vector<VECTOR2I> cornerList;
@@ -2009,20 +1994,6 @@ void GERBER_PLOTTER::Text( const VECTOR2I& aPos,
}
void GERBER_PLOTTER::PlotText( const VECTOR2I& aPos, const COLOR4D& aColor,
const wxString& aText,
const TEXT_ATTRIBUTES& aAttributes,
KIFONT::FONT* aFont,
void* aData )
{
GBR_METADATA* gbr_metadata = static_cast<GBR_METADATA*>( aData );
if( gbr_metadata )
formatNetAttribute( &gbr_metadata->m_NetlistMetadata );
PLOTTER::PlotText( aPos, aColor, aText, aAttributes, aFont, aData );
}
void GERBER_PLOTTER::SetLayerPolarity( bool aPositive )
{
if( aPositive )
+4 -30
View File
@@ -1376,9 +1376,7 @@ void PDF_PLOTTER::Text( const VECTOR2I& aPos,
double ctm_a, ctm_b, ctm_c, ctm_d, ctm_e, ctm_f;
double wideningFactor, heightFactor;
VECTOR2I t_size( std::abs( aSize.x ), std::abs( aSize.y ) );
computeTextParameters( aPos, aText, aOrient, t_size, m_plotMirror, aH_justify,
computeTextParameters( aPos, aText, aOrient, aSize, m_plotMirror, aH_justify,
aV_justify, aWidth, aItalic, aBold, &wideningFactor, &ctm_a,
&ctm_b, &ctm_c, &ctm_d, &ctm_e, &ctm_f, &heightFactor );
@@ -1391,7 +1389,7 @@ void PDF_PLOTTER::Text( const VECTOR2I& aPos,
if( !aFont )
aFont = KIFONT::FONT::GetFont();
VECTOR2I full_box( aFont->StringBoundaryLimits( aText, t_size, aWidth, aBold, aItalic ) );
VECTOR2I full_box( aFont->StringBoundaryLimits( aText, aSize, aWidth, aBold, aItalic ) );
VECTOR2I box_x( full_box.x, 0 );
VECTOR2I box_y( 0, full_box.y );
@@ -1412,13 +1410,13 @@ void PDF_PLOTTER::Text( const VECTOR2I& aPos,
{
wxString word = str_tok.GetNextToken();
computeTextParameters( pos, word, aOrient, t_size, m_plotMirror, GR_TEXT_H_ALIGN_LEFT,
computeTextParameters( pos, word, aOrient, aSize, m_plotMirror, GR_TEXT_H_ALIGN_LEFT,
GR_TEXT_V_ALIGN_BOTTOM, aWidth, aItalic, aBold, &wideningFactor, &ctm_a,
&ctm_b, &ctm_c, &ctm_d, &ctm_e, &ctm_f, &heightFactor );
// Extract the changed width and rotate by the orientation to get the offset for the
// next word
VECTOR2I bbox( aFont->StringBoundaryLimits( word, t_size, aWidth, aBold, aItalic ).x, 0 );
VECTOR2I bbox( aFont->StringBoundaryLimits( word, aSize, aWidth, aBold, aItalic ).x, 0 );
RotatePoint( bbox, aOrient );
pos += bbox;
@@ -1446,30 +1444,6 @@ void PDF_PLOTTER::Text( const VECTOR2I& aPos,
}
void PDF_PLOTTER::PlotText( const VECTOR2I& aPos, const COLOR4D& aColor,
const wxString& aText,
const TEXT_ATTRIBUTES& aAttributes,
KIFONT::FONT* aFont,
void* aData )
{
VECTOR2I size = aAttributes.m_Size;
// PDF files do not like 0 sized texts which create broken files.
if( size.x == 0 || size.y == 0 )
return;
if( aAttributes.m_Mirrored )
size.x = -size.x;
PDF_PLOTTER::Text( aPos, aColor, aText, aAttributes.m_Angle, size,
aAttributes.m_Halign, aAttributes.m_Valign,
aAttributes.m_StrokeWidth,
aAttributes.m_Italic, aAttributes.m_Bold,
aAttributes.m_Multiline,
aFont, aData );
}
void PDF_PLOTTER::HyperlinkBox( const BOX2I& aBox, const wxString& aDestinationURL )
{
m_hyperlinksInPage.push_back( std::make_pair( aBox, aDestinationURL ) );
-22
View File
@@ -967,28 +967,6 @@ void PS_PLOTTER::Text( const VECTOR2I& aPos,
}
void PS_PLOTTER::PlotText( const VECTOR2I& aPos,
const COLOR4D& aColor,
const wxString& aText,
const TEXT_ATTRIBUTES& aAttributes,
KIFONT::FONT* aFont,
void* aData )
{
SetCurrentLineWidth( aAttributes.m_StrokeWidth );
SetColor( aColor );
// Draw the hidden postscript text (if requested)
if( m_textMode == PLOT_TEXT_MODE::PHANTOM )
{
std::string ps_test = encodeStringForPlotter( aText );
VECTOR2D pos_dev = userToDeviceCoordinates( aPos );
fprintf( m_outputFile, "%s %g %g phantomshow\n", ps_test.c_str(), pos_dev.x, pos_dev.y );
}
PLOTTER::PlotText( aPos, aColor, aText, aAttributes, aFont, aData );
}
/**
* Character widths for Helvetica
*/
+1 -27
View File
@@ -633,13 +633,7 @@ void SVG_PLOTTER::PlotImage( const wxImage& aImage, const VECTOR2I& aPos, double
{
wxMemoryOutputStream img_stream;
if( m_colorMode )
aImage.SaveFile( img_stream, wxBITMAP_TYPE_PNG );
else // Plot in B&W
{
wxImage image = aImage.ConvertToGreyscale();
image.SaveFile( img_stream, wxBITMAP_TYPE_PNG );
}
aImage.SaveFile( img_stream, wxBITMAP_TYPE_PNG );
size_t input_len = img_stream.GetOutputStreamBuffer()->GetBufferSize();
std::vector<uint8_t> buffer( input_len );
std::vector<uint8_t> encoded;
@@ -853,23 +847,3 @@ void SVG_PLOTTER::Text( const VECTOR2I& aPos,
fputs( "</g>", m_outputFile );
}
void SVG_PLOTTER::PlotText( const VECTOR2I& aPos, const COLOR4D& aColor,
const wxString& aText,
const TEXT_ATTRIBUTES& aAttributes,
KIFONT::FONT* aFont,
void* aData )
{
VECTOR2I size = aAttributes.m_Size;
if( aAttributes.m_Mirrored )
size.x = -size.x;
SVG_PLOTTER::Text( aPos, aColor, aText, aAttributes.m_Angle, size,
aAttributes.m_Halign, aAttributes.m_Valign,
aAttributes.m_StrokeWidth,
aAttributes.m_Italic, aAttributes.m_Bold,
aAttributes.m_Multiline,
aFont, aData );
}
+18 -50
View File
@@ -2,7 +2,7 @@
* This program source code file is part of KiCad, a free EDA CAD application.
*
* Copyright (C) 2017 Jean-Pierre Charras, jp.charras at wanadoo.fr
* Copyright (C) 2017-2023 KiCad Developers, see AUTHORS.txt for contributors.
* Copyright (C) 2017-2022 KiCad Developers, see AUTHORS.txt for contributors.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@@ -694,6 +694,23 @@ void PLOTTER::PlotPoly( const SHAPE_LINE_CHAIN& aCornerList, FILL_T aFill, int a
}
/**
* Same as GRText, but plot graphic text instead of draw it.
*
* @param aPos is the text position (according to aH_justify, aV_justify).
* @param aColor is the text color.
* @param aText is the text to draw.
* @param aOrient is the angle.
* @param aSize is the text size (size.x or size.y can be < 0 for mirrored texts).
* @param aH_justify is the horizontal justification (Left, center, right).
* @param aV_justify is the vertical justification (bottom, center, top).
* @param aPenWidth is the line width (if = 0, use plot default line width).
* @param aItalic is the true to simulate an italic font.
* @param aBold use true to use a bold font Useful only with default width value (aPenWidth = 0).
* @param aMultilineAllowed use true to plot text as multiline, otherwise single line.
* @param aData is a parameter used by some plotters in SetCurrentLineWidth(),
* not directly used here.
*/
void PLOTTER::Text( const VECTOR2I& aPos,
const COLOR4D& aColor,
const wxString& aText,
@@ -742,55 +759,6 @@ void PLOTTER::Text( const VECTOR2I& aPos,
attributes.m_Valign = aV_justify;
attributes.m_Size = aSize;
// if Size.x is < 0, the text is mirrored (we have no other param to know a text is mirrored)
if( attributes.m_Size.x < 0 )
{
attributes.m_Size.x = -attributes.m_Size.x;
attributes.m_Mirrored = true;
}
if( !aFont )
aFont = KIFONT::FONT::GetFont();
aFont->Draw( &callback_gal, aText, aPos, attributes );
}
void PLOTTER::PlotText( const VECTOR2I& aPos, const COLOR4D& aColor,
const wxString& aText,
const TEXT_ATTRIBUTES& aAttributes,
KIFONT::FONT* aFont,
void* aData )
{
KIGFX::GAL_DISPLAY_OPTIONS empty_opts;
TEXT_ATTRIBUTES attributes = aAttributes;
int penWidth = attributes.m_StrokeWidth;
SetColor( aColor );
SetCurrentLineWidth( penWidth, aData );
if( penWidth == 0 && attributes.m_Bold ) // Use default values if aPenWidth == 0
penWidth = GetPenSizeForBold( std::min( attributes.m_Size.x, attributes.m_Size.y ) );
if( penWidth < 0 )
penWidth = -penWidth;
attributes.m_StrokeWidth = penWidth;
CALLBACK_GAL callback_gal( empty_opts,
// Stroke callback
[&]( const VECTOR2I& aPt1, const VECTOR2I& aPt2 )
{
MoveTo( aPt1 );
LineTo( aPt2 );
PenFinish();
},
// Polygon callback
[&]( const SHAPE_LINE_CHAIN& aPoly )
{
PlotPoly( aPoly, FILL_T::FILLED_SHAPE, 0, aData );
} );
if( !aFont )
aFont = KIFONT::FONT::GetFont();
@@ -193,7 +193,7 @@ void CADSTAR_ARCHIVE_PARSER::LINECODE::Parse( XNODE* aNode, PARSER_CONTEXT* aCon
XNODE* cNode = aNode->GetChildren();
if( !cNode || cNode->GetName() != wxT( "STYLE" ) )
if( cNode->GetName() != wxT( "STYLE" ) )
THROW_UNKNOWN_NODE_IO_ERROR( cNode->GetName(), wxString::Format( "LINECODE -> %s", Name ) );
wxString styleStr = GetXmlAttributeIDString( cNode, 0 );
@@ -486,28 +486,18 @@ void CADSTAR_ARCHIVE_PARSER::VERTEX::AppendToChain( SHAPE_LINE_CHAIN* aChainToAp
const std::function<VECTOR2I( const VECTOR2I& )> aCadstarToKicadPointCallback,
double aAccuracy ) const
{
VECTOR2I endPoint = aCadstarToKicadPointCallback( End );
if( Type == VERTEX_TYPE::POINT )
{
aChainToAppendTo->Append( aCadstarToKicadPointCallback( End ) );
aChainToAppendTo->Append( endPoint );
return;
}
wxCHECK_MSG( aChainToAppendTo->PointCount() > 0, /*void*/,
"Can't append an arc to vertex to an empty chain" );
aChainToAppendTo->Append( BuildArc( aChainToAppendTo->GetPoint( -1 ), aCadstarToKicadPointCallback),
aAccuracy );
}
SHAPE_ARC CADSTAR_ARCHIVE_PARSER::VERTEX::BuildArc( const VECTOR2I& aPrevPoint,
const std::function<VECTOR2I( const VECTOR2I& )> aCadstarToKicadPointCallback ) const
{
wxCHECK_MSG( Type != VERTEX_TYPE::POINT, SHAPE_ARC(),
"Can't build an arc for a straight segment!" );
VECTOR2I startPoint = aPrevPoint;
VECTOR2I endPoint = aCadstarToKicadPointCallback( End );
VECTOR2I startPoint = aChainToAppendTo->GetPoint( -1 );
VECTOR2I centerPoint;
if( Type == VERTEX_TYPE::ANTICLOCKWISE_SEMICIRCLE || Type == VERTEX_TYPE::CLOCKWISE_SEMICIRCLE )
@@ -526,8 +516,9 @@ SHAPE_ARC CADSTAR_ARCHIVE_PARSER::VERTEX::BuildArc( const VECTOR2I& aPrevPoint,
clockwise = !clockwise;
SHAPE_ARC arc;
arc.ConstructFromStartEndCenter( startPoint, endPoint, centerPoint, clockwise );
return arc.ConstructFromStartEndCenter( startPoint, endPoint, centerPoint, clockwise );
aChainToAppendTo->Append( arc, aAccuracy );
}
@@ -2428,9 +2419,7 @@ XNODE* CADSTAR_ARCHIVE_PARSER::LoadArchiveFile( const wxString& aFileName,
const wxString& aFileTypeIdentifier, PROGRESS_REPORTER* aProgressReporter )
{
KEYWORD emptyKeywords[1] = {};
XNODE* rootNode = nullptr;
XNODE* cNode = nullptr;
XNODE* iNode = nullptr;
XNODE * iNode = nullptr, *cNode = nullptr;
int tok;
bool cadstarFileCheckDone = false;
wxString str;
@@ -2462,10 +2451,7 @@ XNODE* CADSTAR_ARCHIVE_PARSER::LoadArchiveFile( const wxString& aFileName,
if( aProgressReporter && ( currentProgress() - previousReportedProgress ) > 0.01 )
{
if( !aProgressReporter->KeepRefreshing() )
{
delete rootNode;
THROW_IO_ERROR( _( "File import cancelled by user." ) );
}
aProgressReporter->SetCurrentProgress( currentProgress() );
previousReportedProgress = currentProgress();
@@ -2481,7 +2467,6 @@ XNODE* CADSTAR_ARCHIVE_PARSER::LoadArchiveFile( const wxString& aFileName,
else
{
//too many closing brackets
delete rootNode;
THROW_IO_ERROR( _( "The selected file is not valid or might be corrupt!" ) );
}
}
@@ -2491,9 +2476,6 @@ XNODE* CADSTAR_ARCHIVE_PARSER::LoadArchiveFile( const wxString& aFileName,
str = wxString( lexer.CurText(), *conv );
cNode = new XNODE( wxXML_ELEMENT_NODE, str );
if( !rootNode )
rootNode = cNode;
if( iNode )
{
//we will add it as attribute as well as child node
@@ -2503,10 +2485,7 @@ XNODE* CADSTAR_ARCHIVE_PARSER::LoadArchiveFile( const wxString& aFileName,
else if( !cadstarFileCheckDone )
{
if( cNode->GetName() != aFileTypeIdentifier )
{
delete rootNode;
THROW_IO_ERROR( _( "The selected file is not valid or might be corrupt!" ) );
}
cadstarFileCheckDone = true;
}
@@ -2522,28 +2501,19 @@ XNODE* CADSTAR_ARCHIVE_PARSER::LoadArchiveFile( const wxString& aFileName,
else
{
//not enough closing brackets
delete rootNode;
THROW_IO_ERROR( _( "The selected file is not valid or might be corrupt!" ) );
}
}
// Not enough closing brackets
if( iNode != nullptr )
{
delete rootNode;
THROW_IO_ERROR( _( "The selected file is not valid or might be corrupt!" ) );
}
// Throw if no data was parsed
if( rootNode )
{
return rootNode;
}
if( cNode )
return cNode;
else
{
delete rootNode;
THROW_IO_ERROR( _( "The selected file is not valid or might be corrupt!" ) );
}
return nullptr;
}
@@ -83,7 +83,6 @@ class wxXmlAttribute;
class PROGRESS_REPORTER;
class SHAPE_LINE_CHAIN;
class SHAPE_POLY_SET;
class SHAPE_ARC;
/**
* @brief Helper functions and common structures for CADSTAR PCB and Schematic archive files.
@@ -93,8 +92,6 @@ class CADSTAR_ARCHIVE_PARSER
public:
CADSTAR_ARCHIVE_PARSER() { m_progressReporter = nullptr; }
virtual ~CADSTAR_ARCHIVE_PARSER() {}
typedef wxString LINECODE_ID;
typedef wxString HATCHCODE_ID;
@@ -454,10 +451,6 @@ public:
void AppendToChain( SHAPE_LINE_CHAIN* aChainToAppendTo,
const std::function<VECTOR2I( const VECTOR2I& )> aCadstarToKicadPointCallback,
double aAccuracy ) const;
SHAPE_ARC BuildArc( const VECTOR2I& aPrevPoint,
const std::function<VECTOR2I( const VECTOR2I& )>
aCadstarToKicadPointCallback ) const;
};
/**
+1
View File
@@ -47,6 +47,7 @@ struct EPART;
struct ETEXT;
typedef std::unordered_map<wxString, wxXmlNode*> NODE_MAP;
typedef std::map<wxString, FOOTPRINT*> FOOTPRINT_MAP;
typedef std::map<wxString, EINSTANCE*> EINSTANCE_MAP;
typedef std::map<wxString, std::unique_ptr<EPART>> EPART_MAP;
+4 -5
View File
@@ -130,7 +130,7 @@ const void* PROPERTY_MANAGER::TypeCast( const void* aSource, TYPE_ID aBase, TYPE
}
PROPERTY_BASE& PROPERTY_MANAGER::AddProperty( PROPERTY_BASE* aProperty, const wxString& aGroup )
void PROPERTY_MANAGER::AddProperty( PROPERTY_BASE* aProperty, const wxString& aGroup )
{
const wxString& name = aProperty->Name();
TYPE_ID hash = aProperty->OwnerHash();
@@ -147,16 +147,15 @@ PROPERTY_BASE& PROPERTY_MANAGER::AddProperty( PROPERTY_BASE* aProperty, const wx
}
m_dirty = true;
return *aProperty;
}
PROPERTY_BASE& PROPERTY_MANAGER::ReplaceProperty( size_t aBase, const wxString& aName,
PROPERTY_BASE* aNew, const wxString& aGroup )
void PROPERTY_MANAGER::ReplaceProperty( size_t aBase, const wxString& aName, PROPERTY_BASE* aNew,
const wxString& aGroup )
{
CLASS_DESC& classDesc = getClass( aNew->OwnerHash() );
classDesc.m_replaced.insert( std::make_pair( aBase, aName ) );
return AddProperty( aNew, aGroup );
AddProperty( aNew, aGroup );
}
+1 -2
View File
@@ -25,7 +25,6 @@
#include <pgm_base.h>
#include <settings/app_settings.h>
#include <settings/json_settings_internals.h>
#include <settings/color_settings.h>
#include <settings/common_settings.h>
#include <settings/parameters.h>
@@ -148,7 +147,7 @@ APP_SETTINGS_BASE::APP_SETTINGS_BASE( const std::string& aFilename, int aSchemaV
&m_System.last_imperial_units, static_cast<int>( EDA_UNITS::INCHES ) ) );
m_params.emplace_back( new PARAM<wxString>( "appearance.color_theme",
&m_ColorTheme, COLOR_SETTINGS::COLOR_BUILTIN_DEFAULT ) );
&m_ColorTheme, wxS( "_builtin_default" ) ) );
addParamsForWindow( &m_Window, "window" );
+2 -4
View File
@@ -31,8 +31,6 @@
///! Update the schema version whenever a migration is required
const int colorsSchemaVersion = 5;
const wxString COLOR_SETTINGS::COLOR_BUILTIN_DEFAULT = "_builtin_default";
const wxString COLOR_SETTINGS::COLOR_BUILTIN_CLASSIC = "_builtin_classic";
COLOR_SETTINGS::COLOR_SETTINGS( const wxString& aFilename, bool aAbsolutePath ) :
@@ -380,12 +378,12 @@ void COLOR_SETTINGS::SetColor( int aLayer, const COLOR4D& aColor )
std::vector<COLOR_SETTINGS*> COLOR_SETTINGS::CreateBuiltinColorSettings()
{
COLOR_SETTINGS* defaultTheme = new COLOR_SETTINGS( COLOR_BUILTIN_DEFAULT );
COLOR_SETTINGS* defaultTheme = new COLOR_SETTINGS( wxT( "_builtin_default" ) );
defaultTheme->SetName( _( "KiCad Default" ) );
defaultTheme->m_writeFile = false;
defaultTheme->Load(); // We can just get the colors out of the param defaults for this one
COLOR_SETTINGS* classicTheme = new COLOR_SETTINGS( COLOR_BUILTIN_CLASSIC );
COLOR_SETTINGS* classicTheme = new COLOR_SETTINGS( wxT( "_builtin_classic" ) );
classicTheme->SetName( _( "KiCad Classic" ) );
classicTheme->m_writeFile = false;
+6 -16
View File
@@ -66,10 +66,6 @@ SETTINGS_MANAGER::SETTINGS_MANAGER( bool aHeadless ) :
// create the common settings shared by all applications. Not loaded immediately
m_common_settings = RegisterSettings( new COMMON_SETTINGS, false );
// Create the built-in color settings
// Here to allow the Python API to access the built-in colors
registerBuiltinColorSettings();
}
SETTINGS_MANAGER::~SETTINGS_MANAGER()
@@ -207,7 +203,7 @@ COLOR_SETTINGS* SETTINGS_MANAGER::GetColorSettings( const wxString& aName )
if( !ret )
{
ret = registerColorSettings( aName );
*ret = *m_color_settings.at( COLOR_SETTINGS::COLOR_BUILTIN_DEFAULT );
*ret = *m_color_settings.at( "_builtin_default" );
ret->SetFilename( wxT( "user" ) );
ret->SetReadOnly( false );
}
@@ -216,7 +212,7 @@ COLOR_SETTINGS* SETTINGS_MANAGER::GetColorSettings( const wxString& aName )
}
// This had better work
return m_color_settings.at( COLOR_SETTINGS::COLOR_BUILTIN_DEFAULT );
return m_color_settings.at( "_builtin_default" );
}
@@ -309,17 +305,11 @@ COLOR_SETTINGS* SETTINGS_MANAGER::GetMigratedColorSettings()
}
void SETTINGS_MANAGER::registerBuiltinColorSettings()
{
for( COLOR_SETTINGS* settings : COLOR_SETTINGS::CreateBuiltinColorSettings() )
m_color_settings[settings->GetFilename()] = RegisterSettings( settings, false );
}
void SETTINGS_MANAGER::loadAllColorSettings()
{
// Create the built-in color settings
registerBuiltinColorSettings();
for( COLOR_SETTINGS* settings : COLOR_SETTINGS::CreateBuiltinColorSettings() )
m_color_settings[settings->GetFilename()] = RegisterSettings( settings, false );
wxFileName third_party_path;
const ENV_VAR_MAP& env = Pgm().GetLocalEnvVariables();
@@ -633,12 +623,12 @@ bool SETTINGS_MANAGER::GetPreviousVersionPaths( std::vector<wxString>* aPaths )
wxFileName wxGtkPath;
wxGtkPath.AssignDir( wxS( "~/.config/kicad" ) );
wxGtkPath.MakeAbsolute();
base_paths.emplace_back( wxGtkPath );
base_paths.emplace_back( wxGtkPath.GetPath() );
// We also want to pick up regular flatpak if we are nightly
wxGtkPath.AssignDir( wxS( "~/.var/app/org.kicad.KiCad/config/kicad" ) );
wxGtkPath.MakeAbsolute();
base_paths.emplace_back( wxGtkPath );
base_paths.emplace_back( wxGtkPath.GetPath() );
}
#endif
+1 -1
View File
@@ -196,7 +196,7 @@ wxString EscapeString( const wxString& aSource, ESCAPE_CONTEXT aContext )
}
else if( aContext == CTX_JS_STR )
{
if( c >= 0x7F || c == '\'' || c == '\\' || c == '(' || c == ')' )
if( c >= 0x7F || c == '\'' || c == '\\' )
{
unsigned int code = c;
char buffer[16];
+1 -41
View File
@@ -34,18 +34,13 @@
%rename(getWxPoint) operator wxPoint;
%rename(getWxSize) operator wxSize;
%{
#include <math/vector2d.h>
#include <math/vector3.h>
#include <math/box2.h>
%}
%include <math/vector2d.h>
%include <math/vector3.h>
#include <math/box2.h>
%include <math/box2.h>
%template(VECTOR2I) VECTOR2<int>;
%template(VECTOR2I_EXTENDED_TYPE) VECTOR2_TRAITS<int>;
%template(VECTOR3D) VECTOR3<double>;
%template(BOX2I) BOX2<VECTOR2I>;
%extend VECTOR2<int>
@@ -79,38 +74,3 @@
%}
}
%extend VECTOR3<double>
{
void Set(double x, double y, double z) { self->x = x; self->y = y; self->z = z; }
PyObject* Get()
{
PyObject* tup = PyTuple_New(3);
PyTuple_SET_ITEM(tup, 0, PyFloat_FromDouble(self->x));
PyTuple_SET_ITEM(tup, 1, PyFloat_FromDouble(self->y));
PyTuple_SET_ITEM(tup, 2, PyFloat_FromDouble(self->z));
return tup;
}
%pythoncode
%{
def __eq__(self,other): return (self.x==other.x and self.y==other.y and self.z==other.z)
def __ne__(self,other): return not (self==other)
def __str__(self): return str(self.Get())
def __repr__(self): return 'VECTOR3D'+str(self.Get())
def __len__(self): return len(self.Get())
def __getitem__(self, index): return self.Get()[index]
def __setitem__(self, index, val):
if index == 0:
self.x = val
elif index == 1:
self.y = val
elif index == 2:
self.z = val
else:
raise IndexError
def __nonzero__(self): return self.Get() != (0, 0, 0)
%}
}
+2 -4
View File
@@ -50,7 +50,7 @@
/// URL to launch a new issue with pre-populated description
wxString COMMON_CONTROL::m_bugReportUrl =
wxS( "https://gitlab.com/kicad/code/kicad/issues/new?issuable_template=bare&issue[description]=%s" );
wxS( "https://gitlab.com/kicad/code/kicad/issues/new?issue[description]=%s" );
/// Issue template to use for reporting bugs (this should not be translated)
@@ -113,9 +113,7 @@ int COMMON_CONTROL::ShowLibraryTable( const TOOL_EVENT& aEvent )
try // Sch frame was not available, try to start it
{
KIFACE* kiface = m_frame->Kiway().KiFACE( KIWAY::FACE_SCH );
if( kiface )
kiface->CreateKiWindow( m_frame, DIALOG_SCH_LIBRARY_TABLE, &m_frame->Kiway() );
kiface->CreateKiWindow( m_frame, DIALOG_SCH_LIBRARY_TABLE, &m_frame->Kiway() );
}
catch( ... )
{
+1 -1
View File
@@ -1400,7 +1400,7 @@ void VIEW::RecacheAllItems()
void VIEW::UpdateItems()
{
if( !m_gal->IsVisible() || !m_gal->IsInitialized() )
if( !m_gal->IsVisible() )
return;
unsigned int cntGeomUpdate = 0;
+1 -12
View File
@@ -24,7 +24,6 @@
#include <widgets/color_swatch.h>
#include <wx/dcmemory.h>
#include <gal/dpi_scaling.h>
#include <dialogs/dialog_color_picker.h>
#include <memory>
@@ -134,16 +133,6 @@ COLOR_SWATCH::COLOR_SWATCH( wxWindow* aParent, const COLOR4D& aColor, int aID,
m_checkerboardSize = ConvertDialogToPixels( CHECKERBOARD_SIZE_DU );
m_checkerboardBg = aParent->GetBackgroundColour();
#ifdef __WXMSW__
// These need additional scaling on Windows because of some discrepancy between pixel and
// content scaling that only affects certain widgets on Windows HiDPI. On other platforms, the
// value returned by ConvertDialogToPixels appears to be correct.
DPI_SCALING dpi( nullptr, aParent );
m_size /= dpi.GetContentScaleFactor();
m_checkerboardSize /= dpi.GetContentScaleFactor();
#endif
auto sizer = new wxBoxSizer( wxHORIZONTAL );
SetSizer( sizer );
@@ -311,4 +300,4 @@ void COLOR_SWATCH::OnDarkModeToggle()
m_checkerboardBg = m_parent->GetBackgroundColour();
wxBitmap bm = MakeBitmap( m_color, m_background, m_size, m_checkerboardSize, m_checkerboardBg );
m_swatch->SetBitmap( bm );
}
}
+1 -7
View File
@@ -18,10 +18,8 @@
*/
#include <widgets/font_choice.h>
#include <kiplatform/ui.h>
#include <wx/fontenum.h>
#include <font/fontconfig.h>
#include <pgm_base.h>
// The "official" name of the building Kicad stroke font (always existing)
#include <font/kicad_font_name.h>
@@ -34,7 +32,7 @@ FONT_CHOICE::FONT_CHOICE( wxWindow* aParent, int aId, wxPoint aPosition, wxSize
m_systemFontCount = wxChoice::GetCount();
std::vector<std::string> fontNames;
Fontconfig()->ListFonts( fontNames, std::string( Pgm().GetLanguageTag().utf8_str() ) );
Fontconfig()->ListFonts( fontNames );
wxArrayString menuList;
@@ -55,11 +53,7 @@ FONT_CHOICE::FONT_CHOICE( wxWindow* aParent, int aId, wxPoint aPosition, wxSize
menuList.Add( wxString( name ) );
menuList.Sort();
Freeze();
Append( menuList );
KIPLATFORM::UI::LargeChoiceBoxHack( this );
Thaw();
m_notFound = wxS( " " ) + _( "<not found>" );
}
+1 -5
View File
@@ -27,7 +27,6 @@
#include <wx/odcombo.h>
#include <wx/menuitem.h>
#include <gal/dpi_scaling.h>
#include <layer_ids.h>
#include <widgets/layer_box_selector.h>
@@ -141,12 +140,9 @@ int LAYER_BOX_SELECTOR::SetLayerSelection( int layer )
void LAYER_BOX_SELECTOR::ResyncBitmapOnly()
{
DPI_SCALING dpi( nullptr, this );
int size = static_cast<int>( dpi.GetScaleFactor() * 14 );
for( int i = 0; i < (int) GetCount(); ++i )
{
wxBitmap layerbmp( size, size );
wxBitmap layerbmp( 14, 14 );
DrawColorSwatch( layerbmp, getLayerColor( LAYER_PCB_BACKGROUND ), getLayerColor( i ) );
}
}
-10
View File
@@ -185,16 +185,6 @@ LIB_TREE::~LIB_TREE()
}
void LIB_TREE::ShowChangedLanguage()
{
if( m_query_ctrl )
m_query_ctrl->SetDescriptiveText( _( "Filter" ) );
if( m_adapter )
m_adapter->ShowChangedLanguage();
}
LIB_ID LIB_TREE::GetSelectedLibId( int* aUnit ) const
{
wxDataViewItem sel = m_tree_ctrl->GetSelection();
+223 -243
View File
@@ -61,8 +61,7 @@ double mpWindow::zoomIncrementalFactor = 1.1;
IMPLEMENT_ABSTRACT_CLASS( mpLayer, wxObject )
mpLayer::mpLayer() :
m_type( mpLAYER_UNDEF )
mpLayer::mpLayer() : m_type( mpLAYER_UNDEF )
{
SetPen( (wxPen&) *wxBLACK_PEN );
SetFont( (wxFont&) *wxNORMAL_FONT );
@@ -198,14 +197,12 @@ wxSize mpInfoLayer::GetSize() const
}
mpInfoCoords::mpInfoCoords() :
mpInfoLayer()
mpInfoCoords::mpInfoCoords() : mpInfoLayer()
{
}
mpInfoCoords::mpInfoCoords( wxRect rect, const wxBrush* brush ) :
mpInfoLayer( rect, brush )
mpInfoCoords::mpInfoCoords( wxRect rect, const wxBrush* brush ) : mpInfoLayer( rect, brush )
{
}
@@ -276,14 +273,12 @@ void mpInfoCoords::Plot( wxDC& dc, mpWindow& w )
}
mpInfoLegend::mpInfoLegend() :
mpInfoLayer()
mpInfoLegend::mpInfoLegend() : mpInfoLayer()
{
}
mpInfoLegend::mpInfoLegend( wxRect rect, const wxBrush* brush ) :
mpInfoLayer( rect, brush )
mpInfoLegend::mpInfoLegend( wxRect rect, const wxBrush* brush ) : mpInfoLayer( rect, brush )
{
}
@@ -306,7 +301,7 @@ void mpInfoLegend::Plot( wxDC& dc, mpWindow& w )
int scrx = w.GetScrX();
int scry = w.GetScrY();
if( m_winX != scrx || m_winY != scry )
if( (m_winX != scrx) || (m_winY != scry) )
{
if( m_winX > 1 )
m_dim.x = (int) floor( (double) (m_dim.x * scrx / m_winX) );
@@ -327,27 +322,26 @@ void mpInfoLegend::Plot( wxDC& dc, mpWindow& w )
// wxBrush semiWhite(image1);
dc.SetBrush( m_brush );
dc.SetFont( m_font );
const int baseWidth = mpLEGEND_MARGIN * 2 + mpLEGEND_LINEWIDTH;
int textX = baseWidth, textY = mpLEGEND_MARGIN;
int plotCount = 0;
int posY = 0;
int tmpX = 0;
int tmpY = 0;
mpLayer* layer = nullptr;
wxPen lpen;
wxString label;
const int baseWidth = (mpLEGEND_MARGIN * 2 + mpLEGEND_LINEWIDTH);
int textX = baseWidth, textY = mpLEGEND_MARGIN;
int plotCount = 0;
int posY = 0;
int tmpX = 0, tmpY = 0;
mpLayer* ly = NULL;
wxPen lpen;
wxString label;
for( unsigned int p = 0; p < w.CountAllLayers(); p++ )
{
layer = w.GetLayer( p );
ly = w.GetLayer( p );
if( layer->GetLayerType() == mpLAYER_PLOT && layer->IsVisible() )
if( (ly->GetLayerType() == mpLAYER_PLOT) && ( ly->IsVisible() ) )
{
label = layer->GetDisplayName();
label = ly->GetName();
dc.GetTextExtent( label, &tmpX, &tmpY );
textX = ( textX > tmpX + baseWidth ) ? textX : tmpX + baseWidth + mpLEGEND_MARGIN;
textY += tmpY;
textX =
( textX > (tmpX + baseWidth) ) ? textX : (tmpX + baseWidth + mpLEGEND_MARGIN);
textY += (tmpY);
}
}
@@ -363,25 +357,25 @@ void mpInfoLegend::Plot( wxDC& dc, mpWindow& w )
for( unsigned int p2 = 0; p2 < w.CountAllLayers(); p2++ )
{
layer = w.GetLayer( p2 );
ly = w.GetLayer( p2 );
if( layer->GetLayerType() == mpLAYER_PLOT && layer->IsVisible() )
if( (ly->GetLayerType() == mpLAYER_PLOT) && ( ly->IsVisible() ) )
{
label = layer->GetDisplayName();
lpen = layer->GetPen();
label = ly->GetName();
lpen = ly->GetPen();
dc.GetTextExtent( label, &tmpX, &tmpY );
dc.SetPen( lpen );
// textX = (textX > (tmpX + baseWidth)) ? textX : (tmpX + baseWidth);
// textY += (tmpY + mpLEGEND_MARGIN);
posY = m_dim.y + mpLEGEND_MARGIN + plotCount * tmpY + (tmpY >> 1);
dc.DrawLine( m_dim.x + mpLEGEND_MARGIN, // X start coord
posY, // Y start coord
m_dim.x + mpLEGEND_LINEWIDTH + mpLEGEND_MARGIN, // X end coord
posY );
dc.DrawLine( m_dim.x + mpLEGEND_MARGIN, // X start coord
posY, // Y start coord
m_dim.x + mpLEGEND_LINEWIDTH + mpLEGEND_MARGIN, // X end coord
posY );
// dc.DrawRectangle(m_dim.x + 5, m_dim.y + 5 + plotCount*tmpY, 5, 5);
dc.DrawText( label,
m_dim.x + baseWidth,
m_dim.y + mpLEGEND_MARGIN + plotCount * tmpY );
m_dim.x + baseWidth,
m_dim.y + mpLEGEND_MARGIN + plotCount * tmpY );
plotCount++;
}
}
@@ -547,8 +541,8 @@ mpFXY::mpFXY( const wxString& name, int flags )
SetName( name );
m_flags = flags;
m_type = mpLAYER_PLOT;
m_scaleX = nullptr;
m_scaleY = nullptr;
m_scaleX = NULL;
m_scaleY = NULL;
// Avoid not initialized members:
maxDrawX = minDrawX = maxDrawY = minDrawY = 0;
@@ -568,216 +562,205 @@ void mpFXY::UpdateViewBoundary( wxCoord xnew, wxCoord ynew )
void mpFXY::Plot( wxDC& dc, mpWindow& w )
{
wxCHECK_RET( m_scaleX, wxS( "X scale was not set" ) );
wxCHECK_RET( m_scaleY, wxS( "Y scale was not set" ) );
if( !m_visible )
return;
wxCoord startPx = m_drawOutsideMargins ? 0 : w.GetMarginLeft();
wxCoord endPx = m_drawOutsideMargins ? w.GetScrX() : w.GetScrX() - w.GetMarginRight();
wxCoord minYpx = m_drawOutsideMargins ? 0 : w.GetMarginTop();
wxCoord maxYpx = m_drawOutsideMargins ? w.GetScrY() : w.GetScrY() - w.GetMarginBottom();
// Check for a collapsed window before we try to allocate a negative number of points
if( endPx <= startPx || minYpx >= maxYpx )
return;
dc.SetPen( m_pen );
double x, y;
// Do this to reset the counters to evaluate bounding box for label positioning
Rewind();
GetNextXY( x, y );
maxDrawX = x;
minDrawX = x;
maxDrawY = y;
minDrawY = y;
// drawnPoints = 0;
Rewind();
dc.SetClippingRegion( startPx, minYpx, endPx - startPx + 1, maxYpx - minYpx + 1 );
if( !m_continuous )
if( m_visible )
{
bool first = true;
wxCoord ix = 0;
std::set<wxCoord> ys;
dc.SetPen( m_pen );
while( GetNextXY( x, y ) )
double x, y;
// Do this to reset the counters to evaluate bounding box for label positioning
Rewind(); GetNextXY( x, y );
maxDrawX = x; minDrawX = x; maxDrawY = y; minDrawY = y;
// drawnPoints = 0;
Rewind();
wxCoord startPx = m_drawOutsideMargins ? 0 : w.GetMarginLeft();
wxCoord endPx = m_drawOutsideMargins ? w.GetScrX() : w.GetScrX() - w.GetMarginRight();
wxCoord minYpx = m_drawOutsideMargins ? 0 : w.GetMarginTop();
wxCoord maxYpx = m_drawOutsideMargins ? w.GetScrY() : w.GetScrY() - w.GetMarginBottom();
dc.SetClippingRegion( startPx, minYpx, endPx - startPx + 1, maxYpx - minYpx + 1 );
if( !m_continuous )
{
double px = m_scaleX->TransformToPlot( x );
double py = m_scaleY->TransformToPlot( y );
wxCoord newX = w.x2p( px );
bool first = true;
wxCoord ix = 0;
std::set<wxCoord> ys;
if( first )
while( GetNextXY( x, y ) )
{
ix = newX;
first = false;
}
double px = m_scaleX->TransformToPlot( x );
double py = m_scaleY->TransformToPlot( y );
wxCoord newX = w.x2p( px );
if( newX == ix ) // continue until a new X coordinate is reached
{
// collect all unique points
ys.insert( w.y2p( py ) );
continue;
}
for( auto& iy: ys )
{
if( m_drawOutsideMargins
|| ( (ix >= startPx) && (ix <= endPx) && (iy >= minYpx) && (iy <= maxYpx) ) )
if( first )
{
// for some reason DrawPoint does not use the current pen, so we use
// DrawLine for fat pens
if( m_pen.GetWidth() <= 1 )
dc.DrawPoint( ix, iy );
else
dc.DrawLine( ix, iy, ix, iy );
UpdateViewBoundary( ix, iy );
ix = newX;
first = false;
}
}
ys.clear();
ix = newX;
ys.insert( w.y2p( py ) );
}
}
else
{
int count = 0;
int x0=0; // X position of merged current vertical line
int ymin0=0; // y min coord of merged current vertical line
int ymax0=0; // y max coord of merged current vertical line
int dupx0 = 0; // count of currently merged vertical lines
wxPoint line_start; // starting point of the current line to draw
// A buffer to store coordinates of lines to draw
std::vector<wxPoint>pointList;
pointList.reserve( endPx - startPx + 1 );
// Note: we can use dc.DrawLines() only for a reasonable number or points (<10000),
// because at least on Windows dc.DrawLines() can hang for a lot of points.
// (> 10000 points) (can happens when a lot of points is calculated)
// To avoid long draw time (and perhaps hanging) one plot only not redundant lines.
// To avoid artifacts when skipping points to the same x coordinate, for each group of
// points at a give, x coordinate we also draw a vertical line at this coord, from the
// ymin to the ymax vertical coordinates of skipped points
while( GetNextXY( x, y ) )
{
double px = m_scaleX->TransformToPlot( x );
double py = m_scaleY->TransformToPlot( y );
wxCoord x1 = w.x2p( px );
wxCoord y1 = w.y2p( py );
// Store only points on the drawing area, to speed up the drawing time
// Note: x1 is a value truncated from px by w.x2p(). So to be sure the first point
// is drawn, the x1 low limit is startPx-1 in plot coordinates
if( x1 >= startPx-1 && x1 <= endPx )
{
if( !count || line_start.x != x1 )
{
if( count && dupx0 > 1 && ymin0 != ymax0 )
{
// Vertical points are merged, draw the pending vertical line
// However, if the line is one pixel length, it is not drawn, because
// the main trace show this point
dc.DrawLine( x0, ymin0, x0, ymax0 );
}
x0 = x1;
ymin0 = ymax0 = y1;
dupx0 = 0;
pointList.emplace_back( wxPoint( x1, y1 ) );
line_start.x = x1;
line_start.y = y1;
count++;
}
else
{
ymin0 = std::min( ymin0, y1 );
ymax0 = std::max( ymax0, y1 );
x0 = x1;
dupx0++;
}
}
}
if( pointList.size() > 1 )
{
// For a better look (when using dashed lines) and more optimization, try to merge
// horizontal segments, in order to plot longer lines
// We are merging horizontal segments because this is easy, and horizontal segments
// are a frequent cases
std::vector<wxPoint> drawPoints;
drawPoints.reserve( endPx - startPx + 1 );
drawPoints.push_back( pointList[0] ); // push the first point in list
for( size_t ii = 1; ii < pointList.size()-1; ii++ )
{
// Skip intermediate points between the first point and the last point of the
// segment candidate
if( drawPoints.back().y == pointList[ii].y &&
drawPoints.back().y == pointList[ii+1].y )
if( newX == ix ) // continue until a new X coordinate is reached
{
// collect all unique points
ys.insert( w.y2p( py ) );
continue;
}
else
for( auto& iy: ys )
{
drawPoints.push_back( pointList[ii] );
if( m_drawOutsideMargins
|| ( (ix >= startPx) && (ix <= endPx) && (iy >= minYpx)
&& (iy <= maxYpx) ) )
{
// for some reason DrawPoint does not use the current pen,
// so we use DrawLine for fat pens
if( m_pen.GetWidth() <= 1 )
{
dc.DrawPoint( ix, iy );
}
else
{
dc.DrawLine( ix, iy, ix, iy );
}
UpdateViewBoundary( ix, iy );
}
}
ys.clear();
ix = newX;
ys.insert( w.y2p( py ) );
}
}
else
{
int count = 0;
int x0=0; // X position of merged current vertical line
int ymin0=0; // y min coord of merged current vertical line
int ymax0=0; // y max coord of merged current vertical line
int dupx0 = 0; // count of currently merged vertical lines
wxPoint line_start; // starting point of the current line to draw
// A buffer to store coordinates of lines to draw
std::vector<wxPoint>pointList;
pointList.reserve( endPx - startPx + 1 );
// Note: we can use dc.DrawLines() only for a reasonable number or points (<10000),
// because at least on Windows dc.DrawLines() can hang for a lot of points.
// (> 10000 points) (can happens when a lot of points is calculated)
// To avoid long draw time (and perhaps hanging) one plot only not redundant lines.
// To avoid artifacts when skipping points to the same x coordinate, for each
// group of points at a give, x coordinate we also draw a vertical line at this coord,
// from the ymin to the ymax vertical coordinates of skipped points
while( GetNextXY( x, y ) )
{
double px = m_scaleX->TransformToPlot( x );
double py = m_scaleY->TransformToPlot( y );
wxCoord x1 = w.x2p( px );
wxCoord y1 = w.y2p( py );
// Store only points on the drawing area, to speed up the drawing time
// Note: x1 is a value truncated from px by w.x2p(). So to be sure the
// first point is drawn, the x1 low limit is startPx-1 in plot coordinates
if( x1 >= startPx-1 && x1 <= endPx )
{
if( !count || line_start.x != x1 )
{
if( count && dupx0 > 1 && ymin0 != ymax0 )
{
// Vertical points are merged, draw the pending vertical line
// However, if the line is one pixel length, it is not drawn,
// because the main trace show this point
dc.DrawLine( x0, ymin0, x0, ymax0 );
}
x0 = x1;
ymin0 = ymax0 = y1;
dupx0 = 0;
pointList.emplace_back( wxPoint( x1, y1 ) );
line_start.x = x1;
line_start.y = y1;
count++;
}
else
{
ymin0 = std::min( ymin0, y1 );
ymax0 = std::max( ymax0, y1 );
x0 = x1;
dupx0++;
}
}
}
// push the last point to draw in list
if( drawPoints.back() != pointList.back() )
drawPoints.push_back( pointList.back() );
if( pointList.size() > 1 )
{
// For a better look (when using dashed lines) and more optimization,
// try to merge horizontal segments, in order to plot longer lines
// we are merging horizontal segments because this is easy,
// and horizontal segments are a frequent cases
std::vector<wxPoint> drawPoints;
drawPoints.reserve( endPx - startPx + 1 );
dc.DrawLines( drawPoints.size(), &drawPoints[0] );
drawPoints.push_back( pointList[0] ); // push the first point in list
for( size_t ii = 1; ii < pointList.size()-1; ii++ )
{
// Skip intermediate points between the first point and the last
// point of the segment candidate
if( drawPoints.back().y == pointList[ii].y &&
drawPoints.back().y == pointList[ii+1].y )
continue;
else
drawPoints.push_back( pointList[ii] );
}
// push the last point to draw in list
if( drawPoints.back() != pointList.back() )
drawPoints.push_back( pointList.back() );
dc.DrawLines( drawPoints.size(), &drawPoints[0] );
}
}
}
if( !m_name.IsEmpty() && m_showName )
{
dc.SetFont( m_font );
wxCoord tx, ty;
dc.GetTextExtent( m_name, &tx, &ty );
// xxx implement else ... if (!HasBBox())
if( !m_name.IsEmpty() && m_showName )
{
// const int sx = w.GetScrX();
// const int sy = w.GetScrY();
dc.SetFont( m_font );
if( (m_flags & mpALIGNMASK) == mpALIGN_NW )
wxCoord tx, ty;
dc.GetTextExtent( m_name, &tx, &ty );
// xxx implement else ... if (!HasBBox())
{
tx = minDrawX + 8;
ty = maxDrawY + 8;
}
else if( (m_flags & mpALIGNMASK) == mpALIGN_NE )
{
tx = maxDrawX - tx - 8;
ty = maxDrawY + 8;
}
else if( (m_flags & mpALIGNMASK) == mpALIGN_SE )
{
tx = maxDrawX - tx - 8;
ty = minDrawY - ty - 8;
}
else
{
// mpALIGN_SW
tx = minDrawX + 8;
ty = minDrawY - ty - 8;
// const int sx = w.GetScrX();
// const int sy = w.GetScrY();
if( (m_flags & mpALIGNMASK) == mpALIGN_NW )
{
tx = minDrawX + 8;
ty = maxDrawY + 8;
}
else if( (m_flags & mpALIGNMASK) == mpALIGN_NE )
{
tx = maxDrawX - tx - 8;
ty = maxDrawY + 8;
}
else if( (m_flags & mpALIGNMASK) == mpALIGN_SE )
{
tx = maxDrawX - tx - 8;
ty = minDrawY - ty - 8;
}
else
{
// mpALIGN_SW
tx = minDrawX + 8;
ty = minDrawY - ty - 8;
}
}
dc.DrawText( m_name, tx, ty );
}
dc.DrawText( m_name, tx, ty );
}
dc.DestroyClippingRegion();
@@ -1412,7 +1395,7 @@ mpScaleY::mpScaleY( const wxString& name, int flags, bool ticks )
m_flags = flags;
m_ticks = ticks;
m_type = mpLAYER_AXIS;
m_masterScale = nullptr;
m_masterScale = NULL;
m_nameFlags = mpALIGN_BORDER_LEFT;
}
@@ -1618,8 +1601,7 @@ EVT_MENU( mpID_ZOOM_OUT, mpWindow::OnZoomOut )
EVT_MENU( mpID_LOCKASPECT, mpWindow::OnLockAspect )
END_EVENT_TABLE()
mpWindow::mpWindow() :
wxWindow(),
mpWindow::mpWindow() : wxWindow(),
m_lockaspect( false ),
m_minX( 0.0 ),
m_maxX( 0.0 ),
@@ -1680,11 +1662,11 @@ mpWindow::mpWindow( wxWindow* parent,
m_minX = m_minY = 0;
m_maxX = m_maxY = 0;
m_last_lx = m_last_ly = 0;
m_buff_bmp = nullptr;
m_buff_bmp = NULL;
m_enableDoubleBuffer = false;
m_enableMouseNavigation = true;
m_enableLimitedView = false;
m_movingInfoLayer = nullptr;
m_movingInfoLayer = NULL;
// Set margins to 0
m_marginTop = 0; m_marginRight = 0; m_marginBottom = 0; m_marginLeft = 0;
@@ -1932,10 +1914,10 @@ void mpWindow::OnMouseLeftRelease( wxMouseEvent& event )
m_zooming = false;
if( m_movingInfoLayer != nullptr )
if( m_movingInfoLayer != NULL )
{
m_movingInfoLayer->UpdateReference();
m_movingInfoLayer = nullptr;
m_movingInfoLayer = NULL;
}
else
{
@@ -1971,7 +1953,7 @@ void mpWindow::Fit( double xMin, double xMax, double yMin, double yMax,
yMin -= yExtra;
yMax += yExtra;
if( printSizeX != nullptr && printSizeY != nullptr )
if( printSizeX != NULL && printSizeY != NULL )
{
// Printer:
m_scrX = *printSizeX;
@@ -2012,7 +1994,7 @@ void mpWindow::Fit( double xMin, double xMax, double yMin, double yMax,
// It is VERY IMPORTANT to DO NOT call Refresh if we are drawing to the printer!!
// Otherwise, the DC dimensions will be those of the window instead of the printer device
if( printSizeX == nullptr || printSizeY == nullptr )
if( printSizeX == NULL || printSizeY == NULL )
UpdateAll();
}
@@ -2652,7 +2634,7 @@ unsigned int mpWindow::CountLayers() const
mpLayer* mpWindow::GetLayer( int position ) const
{
if( ( position >= (int) m_layers.size() ) || position < 0 )
return nullptr;
return NULL;
return m_layers[position];
}
@@ -2666,7 +2648,7 @@ const mpLayer* mpWindow::GetLayerByName( const wxString& name ) const
return layer;
}
return nullptr; // Not found
return NULL; // Not found
}
@@ -2753,7 +2735,7 @@ mpInfoLayer* mpWindow::IsInsideInfoLayer( wxPoint& point )
}
}
return nullptr;
return NULL;
}
@@ -2833,8 +2815,7 @@ void mpWindow::SetColourTheme( const wxColour& bgColour, const wxColour& drawCol
IMPLEMENT_DYNAMIC_CLASS( mpFXYVector, mpFXY )
// Constructor
mpFXYVector::mpFXYVector( const wxString& name, int flags ) :
mpFXY( name, flags )
mpFXYVector::mpFXYVector( const wxString& name, int flags ) : mpFXY( name, flags )
{
m_index = 0;
m_minX = -1;
@@ -3038,8 +3019,7 @@ void mpText::Plot( wxDC& dc, mpWindow& w )
// mpPrintout - provided by Davide Rondini
// -----------------------------------------------------------------------------
mpPrintout::mpPrintout( mpWindow* drawWindow, const wxChar* title ) :
wxPrintout( title )
mpPrintout::mpPrintout( mpWindow* drawWindow, const wxChar* title ) : wxPrintout( title )
{
drawn = false;
plotWindow = drawWindow;
@@ -3098,9 +3078,9 @@ bool mpPrintout::OnPrintPage( int page )
// Restore colours
plotWindow->SetColourTheme( oldBgColour, oldFgColour, oldAxColour );
// Restore drawing
plotWindow->Fit( plotWindow->GetDesiredXmin(), plotWindow->GetDesiredXmax(),
plotWindow->GetDesiredYmin(), plotWindow->GetDesiredYmax(), nullptr,
nullptr );
plotWindow->Fit( plotWindow->GetDesiredXmin(),
plotWindow->GetDesiredXmax(), plotWindow->GetDesiredYmin(),
plotWindow->GetDesiredYmax(), NULL, NULL );
plotWindow->UpdateAll();
}
+44 -67
View File
@@ -65,6 +65,8 @@ PROPERTIES_PANEL::PROPERTIES_PANEL( wxWindow* aParent, EDA_BASE_FRAME* aFrame )
delete wxPGGlobalVars->m_defaultRenderer;
wxPGGlobalVars->m_defaultRenderer = new PG_CELL_RENDERER();
m_cachedSelection = std::make_unique<SELECTION>();
m_caption = new wxStaticText( this, wxID_ANY, _( "No objects selected" ) );
mainSizer->Add( m_caption, 0, wxALL | wxEXPAND, 5 );
@@ -72,7 +74,6 @@ PROPERTIES_PANEL::PROPERTIES_PANEL( wxWindow* aParent, EDA_BASE_FRAME* aFrame )
wxPG_DEFAULT_STYLE );
m_grid->SetUnspecifiedValueAppearance( wxPGCell( wxT( "<...>" ) ) );
m_grid->SetExtraStyle( wxPG_EX_HELP_AS_TOOLTIPS );
m_grid->SetValidationFailureBehavior( wxPG_VFB_MARK_CELL );
m_grid->AddActionTrigger( wxPG_ACTION_NEXT_PROPERTY, WXK_RETURN );
m_grid->AddActionTrigger( wxPG_ACTION_NEXT_PROPERTY, WXK_NUMPAD_ENTER );
m_grid->AddActionTrigger( wxPG_ACTION_NEXT_PROPERTY, WXK_DOWN );
@@ -130,20 +131,23 @@ void PROPERTIES_PANEL::OnLanguageChanged()
void PROPERTIES_PANEL::rebuildProperties( const SELECTION& aSelection )
{
auto reset =
[&]()
{
if( m_grid->IsEditorFocused() )
m_grid->CommitChangesFromEditor();
if( *m_cachedSelection == aSelection )
{
updatePropertyValues( aSelection );
return;
}
m_grid->Clear();
m_displayed.clear();
};
*m_cachedSelection = aSelection;
if( m_grid->IsEditorFocused() )
m_grid->CommitChangesFromEditor();
m_grid->Clear();
m_displayed.clear();
if( aSelection.Empty() )
{
m_caption->SetLabel( _( "No objects selected" ) );
reset();
return;
}
@@ -155,6 +159,15 @@ void PROPERTIES_PANEL::rebuildProperties( const SELECTION& aSelection )
wxCHECK( !types.empty(), /* void */ );
if( aSelection.Size() > 1 )
{
m_caption->SetLabel( wxString::Format( _( "%d objects selected" ), aSelection.Size() ) );
}
else
{
m_caption->SetLabel( aSelection.Front()->GetFriendlyName() );
}
PROPERTY_MANAGER& propMgr = PROPERTY_MANAGER::Instance();
propMgr.SetUnits( m_frame->GetUserUnits() );
propMgr.SetTransforms( &m_frame->GetOriginTransforms() );
@@ -168,7 +181,8 @@ void PROPERTIES_PANEL::rebuildProperties( const SELECTION& aSelection )
std::vector<wxString> groupDisplayOrder = propMgr.GetGroupDisplayOrder( *types.begin() );
std::set<wxString> groups( groupDisplayOrder.begin(), groupDisplayOrder.end() );
std::set<PROPERTY_BASE*> availableProps;
std::map<wxPGProperty*, int> pgPropOrders;
std::map<wxString, std::vector<wxPGProperty*>> pgPropGroups;
// Get all possible properties
for( const TYPE_ID& type : types )
@@ -200,77 +214,40 @@ void PROPERTIES_PANEL::rebuildProperties( const SELECTION& aSelection )
}
}
EDA_ITEM* firstItem = aSelection.Front();
// Find a set of properties that is common to all selected items
for( PROPERTY_BASE* property : commonProps )
{
if( property->IsHiddenFromPropertiesManager() )
if( property->IsInternal() )
continue;
if( propMgr.IsAvailableFor( TYPE_HASH( *firstItem ), property, firstItem ) )
availableProps.insert( property );
}
bool writeable = true;
std::set<PROPERTY_BASE*> existingProps;
for( wxPropertyGridIterator it = m_grid->GetIterator(); !it.AtEnd(); it.Next() )
{
wxPGProperty* pgProp = it.GetProperty();
PROPERTY_BASE* property = propMgr.GetProperty( TYPE_HASH( *firstItem ), pgProp->GetName() );
// Switching item types? Property may no longer be valid
if( !property )
if( !propMgr.IsAvailableFor( TYPE_HASH( *aSelection.Front() ), property,
aSelection.Front() ) )
continue;
// Either determine the common value for a property or "<...>" to indicate multiple values
bool available;
bool writeable;
wxVariant commonVal;
extractValueAndWritability( aSelection, property, commonVal, writeable );
pgProp->SetValue( commonVal );
pgProp->Enable( writeable );
available = extractValueAndWritability( aSelection, property, commonVal, writeable );
existingProps.insert( property );
}
if( existingProps == availableProps )
return;
// Some difference exists: start from scratch
reset();
std::map<wxPGProperty*, int> pgPropOrders;
std::map<wxString, std::vector<wxPGProperty*>> pgPropGroups;
for( PROPERTY_BASE* property : availableProps )
{
wxPGProperty* pgProp = createPGProperty( property );
wxVariant commonVal;
if( !extractValueAndWritability( aSelection, property, commonVal, writeable ) )
continue;
if( pgProp )
if( available )
{
pgProp->SetValue( commonVal );
pgProp->Enable( writeable );
m_displayed.push_back( property );
wxPGProperty* pgProp = createPGProperty( property );
wxASSERT( displayOrder.count( property ) );
pgPropOrders[pgProp] = displayOrder[property];
pgPropGroups[property->Group()].emplace_back( pgProp );
if( pgProp )
{
pgProp->SetValue( commonVal );
pgProp->Enable( writeable );
m_displayed.push_back( property );
wxASSERT( displayOrder.count( property ) );
pgPropOrders[pgProp] = displayOrder[property];
pgPropGroups[property->Group()].emplace_back( pgProp );
}
}
}
if( aSelection.Size() > 1 )
{
m_caption->SetLabel( wxString::Format( _( "%d objects selected" ), aSelection.Size() ) );
}
else
{
m_caption->SetLabel( aSelection.Front()->GetFriendlyName() );
}
const wxString unspecifiedGroupCaption = _( "Basic Properties" );
for( const wxString& groupName : groupDisplayOrder )
+17
View File
@@ -75,10 +75,24 @@ protected:
/**
* Generates the property grid for a given selection of items.
*
* Calling this will remove any existing properties shown, causing visible flicker on some
* platforms and canceling any pending edits. Make sure to only call this when the group of
* selected items has actually changed.
*
* @param aSelection is a set of items to show properties for.
*/
virtual void rebuildProperties( const SELECTION& aSelection );
/**
* Updates the values shown in the property grid for the current selection.
*
* Does not add or remove properties from the display (@see rebuildProperties)
* This implies that aSelection must have the same contents as m_cachedSelection.
*
* @param aSelection is the set of selected items.
*/
virtual void updatePropertyValues( const SELECTION& aSelection ) {}
virtual wxPGProperty* createPGProperty( const PROPERTY_BASE* aProperty ) const = 0;
// Event handlers
@@ -114,6 +128,9 @@ protected:
/// Proportion of the grid column splitter that is used for the key column (0.0 - 1.0)
float m_splitter_key_proportion;
/// A copy of the most recent selection passed to rebuildProperties
std::unique_ptr<SELECTION> m_cachedSelection;
};
#endif /* PROPERTIES_PANEL_H */
+2 -4
View File
@@ -1,7 +1,7 @@
/*
* This program source code file is part of KiCad, a free EDA CAD application.
*
* Copyright (C) 2022-2023 KiCad Developers, see AUTHORS.txt for contributors.
* Copyright (C) 2022 KiCad Developers, see AUTHORS.txt for contributors.
*
* This program is free software: you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
@@ -42,8 +42,6 @@ void SEARCH_PANE::OnLanguageChange()
wxWindow* page = m_notebook->GetPage( i );
SEARCH_PANE_TAB* tab = dynamic_cast<SEARCH_PANE_TAB*>( page );
wxCHECK( tab, /* void */ );
tab->RefreshColumnNames();
m_notebook->SetPageText( i, wxGetTranslation( tab->GetSearchHandler()->GetName() ) );
}
@@ -105,4 +103,4 @@ void SEARCH_PANE::OnNotebookPageChanged( wxBookCtrlEvent& aEvent )
SEARCH_PANE_TAB* SEARCH_PANE::GetCurrentTab() const
{
return dynamic_cast<SEARCH_PANE_TAB*>( m_notebook->GetCurrentPage() );
}
}
+11 -4
View File
@@ -46,6 +46,7 @@ UNIT_BINDER::UNIT_BINDER( EDA_DRAW_FRAME* aParent, wxStaticText* aLabel, wxWindo
UNIT_BINDER::UNIT_BINDER( UNITS_PROVIDER* aUnitsProvider, wxWindow* aEventSource,
wxStaticText* aLabel, wxWindow* aValueCtrl, wxStaticText* aUnitLabel,
bool aAllowEval, bool aBindFocusEvent ) :
m_eventSource( aEventSource ),
m_bindFocusEvent( aBindFocusEvent ),
m_label( aLabel ),
m_valueCtrl( aValueCtrl ),
@@ -98,10 +99,10 @@ UNIT_BINDER::UNIT_BINDER( UNITS_PROVIDER* aUnitsProvider, wxWindow* aEventSource
this );
}
if( aEventSource )
if( m_eventSource )
{
aEventSource->Connect( UNITS_CHANGED, wxCommandEventHandler( UNIT_BINDER::onUnitsChanged ),
nullptr, this );
m_eventSource->Connect( UNITS_CHANGED, wxCommandEventHandler( UNIT_BINDER::onUnitsChanged ),
nullptr, this );
}
}
@@ -114,6 +115,12 @@ UNIT_BINDER::~UNIT_BINDER()
this );
}
if( m_eventSource )
{
m_eventSource->Disconnect( UNITS_CHANGED, wxCommandEventHandler( UNIT_BINDER::onUnitsChanged ),
nullptr, this );
}
if( m_valueCtrl )
{
m_valueCtrl->Disconnect( wxEVT_SET_FOCUS, wxFocusEventHandler( UNIT_BINDER::onSetFocus ),
@@ -388,7 +395,7 @@ void UNIT_BINDER::SetValue( const wxString& aValue )
value += EDA_UNIT_UTILS::GetLabel( m_units, m_dataType );
}
if( textEntry )
textEntry->SetValue( value );
else if( staticText )
+1 -24
View File
@@ -273,7 +273,7 @@ void WX_GRID::DestroyTable( wxGridTableBase* aTable )
}
wxString WX_GRID::GetShownColumnsAsString()
wxString WX_GRID::GetShownColumns()
{
wxString shownColumns;
@@ -292,17 +292,6 @@ wxString WX_GRID::GetShownColumnsAsString()
}
std::bitset<64> WX_GRID::GetShownColumns()
{
std::bitset<64> shownColumns;
for( int ii = 0; ii < GetNumberCols(); ++ii )
shownColumns[ii] = IsColShown( ii );
return shownColumns;
}
void WX_GRID::ShowHideColumns( const wxString& shownColumns )
{
for( int i = 0; i < GetNumberCols(); ++i )
@@ -321,18 +310,6 @@ void WX_GRID::ShowHideColumns( const wxString& shownColumns )
}
void WX_GRID::ShowHideColumns( const std::bitset<64>& aShownColumns )
{
for( int ii = 0; ii < GetNumberCols(); ++ ii )
{
if( aShownColumns[ii] )
ShowCol( ii );
else
HideCol( ii );
}
}
void WX_GRID::DrawCornerLabel( wxDC& dc )
{
if( m_nativeColumnLabels )
+1 -1
View File
@@ -63,7 +63,7 @@ WX_INFOBAR::WX_INFOBAR( wxWindow* aParent, wxAuiManager* aMgr, wxWindowID aWinid
// Infobar is broken on Mac without the effects
SetShowHideEffects( wxSHOW_EFFECT_ROLL_TO_BOTTOM, wxSHOW_EFFECT_ROLL_TO_TOP );
SetEffectDuration( 200 );
SetEffectDuration( 300 );
#else
// Infobar freezes canvas on Windows with the effect, and GTK looks bad with it
SetShowHideEffects( wxSHOW_EFFECT_NONE, wxSHOW_EFFECT_NONE );
+3 -2
View File
@@ -38,8 +38,9 @@ SYMBOLS_LISTBOX::SYMBOLS_LISTBOX( CVPCB_MAINFRAME* parent, wxWindowID id ) :
ITEMS_LISTBOX_BASE( parent, id ),
m_warningAttr( std::make_unique<wxListItemAttr>() )
{
m_warningAttr->SetBackgroundColour( KIPLATFORM::UI::IsDarkTheme() ? wxColour( 112, 96, 32 )
: wxColour( 255, 248, 212 ) );
m_warningAttr->SetBackgroundColour( KIPLATFORM::UI::IsDarkTheme()
? wxColour( 112, 96, 32 )
: *wxYELLOW );
}
-3
View File
@@ -84,9 +84,6 @@ void CVPCB_MAINFRAME::ReCreateHToolbar()
m_tcFilterString = new wxTextCtrl( m_mainToolBar, wxID_ANY, wxEmptyString, wxDefaultPosition,
wxDefaultSize, wxTE_PROCESS_ENTER );
// Min size on Mac is (a not very useful) single character
m_tcFilterString->SetMinSize( wxSize( 150, -1 ) );
m_tcFilterString->Bind( wxEVT_TEXT_ENTER, &CVPCB_MAINFRAME::onTextFilterChanged, this );
m_mainToolBar->AddControl( m_tcFilterString );
+11 -108
View File
@@ -195,7 +195,7 @@ bool CONNECTION_SUBGRAPH::ResolveDrivers( bool aCheckMultipleDrivers )
m_driver_connection->SetDriver( m_driver );
m_driver_connection->ClearDirty();
}
else if( !m_is_bus_member )
else
{
m_driver_connection = nullptr;
}
@@ -246,36 +246,7 @@ wxString CONNECTION_SUBGRAPH::GetNetName() const
}
std::vector<SCH_ITEM*> CONNECTION_SUBGRAPH::GetAllBusLabels() const
{
std::vector<SCH_ITEM*> labels;
for( SCH_ITEM* item : m_drivers )
{
switch( item->Type() )
{
case SCH_LABEL_T:
case SCH_GLOBAL_LABEL_T:
{
CONNECTION_TYPE type = item->Connection( &m_sheet )->Type();
// Only consider bus vectors
if( type == CONNECTION_TYPE::BUS || type == CONNECTION_TYPE::BUS_GROUP )
labels.push_back( item );
break;
}
default:
break;
}
}
return labels;
}
std::vector<SCH_ITEM*> CONNECTION_SUBGRAPH::GetVectorBusLabels() const
std::vector<SCH_ITEM*> CONNECTION_SUBGRAPH::GetBusLabels() const
{
std::vector<SCH_ITEM*> labels;
@@ -1000,58 +971,6 @@ void CONNECTION_GRAPH::collectAllDriverValues()
}
void CONNECTION_GRAPH::generateBusAliasMembers()
{
std::vector<CONNECTION_SUBGRAPH*> new_subgraphs;
SCH_CONNECTION dummy( this );
for( auto&& subgraph : m_driver_subgraphs )
{
auto vec = subgraph->GetAllBusLabels();
for( auto& item : vec )
{
SCH_LABEL_BASE* label = static_cast<SCH_LABEL_BASE*>( item );
dummy.ConfigureFromLabel( label->GetText() );
wxLogTrace( ConnTrace, wxS( "new bus label (%s)" ), label->GetText() );
for( auto& conn : dummy.Members() )
{
wxString name = conn->FullLocalName();
CONNECTION_SUBGRAPH* new_sg = new CONNECTION_SUBGRAPH( this );
SCH_CONNECTION* new_conn = new SCH_CONNECTION( this );
new_conn->SetName( name );
new_conn->SetType( CONNECTION_TYPE::NET );
int code = assignNewNetCode( *new_conn );
wxLogTrace( ConnTrace, wxS( "SG(%ld), Adding full local name (%s) with sg (%d)" ), subgraph->m_code,
name, code );
new_sg->m_driver_connection = new_conn;
new_sg->m_code = m_last_subgraph_code++;
new_sg->m_sheet = subgraph->m_sheet;
new_sg->m_is_bus_member = true;
new_sg->m_strong_driver = true;
/// Need to figure out why these sgs are not getting connected to their bus parents
NET_NAME_CODE_CACHE_KEY key = { new_sg->GetNetName(), code };
m_net_code_to_subgraphs_map[ key ].push_back( new_sg );
m_net_name_to_subgraphs_map[ name ].push_back( new_sg );
m_subgraphs.push_back( new_sg );
new_subgraphs.push_back( new_sg );
}
}
}
std::copy( new_subgraphs.begin(), new_subgraphs.end(), std::back_inserter( m_driver_subgraphs ) );
}
void CONNECTION_GRAPH::generateInvisiblePinSubGraphs()
{
// Generate subgraphs for invisible power pins. These will be merged with other subgraphs
@@ -1196,7 +1115,7 @@ void CONNECTION_GRAPH::processSubGraphs()
name = new_name;
}
else if( subgraph->m_driver )
else
{
// If there is no conflict, promote sheet pins to be strong drivers so that they
// will be considered below for propagation/merging.
@@ -1436,8 +1355,7 @@ void CONNECTION_GRAPH::processSubGraphs()
if( subgraph->m_absorbed )
continue;
if( !subgraph->ResolveDrivers() )
continue;
subgraph->ResolveDrivers();
if( subgraph->m_driver_connection->IsBus() )
assignNetCodesToBus( subgraph->m_driver_connection );
@@ -1494,8 +1412,6 @@ void CONNECTION_GRAPH::buildConnectionGraph( std::function<void( SCH_ITEM* )>* a
generateInvisiblePinSubGraphs();
generateBusAliasMembers();
PROF_TIMER proc_sub_graph( "ProcessSubGraphs" );
processSubGraphs();
@@ -1694,7 +1610,7 @@ void CONNECTION_GRAPH::buildConnectionGraph( std::function<void( SCH_ITEM* )>* a
// As a visual aid, we can check sheet pins that are driven by themselves to see
// if they should be promoted to buses
if( subgraph->m_driver && subgraph->m_driver->Type() == SCH_SHEET_PIN_T )
if( subgraph->m_driver->Type() == SCH_SHEET_PIN_T )
{
SCH_SHEET_PIN* pin = static_cast<SCH_SHEET_PIN*>( subgraph->m_driver );
@@ -1773,8 +1689,6 @@ void CONNECTION_GRAPH::buildConnectionGraph( std::function<void( SCH_ITEM* )>* a
const CONNECTION_SUBGRAPH* driverSubgraph = nullptr;
wxString netclass;
wxCHECK_RET( !subgraphs.empty(), wxT("Invalid empty subgraph" ) );
for( const CONNECTION_SUBGRAPH* subgraph : subgraphs )
{
for( SCH_ITEM* item : subgraph->m_items )
@@ -1785,7 +1699,7 @@ void CONNECTION_GRAPH::buildConnectionGraph( std::function<void( SCH_ITEM* )>* a
break;
}
if( !netclass.IsEmpty() )
if( !netclass.IsEmpty() || !driverSubgraph )
{
driverSubgraph = subgraph;
break;
@@ -1795,9 +1709,6 @@ void CONNECTION_GRAPH::buildConnectionGraph( std::function<void( SCH_ITEM* )>* a
if( netclass.IsEmpty() )
return;
if( !driverSubgraph )
driverSubgraph = subgraphs.front();
const wxString netname = driverSubgraph->GetNetName();
if( driverSubgraph->m_driver_connection->IsBus() )
@@ -1824,30 +1735,22 @@ void CONNECTION_GRAPH::buildConnectionGraph( std::function<void( SCH_ITEM* )>* a
}
int CONNECTION_GRAPH::getOrCreateNetCode( const wxString& aNetName )
int CONNECTION_GRAPH::assignNewNetCode( SCH_CONNECTION& aConnection )
{
int code;
auto it = m_net_name_to_code_map.find( aNetName );
auto it = m_net_name_to_code_map.find( aConnection.Name() );
if( it == m_net_name_to_code_map.end() )
{
code = m_last_net_code++;
m_net_name_to_code_map[ aNetName ] = code;
m_net_name_to_code_map[ aConnection.Name() ] = code;
}
else
{
code = it->second;
}
return code;
}
int CONNECTION_GRAPH::assignNewNetCode( SCH_CONNECTION& aConnection )
{
int code = getOrCreateNetCode( aConnection.Name() );
aConnection.SetNetCode( code );
return code;
@@ -1856,7 +1759,7 @@ int CONNECTION_GRAPH::assignNewNetCode( SCH_CONNECTION& aConnection )
void CONNECTION_GRAPH::assignNetCodesToBus( SCH_CONNECTION* aConnection )
{
std::vector<std::shared_ptr<SCH_CONNECTION>> connections_to_check( aConnection->Members() );
std::vector< std::shared_ptr<SCH_CONNECTION>>& connections_to_check( aConnection->Members() );
for( unsigned i = 0; i < connections_to_check.size(); i++ )
{
@@ -2327,7 +2230,7 @@ std::vector<const CONNECTION_SUBGRAPH*> CONNECTION_GRAPH::GetBusesNeedingMigrati
if( !connection->IsBus() )
continue;
auto labels = subgraph->GetVectorBusLabels();
auto labels = subgraph->GetBusLabels();
if( labels.size() > 1 )
{
+2 -24
View File
@@ -76,7 +76,6 @@ public:
m_graph( aGraph ),
m_dirty( false ),
m_absorbed( false ),
m_is_bus_member( false ),
m_absorbed_by( nullptr ),
m_code( -1 ),
m_multiple_drivers( false ),
@@ -109,11 +108,8 @@ public:
*/
wxString GetNetName() const;
/// Returns all the vector-based bus labels attached to this subgraph (if any)
std::vector<SCH_ITEM*> GetVectorBusLabels() const;
/// Returns all the all bus labels attached to this subgraph (if any)
std::vector<SCH_ITEM*> GetAllBusLabels() const;
/// Returns all the bus labels attached to this subgraph (if any)
std::vector<SCH_ITEM*> GetBusLabels() const;
/// Returns the candidate net name for a driver
const wxString& GetNameForDriver( SCH_ITEM* aItem ) const;
@@ -164,12 +160,6 @@ public:
/// True if this subgraph has been absorbed into another. No pointers here are safe if so!
bool m_absorbed;
/**
* True if the subgraph is not actually part of a net. These are created for bus members
* to ensure that bus-to-bus connection happens but they don't have any valid data
*/
bool m_is_bus_member;
/// If this subgraph is absorbed, points to the absorbing (and valid) subgraph
CONNECTION_SUBGRAPH* m_absorbed_by;
@@ -431,11 +421,6 @@ private:
*/
void generateInvisiblePinSubGraphs();
/**
* Iterate through labels to create placeholders for bus elements
*/
void generateBusAliasMembers();
/**
* Process all subgraphs to assign netcodes and merge subgraphs based on labels
*/
@@ -448,13 +433,6 @@ private:
*/
int assignNewNetCode( SCH_CONNECTION& aConnection );
/**
*
* @param aNetName string with the netname for coding
* @return existing netcode (if it exists) or newly created one
*/
int getOrCreateNetCode( const wxString& aNetName );
/**
* Ensures all members of the bus connection have a valid net code assigned
* @param aConnection is a bus connection
-4
View File
@@ -947,10 +947,6 @@ void SCH_EDIT_FRAME::KiwayMailIn( KIWAY_EXPRESS& mail )
m_toolManager->RunAction( ACTIONS::updateSchematicFromPcb, true );
break;
case MAIL_RELOAD_LIB:
SyncView();
break;
default:;
}
+1 -1
View File
@@ -132,7 +132,7 @@ DIALOG_ANNOTATE::~DIALOG_ANNOTATE()
if( projSettings.m_AnnotateStartNum != startNum )
{
projSettings.m_AnnotateStartNum = startNum;
schFrame->OnModify();
schFrame->SaveProjectSettings();
}
}
}
+12 -12
View File
@@ -512,18 +512,21 @@ int DIALOG_CHANGE_SYMBOLS::processMatchingSymbols()
int DIALOG_CHANGE_SYMBOLS::processSymbols( const std::map<SCH_SYMBOL*,
SYMBOL_CHANGE_INFO>& aSymbols )
SYMBOL_CHANGE_INFO>& aSymbols )
{
wxCHECK( !aSymbols.empty(), 0 );
int matchesProcessed = 0;
SCH_EDIT_FRAME* frame = dynamic_cast<SCH_EDIT_FRAME*>( GetParent() );
wxString msg;
SCH_SCREEN* screen = nullptr;
LIB_SYMBOL* libSymbol = nullptr;
std::map<SCH_SYMBOL*, SYMBOL_CHANGE_INFO> symbols = aSymbols;
wxCHECK( frame, 0 );
std::map<SCH_SYMBOL*, SYMBOL_CHANGE_INFO> symbols = aSymbols;
std::map<SCH_SYMBOL*, SYMBOL_CHANGE_INFO>::iterator it = symbols.begin();
wxString msg;
auto it = symbols.begin();
// Remove all symbols that don't have a valid library symbol link or enough units to
// satify the library symbol update.
@@ -533,7 +536,7 @@ int DIALOG_CHANGE_SYMBOLS::processSymbols( const std::map<SCH_SYMBOL*,
wxCHECK2( symbol && it->second.m_LibId.IsValid(), continue );
LIB_SYMBOL* libSymbol = frame->GetLibSymbol( it->second.m_LibId );
libSymbol = frame->GetLibSymbol( it->second.m_LibId );
if( !libSymbol )
{
@@ -559,21 +562,18 @@ int DIALOG_CHANGE_SYMBOLS::processSymbols( const std::map<SCH_SYMBOL*,
}
}
bool appendUndo = false;
// Removing the symbol needs to be done before the LIB_SYMBOL is changed to prevent stale
// library symbols in the schematic file.
for( const auto& [ symbol, symbol_change_info ] : symbols )
{
wxCHECK( symbol && !symbol_change_info.m_Instances.empty(), 0 );
SCH_SCREEN* screen = symbol_change_info.m_Instances[0].LastScreen();
screen = symbol_change_info.m_Instances[0].LastScreen();
wxCHECK( screen, 0 );
screen->Remove( symbol );
frame->SaveCopyInUndoList( screen, symbol, UNDO_REDO::CHANGED, appendUndo );
appendUndo = true;
frame->SaveCopyInUndoList( screen, symbol, UNDO_REDO::CHANGED, true );
}
for( const auto& [ symbol, symbol_change_info ] : symbols )
@@ -581,9 +581,8 @@ int DIALOG_CHANGE_SYMBOLS::processSymbols( const std::map<SCH_SYMBOL*,
if( symbol_change_info.m_LibId != symbol->GetLibId() )
symbol->SetLibId( symbol_change_info.m_LibId );
LIB_SYMBOL* libSymbol = frame->GetLibSymbol( symbol_change_info.m_LibId );
libSymbol = frame->GetLibSymbol( symbol_change_info.m_LibId );
std::unique_ptr<LIB_SYMBOL> flattenedSymbol = libSymbol->Flatten();
SCH_SCREEN* screen = symbol_change_info.m_Instances[0].LastScreen();
symbol->SetLibSymbol( flattenedSymbol.release() );
@@ -697,6 +696,7 @@ int DIALOG_CHANGE_SYMBOLS::processSymbols( const std::map<SCH_SYMBOL*,
}
symbol->SetSchSymbolLibraryName( wxEmptyString );
screen = symbol_change_info.m_Instances[0].LastScreen();
screen->Append( symbol );
frame->GetCanvas()->GetView()->Update( symbol );
+13 -28
View File
@@ -129,7 +129,7 @@ private:
void InstallPageSpiceModel();
bool TransferDataFromWindow() override;
bool NetlistUpdateOpt();
void NetlistUpdateOpt();
void updateGeneratorButtons();
@@ -254,7 +254,7 @@ DIALOG_EXPORT_NETLIST::DIALOG_EXPORT_NETLIST( SCH_EDIT_FRAME* parent ) :
SCHEMATIC_SETTINGS& settings = m_Parent->Schematic().Settings();
for( EXPORT_NETLIST_PAGE*& page : m_PanelNetType )
for( EXPORT_NETLIST_PAGE*& page : m_PanelNetType)
page = nullptr;
// Add notebook pages:
@@ -463,35 +463,22 @@ void DIALOG_EXPORT_NETLIST::OnNetlistTypeSelection( wxNotebookEvent& event )
}
bool DIALOG_EXPORT_NETLIST::NetlistUpdateOpt()
void DIALOG_EXPORT_NETLIST::NetlistUpdateOpt()
{
bool changed = false;
bool saveAllVoltages = m_PanelNetType[ PANELSPICE ]->m_SaveAllVoltages->IsChecked();
bool saveAllCurrents = m_PanelNetType[ PANELSPICE ]->m_SaveAllCurrents->IsChecked();
bool saveAllVoltages = m_PanelNetType[ PANELSPICE ]->m_SaveAllVoltages->IsChecked();
bool saveAllCurrents = m_PanelNetType[ PANELSPICE ]->m_SaveAllCurrents->IsChecked();
wxString spiceCmdString = m_PanelNetType[ PANELSPICE ]->m_CommandStringCtrl->GetValue();
bool curSheetAsRoot = m_PanelNetType[ PANELSPICE ]->m_CurSheetAsRoot->GetValue();
bool spiceModelCurSheetAsRoot = m_PanelNetType[ PANELSPICEMODEL ]->m_CurSheetAsRoot->GetValue();
SCHEMATIC_SETTINGS& settings = m_Parent->Schematic().Settings();
wxString netFormatName = m_PanelNetType[m_NoteBook->GetSelection()]->GetPageNetFmtName();
changed |= ( settings.m_SpiceSaveAllVoltages != saveAllVoltages );
changed |= ( settings.m_SpiceSaveAllCurrents != saveAllCurrents );
changed |= ( settings.m_SpiceCommandString != spiceCmdString );
changed |= ( settings.m_SpiceCurSheetAsRoot != curSheetAsRoot );
changed |= ( settings.m_SpiceModelCurSheetAsRoot != spiceModelCurSheetAsRoot );
changed |= ( settings.m_NetFormatName != netFormatName );
settings.m_SpiceSaveAllVoltages = saveAllVoltages;
settings.m_SpiceSaveAllCurrents = saveAllCurrents;
settings.m_SpiceCommandString = spiceCmdString;
settings.m_SpiceCurSheetAsRoot = curSheetAsRoot;
settings.m_SpiceSaveAllVoltages = saveAllVoltages;
settings.m_SpiceSaveAllCurrents = saveAllCurrents;
settings.m_SpiceCommandString = spiceCmdString;
settings.m_SpiceCurSheetAsRoot = curSheetAsRoot;
settings.m_SpiceModelCurSheetAsRoot = spiceModelCurSheetAsRoot;
settings.m_NetFormatName = netFormatName;
return changed;
settings.m_NetFormatName = m_PanelNetType[m_NoteBook->GetSelection()]->GetPageNetFmtName();
}
@@ -502,8 +489,7 @@ bool DIALOG_EXPORT_NETLIST::TransferDataFromWindow()
wxString fileExt;
wxString title = _( "Save Netlist File" );
if( NetlistUpdateOpt() )
m_Parent->OnModify();
NetlistUpdateOpt();
EXPORT_NETLIST_PAGE* currPage;
currPage = (EXPORT_NETLIST_PAGE*) m_NoteBook->GetCurrentPage();
@@ -635,8 +621,7 @@ bool DIALOG_EXPORT_NETLIST::FilenamePrms( NETLIST_TYPE_ID aType, wxString * aExt
void DIALOG_EXPORT_NETLIST::WriteCurrentNetlistSetup()
{
if( NetlistUpdateOpt() )
m_Parent->OnModify();
NetlistUpdateOpt();
EESCHEMA_SETTINGS* cfg = dynamic_cast<EESCHEMA_SETTINGS*>( Kiface().KifaceSettings() );
wxASSERT( cfg );
@@ -813,7 +798,7 @@ int InvokeDialogNetList( SCH_EDIT_FRAME* aCaller )
DIALOG_EXPORT_NETLIST dlg( aCaller );
int ret = dlg.ShowModal();
aCaller->SaveProjectLocalSettings();
aCaller->SaveProjectSettings();
return ret;
}
@@ -157,8 +157,6 @@ void DIALOG_FIELD_PROPERTIES::init()
// Predefined fields cannot contain some chars, or cannot be empty,
// and need a SCH_FIELD_VALIDATOR (m_StyledTextCtrl cannot use a SCH_FIELD_VALIDATOR).
// VALUE_FIELD does not use the validator so that it uses the Scintilla text control, since we
// allow text replacement for this field (but not the other predefined fields)
bool use_validator = m_fieldId == REFERENCE_FIELD
|| m_fieldId == FOOTPRINT_FIELD
|| m_fieldId == DATASHEET_FIELD
@@ -191,12 +189,10 @@ void DIALOG_FIELD_PROPERTIES::init()
"cannot be changed." ) ) );
m_note->Show( true );
m_TextCtrl->Enable( false );
m_StyledTextCtrl->Enable( false );
}
else
{
m_TextCtrl->Enable( true );
m_StyledTextCtrl->Enable( true );
}
GetSizer()->SetSizeHints( this );
@@ -489,16 +489,6 @@ void DIALOG_GLOBAL_EDIT_TEXT_AND_GRAPHICS::visitItem( const SCH_SHEET_PATH& aShe
processItem( aSheetPath, pin );
}
}
else if( m_wires->GetValue() && aItem->IsType( { SCH_ITEM_LOCATE_WIRE_T,
SCH_LABEL_LOCATE_WIRE_T } ) )
{
processItem( aSheetPath, aItem );
}
else if( m_buses->GetValue() && aItem->IsType( { SCH_ITEM_LOCATE_BUS_T,
SCH_LABEL_LOCATE_BUS_T } ) )
{
processItem( aSheetPath, aItem );
}
else if( aItem->IsType( { SCH_LABEL_LOCATE_ANY_T } ) )
{
if( m_globalLabels->GetValue() && aItem->Type() == SCH_GLOBAL_LABEL_T )
@@ -539,6 +529,16 @@ void DIALOG_GLOBAL_EDIT_TEXT_AND_GRAPHICS::visitItem( const SCH_SHEET_PATH& aShe
}
}
}
else if( m_wires->GetValue() && aItem->IsType( { SCH_ITEM_LOCATE_WIRE_T,
SCH_LABEL_LOCATE_WIRE_T } ) )
{
processItem( aSheetPath, aItem );
}
else if( m_buses->GetValue() && aItem->IsType( { SCH_ITEM_LOCATE_BUS_T,
SCH_LABEL_LOCATE_BUS_T } ) )
{
processItem( aSheetPath, aItem );
}
else if( m_schTextAndGraphics->GetValue() && aItem->IsType( { SCH_TEXT_T, SCH_TEXTBOX_T,
SCH_ITEM_LOCATE_GRAPHIC_LINE_T,
SCH_SHAPE_T } ) )
@@ -1,5 +1,5 @@
///////////////////////////////////////////////////////////////////////////
// C++ code generated with wxFormBuilder (version 3.10.1-282-g1fa54006)
// C++ code generated with wxFormBuilder (version 3.10.1-0-g8feb16b)
// http://www.wxformbuilder.org/
//
// PLEASE DO *NOT* EDIT THIS FILE!
@@ -79,6 +79,7 @@ DIALOG_IMAGE_PROPERTIES_BASE::DIALOG_IMAGE_PROPERTIES_BASE( wxWindow* parent, wx
this->SetSizer( m_GeneralBoxSizer );
this->Layout();
m_GeneralBoxSizer->Fit( this );
this->Centre( wxBOTH );
}
@@ -36,7 +36,6 @@
<property name="center">wxBOTH</property>
<property name="context_help"></property>
<property name="context_menu">1</property>
<property name="drag_accept_files">0</property>
<property name="enabled">1</property>
<property name="event_handler">impl_virtual</property>
<property name="extra_style"></property>
@@ -48,8 +47,8 @@
<property name="minimum_size"></property>
<property name="name">DIALOG_IMAGE_PROPERTIES_BASE</property>
<property name="pos"></property>
<property name="size">363,281</property>
<property name="style">wxDEFAULT_DIALOG_STYLE|wxRESIZE_BORDER</property>
<property name="size"></property>
<property name="style">wxDEFAULT_DIALOG_STYLE</property>
<property name="subclass">DIALOG_SHIM; dialog_shim.h; forward_declare</property>
<property name="title"></property>
<property name="tooltip"></property>
@@ -88,7 +87,6 @@
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="drag_accept_files">0</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>
@@ -145,7 +143,6 @@
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="drag_accept_files">0</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>
@@ -234,7 +231,6 @@
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="drag_accept_files">0</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>
@@ -296,7 +292,6 @@
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="drag_accept_files">0</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>
@@ -361,7 +356,6 @@
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="drag_accept_files">0</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>
@@ -423,7 +417,6 @@
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="drag_accept_files">0</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>
@@ -485,7 +478,6 @@
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="drag_accept_files">0</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>
@@ -550,7 +542,6 @@
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="drag_accept_files">0</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>

Some files were not shown because too many files have changed in this diff Show More