1 /*
2 * This program source code file is part of KiCad, a free EDA CAD application.
3 *
4 * Copyright (C) 1992-2020 KiCad Developers, see AUTHORS.txt for contributors.
5 *
6 * This program is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU General Public License
8 * as published by the Free Software Foundation; either version 2
9 * of the License, or (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, you may find one here:
18 * http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
19 * or you may search the http://www.gnu.org website for the version 2 license,
20 * or you may write to the Free Software Foundation, Inc.,
21 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
22 */
23
24 #include <pgm_base.h>
25 #include <kiface_base.h>
26 #include <confirm.h>
27 #include <pcb_edit_frame.h>
28 #include <eda_dde.h>
29 #include <wx/file.h>
30 #include <wx/snglinst.h>
31 #include <wx/app.h>
32 #include <board.h>
33 #include <fp_lib_table.h>
34 #include <footprint_viewer_frame.h>
35 #include <footprint_wizard_frame.h>
36 #include <footprint.h>
37 #include <tools/pcb_actions.h>
38 #include <router/router_tool.h>
39 #include <dialog_find.h>
40 #include <dialog_filter_selection.h>
41
42 FP_LIB_TABLE GFootprintTable;
43
44
45 #if 0
46
47 static struct IFACE : public KIFACE_BASE
48 {
49 // Of course all are overloads, implementations of the KIFACE.
50
51 IFACE( const char* aName, KIWAY::FACE_T aType ) :
52 KIFACE_BASE( aName, aType )
53 {}
54
55 bool OnKifaceStart( PGM_BASE* aProgram, int aCtlBits ) override
56 {
57 return true;
58 }
59
60 void OnKifaceEnd() override {}
61
62 wxWindow* CreateWindow( wxWindow* aParent, int aClassId, KIWAY* aKiway, int aCtlBits = 0 ) override
63 {
64 assert( false );
65 return nullptr;
66 }
67
68 /**
69 * Function IfaceOrAddress
70 * return a pointer to the requested object. The safest way to use this
71 * is to retrieve a pointer to a static instance of an interface, similar to
72 * how the KIFACE interface is exported. But if you know what you are doing
73 * use it to retrieve anything you want.
74 *
75 * @param aDataId identifies which object you want the address of.
76 *
77 * @return void* - and must be cast into the know type.
78 */
79 void* IfaceOrAddress( int aDataId ) override
80 {
81 return NULL;
82 }
83 }
84 kiface( "pcb_test_frame", KIWAY::FACE_PCB );
85
86 static struct PGM_TEST_FRAME : public PGM_BASE
87 {
88 bool OnPgmInit();
89
90 void OnPgmExit()
91 {
92 Kiway.OnKiwayEnd();
93
94 // Destroy everything in PGM_BASE, especially wxSingleInstanceCheckerImpl
95 // earlier than wxApp and earlier than static destruction would.
96 PGM_BASE::Destroy();
97 }
98
99 void MacOpenFile( const wxString& aFileName ) override
100 {
101 wxFileName filename( aFileName );
102
103 if( filename.FileExists() )
104 {
105 #if 0
106 // this pulls in EDA_DRAW_FRAME type info, which we don't want in
107 // the single_top link image.
108 KIWAY_PLAYER* frame = dynamic_cast<KIWAY_PLAYER*>( App().GetTopWindow() );
109 #else
110 KIWAY_PLAYER* frame = (KIWAY_PLAYER*) App().GetTopWindow();
111 #endif
112
113 if( frame )
114 frame->OpenProjectFiles( std::vector<wxString>( 1, aFileName ) );
115 }
116 }
117 }
118 program;
119
120 PGM_BASE& Pgm()
121 {
122 return program;
123 }
124
125
126 // Similar to PGM_BASE& Pgm(), but return nullptr when a *.ki_face
127 // is run from a python script, mot from a Kicad application
128 PGM_BASE* PgmOrNull()
129 {
130 return nullptr; //&program;
131 }
132
133
134 KIFACE_BASE& Kiface()
135 {
136 return kiface;
137 }
138 #endif
139
140 // FP_LIB_TABLE GFootprintTable;
141
DIALOG_FIND(PCB_BASE_FRAME * aParent)142 DIALOG_FIND::DIALOG_FIND( PCB_BASE_FRAME* aParent ) : DIALOG_FIND_BASE( aParent )
143 {
144 // these members are initialized to avoid warnings about non initialized vars
145 m_frame = aParent;
146 m_hitList.clear();
147 m_it = m_hitList.begin();
148 m_upToDate = false;
149 }
150
onFindNextClick(wxCommandEvent & aEvent)151 void DIALOG_FIND::onFindNextClick( wxCommandEvent& aEvent )
152 {
153 }
154
onFindPreviousClick(wxCommandEvent & aEvent)155 void DIALOG_FIND::onFindPreviousClick( wxCommandEvent& aEvent )
156 {
157 }
158
onSearchAgainClick(wxCommandEvent & aEvent)159 void DIALOG_FIND::onSearchAgainClick( wxCommandEvent& aEvent )
160 {
161 }
162
onTextEnter(wxCommandEvent & event)163 void DIALOG_FIND::onTextEnter( wxCommandEvent& event )
164 {
165 }
166
OnCloseButtonClick(wxCommandEvent & aEvent)167 void DIALOG_FIND::OnCloseButtonClick( wxCommandEvent& aEvent )
168 {
169 }
170
Show(bool show)171 bool DIALOG_FIND::Show( bool show )
172 {
173 return true;
174 }
175
OnClose(wxCloseEvent & aEvent)176 void DIALOG_FIND::OnClose( wxCloseEvent& aEvent )
177 {
178 }
179
180
DIALOG_FIND_BASE(wxWindow * parent,wxWindowID id,const wxString & title,const wxPoint & pos,const wxSize & size,long style)181 DIALOG_FIND_BASE::DIALOG_FIND_BASE( wxWindow* parent, wxWindowID id, const wxString& title,
182 const wxPoint& pos, const wxSize& size, long style ) :
183 DIALOG_SHIM( parent, id, title, pos, size, style )
184 {
185 // these members are initialized only to avoid warnings about non initialized vars
186 searchStringLabel = nullptr;
187 m_searchCombo = nullptr;
188 m_matchCase = nullptr;
189 m_matchWords = nullptr;
190 m_wildcards = nullptr;
191 m_wrap = nullptr;
192 m_includeValues = nullptr;
193 m_includeReferences = nullptr;
194 m_includeTexts = nullptr;
195 m_includeMarkers = nullptr;
196 m_includeVias = nullptr;
197 m_findNext = nullptr;
198 m_findPrevious = nullptr;
199 m_searchAgain = nullptr;
200 m_closeButton = nullptr;
201 m_status = nullptr;
202 }
203
204
~DIALOG_FIND_BASE()205 DIALOG_FIND_BASE::~DIALOG_FIND_BASE()
206 {
207 }
208
209
GetFootprintFromBoardByReference()210 FOOTPRINT* PCB_BASE_FRAME::GetFootprintFromBoardByReference()
211 {
212 return nullptr;
213 }
214
215
DIALOG_FILTER_SELECTION_BASE(wxWindow * parent,wxWindowID id,const wxString & title,const wxPoint & pos,const wxSize & size,long style)216 DIALOG_FILTER_SELECTION_BASE::DIALOG_FILTER_SELECTION_BASE( wxWindow* parent, wxWindowID id,
217 const wxString& title,
218 const wxPoint& pos, const wxSize& size,
219 long style ) :
220 DIALOG_SHIM( parent, id, title, pos, size, style )
221 {
222 // these members are initialized only to avoid warnings about non initialized vars
223 m_Include_Modules = nullptr;
224 m_Include_PcbTexts = nullptr;
225 m_IncludeLockedModules = nullptr;
226 m_Include_Draw_Items = nullptr;
227 m_Include_Tracks = nullptr;
228 m_Include_Vias = nullptr;
229 m_Include_Edges_Items = nullptr;
230 m_Include_Zones = nullptr;
231 m_sdbSizer1 = nullptr;
232 m_staticLine = nullptr;
233 m_sdbSizer1OK = nullptr;
234 m_sdbSizer1Cancel = nullptr;
235 }
236
237
~DIALOG_FILTER_SELECTION_BASE()238 DIALOG_FILTER_SELECTION_BASE::~DIALOG_FILTER_SELECTION_BASE()
239 {
240 }
241
242
DIALOG_FILTER_SELECTION(PCB_BASE_FRAME * aParent,OPTIONS & aOptions)243 DIALOG_FILTER_SELECTION::DIALOG_FILTER_SELECTION( PCB_BASE_FRAME* aParent, OPTIONS& aOptions ) :
244 DIALOG_FILTER_SELECTION_BASE( aParent ),
245 m_options( aOptions )
246 {
247 // silence another compiler warning about m_options not being used
248 if( m_options.includeModules )
249 {
250 }
251 }
252
253
checkBoxClicked(wxCommandEvent & aEvent)254 void DIALOG_FILTER_SELECTION::checkBoxClicked( wxCommandEvent& aEvent )
255 {
256 }
257
258
allItemsClicked(wxCommandEvent & aEvent)259 void DIALOG_FILTER_SELECTION::allItemsClicked( wxCommandEvent& aEvent )
260 {
261 }
262
263
TransferDataFromWindow()264 bool DIALOG_FILTER_SELECTION::TransferDataFromWindow()
265 {
266 return true;
267 }
268
269
NeighboringSegmentFilter(const VECTOR2I &,GENERAL_COLLECTOR &)270 void ROUTER_TOOL::NeighboringSegmentFilter( const VECTOR2I&, GENERAL_COLLECTOR& )
271 {
272 }
273
274
275
276 #include <tools/pcb_selection_tool.h>
277
278
279 /**
280 * Private implementation of firewalled private data
281 */
282 class PCB_SELECTION_TOOL::PRIV
283 {
284 public:
285 DIALOG_FILTER_SELECTION::OPTIONS m_filterOpts;
286 };
287
288
PCB_SELECTION_TOOL()289 PCB_SELECTION_TOOL::PCB_SELECTION_TOOL() :
290 PCB_TOOL_BASE( "pcbnew.InteractiveSelection" ),
291 m_frame( NULL ),
292 m_enteredGroup( NULL ),
293 m_nonModifiedCursor( KICURSOR::ARROW ),
294 m_priv( nullptr )
295 {
296 }
297
298
~PCB_SELECTION_TOOL()299 PCB_SELECTION_TOOL::~PCB_SELECTION_TOOL()
300 {
301 }
302
303
Init()304 bool PCB_SELECTION_TOOL::Init()
305 {
306 return true;
307 }
308
309
Reset(RESET_REASON aReason)310 void PCB_SELECTION_TOOL::Reset( RESET_REASON aReason )
311 {
312 }
313
314
Main(const TOOL_EVENT & aEvent)315 int PCB_SELECTION_TOOL::Main( const TOOL_EVENT& aEvent )
316 {
317 return 0;
318 }
319
320
EnterGroup()321 void PCB_SELECTION_TOOL::EnterGroup()
322 {
323 }
324
325
ExitGroup(bool aSelectGroup)326 void PCB_SELECTION_TOOL::ExitGroup( bool aSelectGroup )
327 {
328 }
329
330
GetSelection()331 PCB_SELECTION& PCB_SELECTION_TOOL::GetSelection()
332 {
333 return m_selection;
334 }
335
336
RequestSelection(CLIENT_SELECTION_FILTER aClientFilter,bool aConfirmLockedItems)337 PCB_SELECTION& PCB_SELECTION_TOOL::RequestSelection( CLIENT_SELECTION_FILTER aClientFilter,
338 bool aConfirmLockedItems )
339 {
340 return m_selection;
341 }
342
343
getCollectorsGuide() const344 const GENERAL_COLLECTORS_GUIDE PCB_SELECTION_TOOL::getCollectorsGuide() const
345 {
346 return GENERAL_COLLECTORS_GUIDE( LSET(), PCB_LAYER_ID::UNDEFINED_LAYER, nullptr );
347 }
348
349
selectPoint(const VECTOR2I & aWhere,bool aOnDrag,bool * aSelectionCancelledFlag,CLIENT_SELECTION_FILTER aClientFilter)350 bool PCB_SELECTION_TOOL::selectPoint( const VECTOR2I& aWhere, bool aOnDrag,
351 bool* aSelectionCancelledFlag,
352 CLIENT_SELECTION_FILTER aClientFilter )
353 {
354 return false;
355 }
356
357
selectCursor(bool aForceSelect,CLIENT_SELECTION_FILTER aClientFilter)358 bool PCB_SELECTION_TOOL::selectCursor( bool aForceSelect, CLIENT_SELECTION_FILTER aClientFilter )
359 {
360 return false;
361 }
362
363
selectMultiple()364 bool PCB_SELECTION_TOOL::selectMultiple()
365 {
366 return false;
367 }
368
369
CursorSelection(const TOOL_EVENT & aEvent)370 int PCB_SELECTION_TOOL::CursorSelection( const TOOL_EVENT& aEvent )
371 {
372 return 0;
373 }
374
375
ClearSelection(const TOOL_EVENT & aEvent)376 int PCB_SELECTION_TOOL::ClearSelection( const TOOL_EVENT& aEvent )
377 {
378 return 0;
379 }
380
381
SelectItems(const TOOL_EVENT & aEvent)382 int PCB_SELECTION_TOOL::SelectItems( const TOOL_EVENT& aEvent )
383 {
384 return 0;
385 }
386
387
SelectItem(const TOOL_EVENT & aEvent)388 int PCB_SELECTION_TOOL::SelectItem( const TOOL_EVENT& aEvent )
389 {
390 return 0;
391 }
392
393
SelectAll(const TOOL_EVENT & aEvent)394 int PCB_SELECTION_TOOL::SelectAll( const TOOL_EVENT& aEvent )
395 {
396 return 0;
397 }
398
399
AddItemToSel(BOARD_ITEM * aItem,bool aQuietMode)400 void PCB_SELECTION_TOOL::AddItemToSel( BOARD_ITEM* aItem, bool aQuietMode )
401 {
402 }
403
404
UnselectItems(const TOOL_EVENT & aEvent)405 int PCB_SELECTION_TOOL::UnselectItems( const TOOL_EVENT& aEvent )
406 {
407 return 0;
408 }
409
410
UnselectItem(const TOOL_EVENT & aEvent)411 int PCB_SELECTION_TOOL::UnselectItem( const TOOL_EVENT& aEvent )
412 {
413 return 0;
414 }
415
416
RemoveItemFromSel(BOARD_ITEM * aItem,bool aQuietMode)417 void PCB_SELECTION_TOOL::RemoveItemFromSel( BOARD_ITEM* aItem, bool aQuietMode )
418 {
419 }
420
421
BrightenItem(BOARD_ITEM * aItem)422 void PCB_SELECTION_TOOL::BrightenItem( BOARD_ITEM* aItem )
423 {
424 }
425
426
UnbrightenItem(BOARD_ITEM * aItem)427 void PCB_SELECTION_TOOL::UnbrightenItem( BOARD_ITEM* aItem )
428 {
429 }
430
431
expandConnection(const TOOL_EVENT & aEvent)432 int PCB_SELECTION_TOOL::expandConnection( const TOOL_EVENT& aEvent )
433 {
434 return 0;
435 }
436
437
selectConnectedTracks(BOARD_CONNECTED_ITEM & aStartItem,STOP_CONDITION aStopCondition)438 void PCB_SELECTION_TOOL::selectConnectedTracks( BOARD_CONNECTED_ITEM& aStartItem,
439 STOP_CONDITION aStopCondition )
440 {
441 }
442
443
selectAllItemsOnNet(int aNetCode,bool aSelect)444 void PCB_SELECTION_TOOL::selectAllItemsOnNet( int aNetCode, bool aSelect )
445 {
446 }
447
448
selectNet(const TOOL_EVENT & aEvent)449 int PCB_SELECTION_TOOL::selectNet( const TOOL_EVENT& aEvent )
450 {
451 return 0;
452 }
453
454
selectAllItemsOnSheet(wxString & aSheetPath)455 void PCB_SELECTION_TOOL::selectAllItemsOnSheet( wxString& aSheetPath )
456 {
457 }
458
459
zoomFitSelection()460 void PCB_SELECTION_TOOL::zoomFitSelection()
461 {
462 }
463
464
selectSheetContents(const TOOL_EVENT & aEvent)465 int PCB_SELECTION_TOOL::selectSheetContents( const TOOL_EVENT& aEvent )
466 {
467 return 0;
468 }
469
470
selectSameSheet(const TOOL_EVENT & aEvent)471 int PCB_SELECTION_TOOL::selectSameSheet( const TOOL_EVENT& aEvent )
472 {
473 return 0;
474 }
475
476
477 /**
478 * Function itemIsIncludedByFilter()
479 *
480 * Determine if an item is included by the filter specified
481 *
482 * @return true if aItem should be selected by this filter (i..e not filtered out)
483 */
itemIsIncludedByFilter(const BOARD_ITEM & aItem,const BOARD & aBoard,const DIALOG_FILTER_SELECTION::OPTIONS & aFilterOptions)484 static bool itemIsIncludedByFilter( const BOARD_ITEM& aItem, const BOARD& aBoard,
485 const DIALOG_FILTER_SELECTION::OPTIONS& aFilterOptions )
486 {
487 return false;
488 }
489
490
filterSelection(const TOOL_EVENT & aEvent)491 int PCB_SELECTION_TOOL::filterSelection( const TOOL_EVENT& aEvent )
492 {
493 return 0;
494 }
495
496
FilterCollectedItems(GENERAL_COLLECTOR & aCollector,bool aMultiSelect)497 void PCB_SELECTION_TOOL::FilterCollectedItems( GENERAL_COLLECTOR& aCollector, bool aMultiSelect )
498 {
499 }
500
501
itemPassesFilter(BOARD_ITEM * aItem,bool aMultiSelect)502 bool PCB_SELECTION_TOOL::itemPassesFilter( BOARD_ITEM* aItem, bool aMultiSelect )
503 {
504 return true;
505 }
506
507
ClearSelection(bool aQuietMode)508 void PCB_SELECTION_TOOL::ClearSelection( bool aQuietMode )
509 {
510 }
511
512
RebuildSelection()513 void PCB_SELECTION_TOOL::RebuildSelection()
514 {
515 }
516
517
SelectionMenu(const TOOL_EVENT & aEvent)518 int PCB_SELECTION_TOOL::SelectionMenu( const TOOL_EVENT& aEvent )
519 {
520 return 0;
521 }
522
523
doSelectionMenu(GENERAL_COLLECTOR * aCollector)524 bool PCB_SELECTION_TOOL::doSelectionMenu( GENERAL_COLLECTOR* aCollector )
525 {
526 return false;
527 }
528
529
Selectable(const BOARD_ITEM * aItem,bool checkVisibilityOnly) const530 bool PCB_SELECTION_TOOL::Selectable( const BOARD_ITEM* aItem, bool checkVisibilityOnly ) const
531 {
532 return false;
533 }
534
535
select(BOARD_ITEM * aItem)536 void PCB_SELECTION_TOOL::select( BOARD_ITEM* aItem )
537 {
538 }
539
540
unselect(BOARD_ITEM * aItem)541 void PCB_SELECTION_TOOL::unselect( BOARD_ITEM* aItem )
542 {
543 }
544
highlight(BOARD_ITEM * aItem,int aMode,PCB_SELECTION * aGroup)545 void PCB_SELECTION_TOOL::highlight( BOARD_ITEM* aItem, int aMode, PCB_SELECTION* aGroup )
546 {
547 }
548
highlightInternal(BOARD_ITEM * aItem,int aMode,bool aUsingOverlay)549 void PCB_SELECTION_TOOL::highlightInternal( BOARD_ITEM* aItem, int aMode, bool aUsingOverlay )
550 {
551 }
552
553
unhighlight(BOARD_ITEM * aItem,int aMode,PCB_SELECTION * aGroup)554 void PCB_SELECTION_TOOL::unhighlight( BOARD_ITEM* aItem, int aMode, PCB_SELECTION* aGroup )
555 {
556 }
557
558
unhighlightInternal(BOARD_ITEM * aItem,int aMode,bool aUsingOverlay)559 void PCB_SELECTION_TOOL::unhighlightInternal( BOARD_ITEM* aItem, int aMode, bool aUsingOverlay )
560 {
561 }
562
563
selectionContains(const VECTOR2I & aPoint) const564 bool PCB_SELECTION_TOOL::selectionContains( const VECTOR2I& aPoint ) const
565 {
566 return false;
567 }
568
GuessSelectionCandidates(GENERAL_COLLECTOR & aCollector,const VECTOR2I & aWhere) const569 void PCB_SELECTION_TOOL::GuessSelectionCandidates( GENERAL_COLLECTOR& aCollector,
570 const VECTOR2I& aWhere ) const
571 {
572 }
573
574
575
576
updateSelection(const TOOL_EVENT & aEvent)577 int PCB_SELECTION_TOOL::updateSelection( const TOOL_EVENT& aEvent )
578 {
579 return 0;
580 }
581
582
UpdateMenu(const TOOL_EVENT & aEvent)583 int PCB_SELECTION_TOOL::UpdateMenu( const TOOL_EVENT& aEvent )
584 {
585 return 0;
586 }
587
588
setTransitions()589 void PCB_SELECTION_TOOL::setTransitions()
590 {
591 }
592
doInteractiveItemPlacement(const std::string & aTool,INTERACTIVE_PLACER_BASE * aPlacer,const wxString & aCommitMessage,int aOptions)593 void PCB_TOOL_BASE::doInteractiveItemPlacement( const std::string& aTool,
594 INTERACTIVE_PLACER_BASE* aPlacer,
595 const wxString& aCommitMessage, int aOptions )
596 {
597 }
598
599
Init()600 bool PCB_TOOL_BASE::Init()
601 {
602 return true;
603 }
604
605
Reset(RESET_REASON aReason)606 void PCB_TOOL_BASE::Reset( RESET_REASON aReason )
607 {
608 }
609
610
setTransitions()611 void PCB_TOOL_BASE::setTransitions()
612 {
613 }
614
615
Is45Limited() const616 bool PCB_TOOL_BASE::Is45Limited() const
617 {
618 return false;
619 }
620
621
displayOptions() const622 const PCB_DISPLAY_OPTIONS& PCB_TOOL_BASE::displayOptions() const
623 {
624 static PCB_DISPLAY_OPTIONS disp;
625
626 return disp;
627 }
628
canvas() const629 PCB_DRAW_PANEL_GAL* PCB_TOOL_BASE::canvas() const
630 {
631 return nullptr;
632 }
633
634
selection() const635 const PCB_SELECTION& PCB_TOOL_BASE::selection() const
636 {
637 static PCB_SELECTION sel;
638
639 return sel;
640 }
641
642
selection()643 PCB_SELECTION& PCB_TOOL_BASE::selection()
644 {
645 static PCB_SELECTION sel;
646
647 return sel;
648 }
649
650
GetTopLeftItem(bool onlyModules) const651 EDA_ITEM* PCB_SELECTION::GetTopLeftItem( bool onlyModules ) const
652 {
653 return nullptr;
654 }
655
656
updateDrawList() const657 const std::vector<KIGFX::VIEW_ITEM*> PCB_SELECTION::updateDrawList() const
658 {
659 std::vector<VIEW_ITEM*> items;
660
661 return items;
662 }
663
664
GetSelectionLayers()665 const LSET PCB_SELECTION::GetSelectionLayers()
666 {
667 return LSET();
668 }
669
670 #if 0
671 #include <3d_canvas/board_adapter.h>
672
673 BOARD_ADAPTER::BOARD_ADAPTER() {};
674 BOARD_ADAPTER::~BOARD_ADAPTER() {};
675 BBOX_3D::BBOX_3D(){};
676 BBOX_3D::~BBOX_3D(){};
677 TRACK_BALL::TRACK_BALL(float x) : CAMERA(x) {};
678 BVH_CONTAINER_2D::BVH_CONTAINER_2D() : CONTAINER_2D_BASE( OBJECT_2D_TYPE::POLYGON ) {};
679 BVH_CONTAINER_2D::~BVH_CONTAINER_2D() {};
680
681 #endif
682
683 #include <board_stackup_manager/stackup_predefined_prms.h>
684
GetColorStandardList()685 const FAB_LAYER_COLOR* GetColorStandardList()
686 {
687 return nullptr;
688 }
689
690
GetColorStandardListCount()691 int GetColorStandardListCount()
692 {
693 return 0;
694 }
695