SAGA API Version 9.12
Loading...
Searching...
No Matches
tool_chain.cpp
Go to the documentation of this file.
1
3// //
4// SAGA //
5// //
6// System for Automated Geoscientific Analyses //
7// //
8// Application Programming Interface //
9// //
10// Library: SAGA_API //
11// //
12//-------------------------------------------------------//
13// //
14// tool_chain.cpp //
15// //
16// Copyright (C) 2014 by Olaf Conrad //
17// //
18//-------------------------------------------------------//
19// //
20// This file is part of 'SAGA - System for Automated //
21// Geoscientific Analyses'. //
22// //
23// This library is free software; you can redistribute //
24// it and/or modify it under the terms of the GNU Lesser //
25// General Public License as published by the Free //
26// Software Foundation, either version 2.1 of the //
27// License, or (at your option) any later version. //
28// //
29// This library is distributed in the hope that it will //
30// be useful, but WITHOUT ANY WARRANTY; without even the //
31// implied warranty of MERCHANTABILITY or FITNESS FOR A //
32// PARTICULAR PURPOSE. See the GNU Lesser General Public //
33// License for more details. //
34// //
35// You should have received a copy of the GNU Lesser //
36// General Public License along with this program; if //
37// not, see <http://www.gnu.org/licenses/>. //
38// //
39//-------------------------------------------------------//
40// //
41// contact: Olaf Conrad //
42// Institute of Geography //
43// University of Hamburg //
44// Germany //
45// //
46// e-mail: oconrad@saga-gis.org //
47// //
49
50//---------------------------------------------------------
51#include "saga_api.h"
52
53#include "tool_chain.h"
54
55
57// //
58// //
59// //
61
62//---------------------------------------------------------
63#define GET_XML_CONTENT(XML, ID, DEFAULT, TRANSLATE) (!XML(ID) ? CSG_String(DEFAULT) : !TRANSLATE ? XML[ID].Get_Content() : CSG_String(SG_Translate(XML[ID].Get_Content())))
64
65#define IS_TRUE_STRING(String) (!String.CmpNoCase("true") || !String.CmpNoCase("1"))
66#define IS_TRUE_PROPERTY(Item, Property) (Item.Cmp_Property(Property, "true", true) || Item.Cmp_Property(Property, "1"))
67
68
70// //
71// //
72// //
74
75//---------------------------------------------------------
77{
78 // nop
79}
80
81//---------------------------------------------------------
82CSG_Tool_Chain::CSG_Tool_Chain(const CSG_Tool_Chain &Tool, bool bWithGUI, bool bWithCMD)
83{
84 Create(Tool, bWithGUI, bWithCMD);
85}
86
87//---------------------------------------------------------
89{
90 Create(File);
91}
92
93//---------------------------------------------------------
98
99//---------------------------------------------------------
101{
102 Reset();
103}
104
105//---------------------------------------------------------
106void CSG_Tool_Chain::Reset(void)
107{
109
110 m_Chain.Destroy();
111
112 m_Conditions.Destroy();
113
114 m_Menu.Clear();
115}
116
117//---------------------------------------------------------
119{
120 m_Library_Menu = Menu;
121}
122
123
125// //
127
128//---------------------------------------------------------
129bool CSG_Tool_Chain::Create(const CSG_Tool_Chain &Tool, bool bWithGUI, bool bWithCMD)
130{
131 if( !Create(Tool.m_Chain) )
132 {
133 return( false );
134 }
135
136 m_ID = Tool.m_ID;
137 m_Library = Tool.m_Library;
138 m_Library_Menu = Tool.m_Library_Menu;
139 m_File_Name = Tool.m_File_Name;
140 m_bGUI = bWithGUI && m_bGUI;
141 m_bCMD = bWithCMD && m_bCMD;
142
143 return( true );
144}
145
146//---------------------------------------------------------
148{
149 if( !SG_File_Cmp_Extension(File, "xml") )
150 {
151 return( false );
152 }
153
154 if( File.Right(sizeof(".pyt.xml")).Make_Lower().Find(".pyt.xml") >= 0 )
155 {
156 return( false );
157 }
158
160
161 if( !Chain.Load(File) )
162 {
163 Error_Fmt("%s: %s", _TL("failed to load or parse xml file"), File.c_str());
164
165 return( false );
166 }
167
168 if( Chain.Cmp_Name("toolchains") ) // don't report any error, this xml-file provides info for a category of tool chains
169 {
170 return( false );
171 }
172
173 if( !Chain.Cmp_Name("toolchain") || !Chain("identifier") || !Chain("parameters") )
174 {
175 Error_Fmt("%s: %s", _TL("xml file is not a valid tool chain"), File.c_str());
176
177 return( false );
178 }
179
180 //-----------------------------------------------------
181 SG_UI_Msg_Add(CSG_String::Format("%s: %s...", File.Cmp(m_File_Name) ? _TL("Loading tool chain") : _TL("Reloading tool chain"), File.c_str()), true);
182
183 if( Create(Chain) )
184 {
185 m_File_Name = File;
186
188
189 return( true );
190 }
191
192 m_File_Name.Clear(); Reset();
193
194 SG_UI_Msg_Add(_TL("failed"), false, SG_UI_MSG_STYLE_FAILURE);
195
196 return( false );
197}
198
199//---------------------------------------------------------
201{
202 if( !Chain.Cmp_Name("toolchain") || !Chain("identifier") || !Chain("parameters") || !Chain("tools") )
203 {
204 return( false );
205 }
206
207 if( SG_Compare_Version(Chain.Get_Property("saga-version"), "2.1.3") < 0 )
208 {
209 Error_Fmt("%s %s: %s", _TL("Warning"), _TL("unsupported tool chain version"), Chain.Get_Property("saga-version"));
210 }
211
212 //-----------------------------------------------------
213 Reset();
214
215 m_Chain = Chain;
216 m_ID = GET_XML_CONTENT(m_Chain, "identifier" , "" , false) ;
217 m_Library = GET_XML_CONTENT(m_Chain, "group" , "toolchains" , false) ;
218 m_Menu = GET_XML_CONTENT(m_Chain, "menu" , "" , true) ;
219 Set_Name (GET_XML_CONTENT(m_Chain, "name" , _TL("Not Named" ), true));
220 Set_Author (GET_XML_CONTENT(m_Chain, "author" , _TL("unknown" ), false));
221 Set_Version (GET_XML_CONTENT(m_Chain, "version" , "1.0" , false));
222 Set_Description (GET_XML_CONTENT(m_Chain, "description", _TL("no description"), true));
223
224 if( m_Library.is_Empty() )
225 {
226 m_Library = "toolchains";
227 }
228
229 Add_References();
230
231 CSG_String Description = Get_Description();
232 Description.Replace("[[", "<"); // support for xml/html tags
233 Description.Replace("]]", ">");
234 Set_Description(Description);
235
236 if( !m_Menu.is_Empty() && (m_Menu.Length() < 2 || m_Menu[1] != ':') )
237 {
238 if( IS_TRUE_PROPERTY(m_Chain["menu"], "absolute") )
239 m_Menu.Prepend("A:"); // absolute path
240 else
241 m_Menu.Prepend("R:"); // relative path
242 }
243
244 m_bAddHistory = IS_TRUE_PROPERTY(m_Chain["tools"], "history");
245
246 //-----------------------------------------------------
247 for(int i=0; i<m_Chain["parameters"].Get_Children_Count(); i++)
248 {
249 const CSG_MetaData &Parameter = m_Chain["parameters"][i];
250
251 CSG_String ID = Parameter.Get_Property("varname");
252
253 if( ID.is_Empty() || Parameters(ID) )
254 {
255 continue;
256 }
257
258 if( Parameter.Get_Property("with_gui") && !IS_TRUE_PROPERTY(Parameter, "with_gui") && has_GUI() == false )
259 {
260 continue;
261 }
262
263 if( Parameter.Get_Property("with_cmd") && !IS_TRUE_PROPERTY(Parameter, "with_cmd") && has_GUI() != false )
264 {
265 continue;
266 }
267
268 //-------------------------------------------------
269 CSG_String Value; int Constraint = 0; bool bMin = false, bMax = false; double Min = 0., Max = 0.;
270
271 if( Parameter.Cmp_Name("input") )
272 {
273 Constraint = IS_TRUE_PROPERTY(Parameter, "optional") ? PARAMETER_INPUT_OPTIONAL : PARAMETER_INPUT;
274 }
275 else if( Parameter.Cmp_Name("output") )
276 {
277 Constraint = IS_TRUE_PROPERTY(Parameter, "optional") ? PARAMETER_OUTPUT_OPTIONAL : PARAMETER_OUTPUT;
278 }
279 else if( Parameter.Cmp_Name("option") && Parameter("value") )
280 {
281 Value = Parameter.Get_Content("value");
282
283 bMin = Parameter["value"].Get_Property("min", Min);
284 bMax = Parameter["value"].Get_Property("max", Max);
285 }
286
287 //-------------------------------------------------
288 if( Parameter("condition") )
289 {
290 CSG_MetaData &Conditions = *m_Conditions.Add_Child(ID);
291
292 for(int j=0; j<Parameter.Get_Children_Count(); j++) // there might be more than one condition to be checked
293 {
294 if( Parameter[j].Cmp_Name("condition") )
295 {
296 Conditions.Add_Child(Parameter[j]);
297 }
298 }
299 }
300
301 //-------------------------------------------------
302 CSG_String Name(SG_Translate(Parameter.Get_Content("name" )));
303 CSG_String Desc(SG_Translate(Parameter.Get_Content("description")));
304
305 CSG_Parameter *pParent = Parameters(Parameter.Get_Property("parent"));
306 CSG_String ParentID(pParent ? pParent->Get_Identifier() : SG_T(""));
307
308 //-------------------------------------------------
309 switch( SG_Parameter_Type_Get_Type(Parameter.Get_Property("type")) )
310 {
311 case PARAMETER_TYPE_Node : Parameters.Add_Node (ParentID, ID, Name, Desc); break;
312
313 case PARAMETER_TYPE_Bool : Parameters.Add_Bool (ParentID, ID, Name, Desc, IS_TRUE_STRING(Value)); break;
314 case PARAMETER_TYPE_Int : Parameters.Add_Int (ParentID, ID, Name, Desc, Value.asInt (), (int)Min, bMin, (int)Max, bMax); break;
315 case PARAMETER_TYPE_Double : Parameters.Add_Double (ParentID, ID, Name, Desc, Value.asDouble(), Min, bMin, Max, bMax); break;
316 case PARAMETER_TYPE_Degree : Parameters.Add_Degree (ParentID, ID, Name, Desc, Value.asDouble(), Min, bMin, Max, bMax); break;
317
318 case PARAMETER_TYPE_Date : Parameters.Add_Date (ParentID, ID, Name, Desc, 0.)->Set_Value(Value); break;
319
320 case PARAMETER_TYPE_Range : Parameters.Add_Range (ParentID, ID, Name, Desc, Value.BeforeFirst(';').asDouble(), Value.AfterFirst(';').asDouble(), Min, bMin, Max, bMax); break;
322 case PARAMETER_TYPE_Choice : Parameters.Add_Choice (ParentID, ID, Name, Desc, Parameter.Get_Content("choices"))->Set_Value(Value); break;
323 case PARAMETER_TYPE_Choices : Parameters.Add_Choices (ParentID, ID, Name, Desc, Parameter.Get_Content("choices"))->Set_Value(Value); break;
324
325 case PARAMETER_TYPE_String : Parameters.Add_String (ParentID, ID, Name, Desc, Value, false); break;
326 case PARAMETER_TYPE_Text : Parameters.Add_String (ParentID, ID, Name, Desc, Value, true); break;
327
328 case PARAMETER_TYPE_FilePath : Parameters.Add_FilePath (ParentID, ID, Name, Desc, Parameter.Get_Content("filter"), Value,
329 IS_TRUE_PROPERTY(Parameter, "save" ),
330 IS_TRUE_PROPERTY(Parameter, "directory"),
331 IS_TRUE_PROPERTY(Parameter, "multiple" )
332 ); break;
333
334 case PARAMETER_TYPE_Font : break;
335 case PARAMETER_TYPE_Color : Parameters.Add_Color (ParentID, ID, Name, Desc, Value.asInt()); break;
336 case PARAMETER_TYPE_Colors : Parameters.Add_Colors (ParentID, ID, Name, Desc); break;
337 case PARAMETER_TYPE_FixedTable : Parameters.Add_FixedTable (ParentID, ID, Name, Desc)->Serialize(*Parameter("option"), false); break;
338
339 case PARAMETER_TYPE_Grid_System : Parameters.Add_Grid_System (ParentID, ID, Name, Desc); break;
340
341 case PARAMETER_TYPE_Table_Field : Parameters.Add_Table_Field (ParentID, ID, Name, Desc, (!Value.CmpNoCase("true") || !Value.CmpNoCase("1"))); break;
342 case PARAMETER_TYPE_Table_Fields : Parameters.Add_Table_Fields (ParentID, ID, Name, Desc); break;
343
344 case PARAMETER_TYPE_Grid : Parameter.Cmp_Property("target", "none")
345 ? Parameters.Add_Grid_Output ( "", ID, Name, Desc)
346 : Parameters.Add_Grid (ParentID, ID, Name, Desc, Constraint); break;
347
348 case PARAMETER_TYPE_Grids : Parameter.Cmp_Property("target", "none")
349 ? Parameters.Add_Grids_Output ( "", ID, Name, Desc)
350 : Parameters.Add_Grids (ParentID, ID, Name, Desc, Constraint); break;
351
352 case PARAMETER_TYPE_Table : Parameters.Add_Table (ParentID, ID, Name, Desc, Constraint); break;
353
354 case PARAMETER_TYPE_Shapes : Parameters.Add_Shapes (ParentID, ID, Name, Desc, Constraint,
355 Parameter.Cmp_Property("feature_type", "point" ) ? SHAPE_TYPE_Point :
356 Parameter.Cmp_Property("feature_type", "points" ) ? SHAPE_TYPE_Points :
357 Parameter.Cmp_Property("feature_type", "line" ) ? SHAPE_TYPE_Line :
358 Parameter.Cmp_Property("feature_type", "polygon") ? SHAPE_TYPE_Polygon : SHAPE_TYPE_Undefined
359 ); break;
360
361 case PARAMETER_TYPE_TIN : Parameters.Add_TIN (ParentID, ID, Name, Desc, Constraint); break;
362 case PARAMETER_TYPE_PointCloud : Parameters.Add_PointCloud (ParentID, ID, Name, Desc, Constraint); break;
363
364 case PARAMETER_TYPE_Grid_List : Parameters.Add_Grid_List (ParentID, ID, Name, Desc, Constraint, !IS_TRUE_PROPERTY(Parameter, "no_system")); break;
365 case PARAMETER_TYPE_Grids_List : Parameters.Add_Grids_List (ParentID, ID, Name, Desc, Constraint, !IS_TRUE_PROPERTY(Parameter, "no_system")); break;
366 case PARAMETER_TYPE_Table_List : Parameters.Add_Table_List (ParentID, ID, Name, Desc, Constraint); break;
367 case PARAMETER_TYPE_Shapes_List : Parameters.Add_Shapes_List (ParentID, ID, Name, Desc, Constraint); break;
368 case PARAMETER_TYPE_TIN_List : Parameters.Add_TIN_List (ParentID, ID, Name, Desc, Constraint); break;
369 case PARAMETER_TYPE_PointCloud_List : Parameters.Add_PointCloud_List(ParentID, ID, Name, Desc, Constraint); break;
370
372 case PARAMETER_TYPE_Parameters : break; // to do ?
373
374 default: break;
375 }
376 }
377
378 //-----------------------------------------------------
379 return( is_Okay() );
380}
381
382
384// //
386
387//---------------------------------------------------------
389{
390 return( !m_Chain("CRS_SYNC") || IS_TRUE_STRING(m_Chain["CRS_SYNC"].Get_Content()) );
391}
392
393//---------------------------------------------------------
394void CSG_Tool_Chain::Add_References(void)
395{
396 for(int i=0; i<m_Chain.Get_Children_Count(); i++)
397 {
398 if( !m_Chain[i].Get_Name().CmpNoCase("REFERENCE") )
399 {
400 CSG_String Authors, Year, Title, Where, Link, Link_Text, DOI;
401
402 if( m_Chain[i]("AUTHORS" ) ) Authors = m_Chain[i].Get_Content("AUTHORS" );
403 if( m_Chain[i]("YEAR" ) ) Year = m_Chain[i].Get_Content("YEAR" );
404 if( m_Chain[i]("TITLE" ) ) Title = m_Chain[i].Get_Content("TITLE" );
405 if( m_Chain[i]("WHERE" ) ) Where = m_Chain[i].Get_Content("WHERE" );
406 if( m_Chain[i]("LINK" ) ) Link = m_Chain[i].Get_Content("LINK" );
407 if( m_Chain[i]("LINK_TEXT") ) Link_Text = m_Chain[i].Get_Content("LINK_TEXT");
408 if( m_Chain[i]("DOI" ) ) DOI = m_Chain[i].Get_Content("DOI" );
409
410 if( !DOI.is_Empty() )
411 {
412 Link = "https://doi.org/" + DOI; Link_Text = "doi:" + DOI;
413 }
414
415 if( !Authors.is_Empty() && !Year.is_Empty() && !Title.is_Empty() )
416 {
417 Add_Reference(Authors, Year, Title, Where, Link.c_str(), Link_Text.c_str());
418 }
419 else if( !Link.is_Empty() )
420 {
421 Add_Reference(Link, Link_Text.c_str());
422 }
423 }
424 }
425}
426
427
429// //
431
432//---------------------------------------------------------
434{
435 for(int iParameter=0; iParameter<m_Conditions.Get_Children_Count(); iParameter++)
436 {
437 const CSG_MetaData &Conditions = m_Conditions[iParameter];
438
439 if( (*pParameters)(Conditions.Get_Name()) )
440 {
441 bool bEnable = true;
442
443 for(int iCondition=0; bEnable && iCondition<Conditions.Get_Children_Count(); iCondition++)
444 {
445 bEnable = Check_Condition(Conditions[iCondition], pParameters);
446 }
447
448 (*pParameters)(Conditions.Get_Name())->Set_Enabled(bEnable);
449 }
450 }
451
452 return( CSG_Tool::On_Parameters_Enable(pParameters, pParameter) );
453}
454
455
457// //
459
460//---------------------------------------------------------
462{
463 bool bResult = Data_Initialize();
464
465 if( !bResult )
466 {
467 Error_Set(_TL("no data objects"));
468 }
469
470 for(int i=0; bResult && i<m_Chain["tools"].Get_Children_Count(); i++)
471 {
472 bResult = Tool_Run(m_Chain["tools"][i]);
473 }
474
475 Data_Finalize();
476
477 return( bResult );
478}
479
480
482// //
484
485//---------------------------------------------------------
486bool CSG_Tool_Chain::Data_Add(const CSG_String &ID, CSG_Parameter *pData)
487{
488 if( !pData )
489 {
490 return( false );
491 }
492
493 CSG_Parameter *pParameter = m_Data(ID); // check if the local data manager already has a parameter with this identifier
494
495 if( pParameter ) // it has, so don't add twice!
496 {
497 if( pParameter->is_Input() && pParameter->Get_Type() != pData->Get_Type() ) // don't allow to change parameter's data object type!
498 {
499 Error_Fmt("%s\n[%s] %s <> %s", _TL("Tool chain uses same variable name for different data object types."),
500 ID.c_str(), pParameter->Get_Type_Identifier().c_str(), pData->Get_Type_Identifier().c_str()
501 );
502
503 return( false );
504 }
505 }
506
507 //-----------------------------------------------------
508 else switch( pData->Get_Type() )
509 {
510 case PARAMETER_TYPE_PointCloud : pParameter = m_Data.Add_PointCloud ("", ID, "", "", 0 ); break;
511 case PARAMETER_TYPE_Grid : pParameter = m_Data.Add_Grid ("", ID, "", "", 0 ); break;
512 case PARAMETER_TYPE_Grids : pParameter = m_Data.Add_Grids ("", ID, "", "", 0 ); break;
513 case PARAMETER_TYPE_Table : pParameter = m_Data.Add_Table ("", ID, "", "", 0 ); break;
514 case PARAMETER_TYPE_Shapes : pParameter = m_Data.Add_Shapes ("", ID, "", "", 0 ); break;
515 case PARAMETER_TYPE_TIN : pParameter = m_Data.Add_TIN ("", ID, "", "", 0 ); break;
516
517 case PARAMETER_TYPE_PointCloud_List: pParameter = m_Data.Add_PointCloud_List("", ID, "", "", 0 ); break;
518 case PARAMETER_TYPE_Grid_List : pParameter = m_Data.Add_Grid_List ("", ID, "", "", 0, false); break;
519 case PARAMETER_TYPE_Grids_List : pParameter = m_Data.Add_Grids_List ("", ID, "", "", 0, false); break;
520 case PARAMETER_TYPE_Table_List : pParameter = m_Data.Add_Table_List ("", ID, "", "", 0 ); break;
521 case PARAMETER_TYPE_Shapes_List : pParameter = m_Data.Add_Shapes_List ("", ID, "", "", 0 ); break;
522 case PARAMETER_TYPE_TIN_List : pParameter = m_Data.Add_TIN_List ("", ID, "", "", 0 ); break;
523
525 switch( pData->Get_DataObject_Type() )
526 {
527 case SG_DATAOBJECT_TYPE_PointCloud: pParameter = m_Data.Add_PointCloud ("", ID, "", "", 0 ); break;
528 case SG_DATAOBJECT_TYPE_Grid : pParameter = m_Data.Add_Grid ("", ID, "", "", 0 ); break;
529 case SG_DATAOBJECT_TYPE_Grids : pParameter = m_Data.Add_Grids ("", ID, "", "", 0 ); break;
530 case SG_DATAOBJECT_TYPE_Table : pParameter = m_Data.Add_Table ("", ID, "", "", 0 ); break;
531 case SG_DATAOBJECT_TYPE_Shapes : pParameter = m_Data.Add_Shapes ("", ID, "", "", 0 ); break;
532 case SG_DATAOBJECT_TYPE_TIN : pParameter = m_Data.Add_TIN ("", ID, "", "", 0 ); break;
533 default:
534 return( true );
535 }
536 break;
537
538 default:
539 return( true );
540 }
541
542 //-----------------------------------------------------
543 if( pData->is_DataObject() )
544 {
545 if( pParameter->is_DataObject() )
546 {
547 pParameter->Set_Value(pData->asDataObject());
548 }
549 else
550 {
551 pParameter->asList()->Add_Item(pData->asDataObject());
552 }
553
554 m_Data_Manager.Add(pData->asDataObject());
555 }
556 else if( pData->is_DataObject_List() && pParameter->is_DataObject_List() )
557 {
558 for(int i=0; i<pData->asList()->Get_Item_Count(); i++)
559 {
560 pParameter->asList()->Add_Item(pData->asList()->Get_Item(i));
561 m_Data_Manager .Add (pData->asList()->Get_Item(i));
562 }
563 }
564
565 return( true );
566}
567
568//---------------------------------------------------------
569bool CSG_Tool_Chain::Data_Add_TempList(const CSG_String &ID, const CSG_String &Type)
570{
571 if( !m_Data(ID) )
572 {
573 switch( SG_Parameter_Type_Get_Type(Type) )
574 {
575 case PARAMETER_TYPE_PointCloud_List: m_Data.Add_PointCloud_List("", ID, "", "", 0 ); break;
576 case PARAMETER_TYPE_Grid_List : m_Data.Add_Grid_List ("", ID, "", "", 0, false); break;
577 case PARAMETER_TYPE_Grids_List : m_Data.Add_Grids_List ("", ID, "", "", 0, false); break;
578 case PARAMETER_TYPE_Table_List : m_Data.Add_Table_List ("", ID, "", "", 0 ); break;
579 case PARAMETER_TYPE_Shapes_List : m_Data.Add_Shapes_List ("", ID, "", "", 0 ); break;
580 case PARAMETER_TYPE_TIN_List : m_Data.Add_TIN_List ("", ID, "", "", 0 ); break;
581
582 default:
583 Error_Fmt("%s: %s [%s|%s]", SG_T("datalist"), _TL("unsupported data list type"), ID.c_str(), Type.c_str());
584
585 return( false );
586 }
587 }
588
589 return( true );
590}
591
592//---------------------------------------------------------
593bool CSG_Tool_Chain::Data_Del_Temp(const CSG_String &ID, bool bData)
594{
595 CSG_Parameter *pData = m_Data(ID);
596
597 if( pData )
598 {
599 if( bData )
600 {
601 if( pData->is_DataObject() )
602 {
603 m_Data_Manager.Delete(pData->asDataObject());
604 }
605 else if( pData->is_DataObject_List() )
606 {
607 for(int i=0; i<pData->asList()->Get_Item_Count(); i++)
608 {
609 m_Data_Manager.Delete(pData->asList()->Get_Item(i));
610 }
611 }
612 }
613
614 m_Data.Del_Parameter(ID);
615 }
616
617 return( true );
618}
619
620//---------------------------------------------------------
621bool CSG_Tool_Chain::Data_Update(const CSG_String &ID, bool bShow)
622{
623 CSG_Parameter *pData = m_Data(ID);
624
625 if( pData && pData->asDataObject() && pData->asDataObject()->is_Valid() )
626 {
628 }
629
630 return( true );
631}
632
633
635// //
637
638//---------------------------------------------------------
639bool CSG_Tool_Chain::Data_Exists(CSG_Data_Object *pData)
640{
641 for(int i=0; i<m_Data.Get_Count(); i++)
642 {
643 if( m_Data[i].is_DataObject() )
644 {
645 if( pData == m_Data[i].asDataObject() )
646 {
647 return( true );
648 }
649 }
650 else if( m_Data[i].is_DataObject_List() )
651 {
652 for(int j=0; j<m_Data[i].asList()->Get_Item_Count(); j++)
653 {
654 if( pData == m_Data[i].asList()->Get_Item(j) )
655 {
656 return( true );
657 }
658 }
659 }
660 }
661
662 return( false );
663}
664
665//---------------------------------------------------------
666bool CSG_Tool_Chain::Data_Initialize(void)
667{
668 m_Data.Set_Manager(NULL);
669
670 for(int i=0; i<Parameters.Get_Count(); i++)
671 {
672 CSG_Parameter &P = Parameters[i];
673
674 if( !(P.is_DataObject() && !P.asDataObject()) )
675 {
676 if( !Data_Add(P.Get_Identifier(), &P) )
677 {
678 return( false );
679 }
680 }
681 }
682
683 return( true );
684}
685
686//---------------------------------------------------------
687bool CSG_Tool_Chain::Data_Finalize(void)
688{
689 for(int i=0; i<Parameters.Get_Count(); i++) // detach non temporary data before freeing the local data manager !!!
690 {
691 CSG_Parameter &P = Parameters[i];
692
693 if( P.is_DataObject() )
694 {
695 if( m_Data(P.Get_Identifier()) )
696 {
698 {
699 P.Set_Value(m_Data(P.Get_Identifier())->asDataObject());
700 }
701 }
702
703 m_Data_Manager.Delete(P.asDataObject(), true);
704 }
705 else if( P.is_DataObject_List() )
706 {
707 if( P.is_Output() && m_Data(P.Get_Identifier()) ) // output lists cannot be up-to-date yet
708 {
709 CSG_Parameter *pData = m_Data(P.Get_Identifier());
710
711 for(int j=0; j<pData->asList()->Get_Item_Count(); j++) // csg_parameter::assign() will not work, if parameters data manager is the standard data manager because it checks for existing data sets
712 {
713 P.asList()->Add_Item(pData->asList()->Get_Item(j));
714 }
715 }
716
717 for(int j=0; j<P.asList()->Get_Item_Count(); j++)
718 {
719 m_Data_Manager.Delete(P.asList()->Get_Item(j), true);
720 }
721 }
722 }
723
724 m_Data_Manager.Delete();
725
726 m_Data.Destroy();
727
728 //-----------------------------------------------------
729 for(int i=0; i<m_Chain["parameters"].Get_Children_Count(); i++)
730 {
731 const CSG_MetaData &Parameter = m_Chain["parameters"][i];
732
733 if( Parameter.Cmp_Name("output") )
734 {
735 CSG_Parameter *pParameter = Parameters(Parameter.Get_Property("varname"));
736
737 if( pParameter && pParameter->is_DataObject() && pParameter->asDataObject() && pParameter->asDataObject() != DATAOBJECT_CREATE )
738 {
739 if( Parameter("colours") )
740 {
741 DataObject_Set_Colors(pParameter->asDataObject(), Parameter["colours"].Get_Content(), 0, IS_TRUE_PROPERTY(Parameter["colours"], "revert"));
742 }
743
744 if( Parameter("copy_settings") )
745 {
746 CSG_Parameter *pInput = Parameters(Parameter["copy_settings"].Get_Content());
747
748 if( pInput && pInput->is_DataObject() && pInput->asDataObject() )
749 {
750 DataObject_Set_Parameters(pParameter->asDataObject(), pInput->asDataObject());
751 }
752 }
753
754 if( Parameter("output_name") )
755 {
756 if( IS_TRUE_PROPERTY(Parameter["output_name"], "input") )
757 {
758 CSG_Parameter *pInput = Parameters(Parameter["output_name"].Get_Content());
759
760 if( pInput && pInput->is_DataObject() && pInput->asDataObject() )
761 {
762 CSG_String Suffix;
763
764 if( Parameter["output_name"].Get_Property("suffix", Suffix) && !Suffix.is_Empty() )
765 {
766 Suffix = " [" + Suffix + "]";
767 }
768
769 pParameter->asDataObject()->Set_Name(pInput->asDataObject()->Get_Name() + Suffix);
770 }
771 }
772 else if( !Parameter["output_name"].Get_Content().is_Empty() )
773 {
774 pParameter->asDataObject()->Set_Name(Parameter["output_name"].Get_Content());
775 }
776 }
777 }
778 }
779 }
780
781 //-----------------------------------------------------
782 return( true );
783}
784
785
787// //
789
790//---------------------------------------------------------
791bool CSG_Tool_Chain::Parameter_isCompatible(TSG_Parameter_Type A, TSG_Parameter_Type B)
792{
793 if( A == B )
794 {
795 return( true );
796 }
797
798 switch( A )
799 {
800 default:
801 return( false );
802
804 return( B == PARAMETER_TYPE_Shapes
806 || B == PARAMETER_TYPE_TIN );
807
809 return( B == PARAMETER_TYPE_PointCloud );
810 }
811}
812
813
815// //
817
818//---------------------------------------------------------
819bool CSG_Tool_Chain::Message(const CSG_MetaData &Message)
820{
821 if( Message.Cmp_Name("message") )
822 {
823 if( IS_TRUE_PROPERTY(Message, "dialog") )
824 {
825 Message_Dlg(Message.Get_Content());
826 }
827
828 Message_Fmt("\n%s", Message.Get_Content().c_str());
829 }
830
831 return( true );
832}
833
834
836// //
838
839//---------------------------------------------------------
840bool CSG_Tool_Chain::Check_Condition(const CSG_MetaData &Condition, CSG_Parameters *pData)
841{
842 CSG_String Type;
843
844 if( !Condition.Cmp_Name("condition") || !Condition.Get_Property("type", Type) )
845 {
846 return( true );
847 }
848
849 //-----------------------------------------------------
850 CSG_String Variable;
851
852 if( !Condition.Get_Property("varname", Variable) && !Condition.Get_Property("variable", Variable) )
853 {
854 Variable = Condition.Get_Content();
855 }
856
857 //-----------------------------------------------------
858 if( !Type.CmpNoCase("has_gui" ) ) // executed from saga_gui ? (tool might offer different parameters if called from saga_cmd, python etc.)
859 {
860 return( IS_TRUE_STRING(Variable) ? has_GUI() != false : has_GUI() == false );
861 }
862
863 //-----------------------------------------------------
864 if( !Type.CmpNoCase("exists" ) ) // data object exists
865 {
866 CSG_Parameter *pParameter = (*pData)(Variable);
867
868 return( pParameter && ((pParameter->is_DataObject() && pParameter->asDataObject()) || (pParameter->is_DataObject_List() && pParameter->asList()->Get_Item_Count())) );
869 }
870
871 if( !Type.CmpNoCase("not_exists") ) // data object does not exist
872 {
873 return( (*pData)(Variable) == NULL || (*pData)(Variable)->asDataObject() == NULL );
874 }
875
876 //-----------------------------------------------------
877 CSG_Parameter *pOption = (*pData)(Variable);
878
879 if( pOption == NULL )
880 {
881 return( true );
882 }
883
884 switch( pOption->Get_Type() )
885 {
886 //-----------------------------------------------------
888 {
889 CSG_String Value;
890
891 if( Condition.Get_Property("value", Value) )
892 {
893 if( !Type.CmpNoCase("=") || !Type.CmpNoCase("equal" ) ) { return( (IS_TRUE_STRING(Value) ? pOption->asBool() : !pOption->asBool()) ); }
894 else if( !Type.CmpNoCase("!") || !Type.CmpNoCase("not_equal") ) { return( (IS_TRUE_STRING(Value) ? !pOption->asBool() : pOption->asBool()) ); }
895 }
896 }
897 break;
898
899 //-----------------------------------------------------
900 case PARAMETER_TYPE_Int :
904 {
905 int Value;
906
907 if( Condition.Get_Property("value", Value) )
908 {
909 if( !Type.CmpNoCase("=") || !Type.CmpNoCase("equal" ) ) { if( Value != pOption->asInt() ) { return( false ); } }
910 else if( !Type.CmpNoCase("!") || !Type.CmpNoCase("not_equal") ) { if( Value == pOption->asInt() ) { return( false ); } }
911 else if( !Type.CmpNoCase("<") || !Type.CmpNoCase("less" ) ) { if( Value >= pOption->asInt() ) { return( false ); } }
912 else if( !Type.CmpNoCase(">") || !Type.CmpNoCase("greater" ) ) { if( Value <= pOption->asInt() ) { return( false ); } }
913 }
914 }
915 break;
916
917 //-----------------------------------------------------
920 {
921 double Value;
922
923 if( Condition.Get_Property("value", Value) )
924 {
925 if( !Type.CmpNoCase("=") || !Type.CmpNoCase("equal" ) ) { if( Value != pOption->asDouble() ) { return( false ); } }
926 else if( !Type.CmpNoCase("!") || !Type.CmpNoCase("not_equal") ) { if( Value == pOption->asDouble() ) { return( false ); } }
927 else if( !Type.CmpNoCase("<") || !Type.CmpNoCase("less" ) ) { if( Value >= pOption->asDouble() ) { return( false ); } }
928 else if( !Type.CmpNoCase(">") || !Type.CmpNoCase("greater" ) ) { if( Value <= pOption->asDouble() ) { return( false ); } }
929 }
930 }
931 break;
932
933 //-----------------------------------------------------
937 {
938 CSG_String Value;
939
940 Condition.Get_Property("value", Value); // no 'if', bcos empty string would return false !!
941
942 {
943 if( !Type.CmpNoCase("=") || !Type.CmpNoCase("equal" ) ) { if( Value.Cmp(pOption->asString()) != 0 ) { return( false ); } }
944 else if( !Type.CmpNoCase("!") || !Type.CmpNoCase("not_equal") ) { if( Value.Cmp(pOption->asString()) == 0 ) { return( false ); } }
945 else if( !Type.CmpNoCase("<") || !Type.CmpNoCase("less" ) ) { if( Value.Cmp(pOption->asString()) >= 0 ) { return( false ); } }
946 else if( !Type.CmpNoCase(">") || !Type.CmpNoCase("greater" ) ) { if( Value.Cmp(pOption->asString()) <= 0 ) { return( false ); } }
947 }
948 }
949 break;
950
951 //-----------------------------------------------------
953 {
954 CSG_String Value;
955
956 if( Condition.Get_Property("value", Value) )
957 {
958 bool bValid = pOption->asGrid_System()->is_Valid();
959
960 if( !Type.CmpNoCase("=") || !Type.CmpNoCase("equal" ) ) { return( (IS_TRUE_STRING(Value) ? bValid : !bValid) ); }
961 else if( !Type.CmpNoCase("!") || !Type.CmpNoCase("not_equal") ) { return( (IS_TRUE_STRING(Value) ? !bValid : bValid) ); }
962 }
963 }
964 break;
965
966 //-----------------------------------------------------
967 default:
968 // nop
969 break;
970 }
971
972 return( true );
973}
974
975
977// //
979
980//---------------------------------------------------------
981bool CSG_Tool_Chain::ForEach(const CSG_MetaData &Commands)
982{
983 for(int i=0; i<Commands.Get_Children_Count(); i++) // add internal target lists, if any..
984 {
985 if( Commands[i].Cmp_Name("output") || Commands[i].Cmp_Name("datalist") )
986 {
987 Data_Add_TempList(Commands[i].Get_Content(), Commands[i].Get_Property("type"));
988 }
989 }
990
991 //-----------------------------------------------------
992 bool bIgnoreErrors = IS_TRUE_PROPERTY(Commands, "ignore_errors");
993
994 CSG_String VarName;
995
996 if( Commands.Get_Property("varname", VarName) )
997 {
998 return( ForEach_Iterator(Commands, VarName, bIgnoreErrors) );
999 }
1000
1001 if( Commands.Get_Property("input", VarName) )
1002 {
1003 return( ForEach_Object (Commands, VarName, bIgnoreErrors)
1004 || ForEach_File (Commands, VarName, bIgnoreErrors) );
1005 }
1006
1007 Error_Set("foreach statement misses iterator or input list definition");
1008
1009 return( false );
1010}
1011
1012//---------------------------------------------------------
1013bool CSG_Tool_Chain::ForEach_Iterator(const CSG_MetaData &Commands, const CSG_String &VarName, bool bIgnoreErrors)
1014{
1015 CSG_Parameter *pIterator = Parameters(VarName);
1016
1017 if( pIterator )
1018 {
1019 Error_Set("foreach statement iterator variable name is already in use");
1020
1021 return( false );
1022 }
1023
1024 //-----------------------------------------------------
1025 CSG_String s;
1026
1027 double begin = Commands.Get_Property("begin", s) ? (Parameters(s) ? Parameters[s].asDouble() : s.asDouble()) : 0.;
1028 double end = Commands.Get_Property("end" , s) ? (Parameters(s) ? Parameters[s].asDouble() : s.asDouble()) : 0.;
1029
1030 if( begin >= end )
1031 {
1032 Error_Set("foreach iterator statement with invalid range (define begin < end)");
1033
1034 return( false );
1035 }
1036
1037 double step = 1.;
1038
1039 if( Commands.Get_Property("steps", s) )
1040 {
1041 double steps = Parameters(s) ? Parameters[s].asDouble() : s.asDouble();
1042
1043 if( steps > 0 )
1044 {
1045 step = (end - begin) / steps;
1046 }
1047 }
1048 else if( Commands.Get_Property("step", s) )
1049 {
1050 step = Parameters(s) ? Parameters[s].asDouble() : s.asDouble();
1051 }
1052
1053 if( step <= 0. )
1054 {
1055 Error_Set("foreach iterator statement with invalid step size (define step > 0 or steps > 0)");
1056
1057 return( false );
1058 }
1059
1060 Message_Fmt("\nfor i = %f to %f step %f (%d steps)", begin, end, step, (int)((end - begin) / step));
1061
1062 //-----------------------------------------------------
1063 bool bResult = true;
1064
1065 pIterator = Parameters.Add_Double("", VarName, "Iterator", "");
1066
1067 for(double i=begin; bResult && i<=end; i+=step)
1068 {
1069 Message_Fmt("\nfor step: %f", i);
1070
1071 pIterator->Set_Value(i);
1072
1073 for(int iTool=0; bResult && iTool<Commands.Get_Children_Count(); iTool++)
1074 {
1075 const CSG_MetaData &Tool = Commands[iTool];
1076
1077 if( Tool.Cmp_Name("tool") )
1078 {
1079 bResult = Tool_Run(Tool, bIgnoreErrors);
1080
1081 if( !bResult && bIgnoreErrors )
1082 {
1083 bResult = true;
1084 }
1085 }
1086 }
1087 }
1088
1089 Parameters.Del_Parameter(VarName);
1090
1091 return( bResult );
1092}
1093
1094//---------------------------------------------------------
1095bool CSG_Tool_Chain::ForEach_Object(const CSG_MetaData &Commands, const CSG_String &ListVarName, bool bIgnoreErrors)
1096{
1097 CSG_Parameter *pList = m_Data(ListVarName);
1098
1099 if( !pList )
1100 {
1101 return( false );
1102 }
1103
1104 //-----------------------------------------------------
1105 bool bResult = true;
1106
1107 if( pList->is_DataObject_List() )
1108 {
1109 for(int iObject=0; bResult && iObject<pList->asList()->Get_Item_Count(); iObject++)
1110 {
1111 for(int iTool=0; bResult && iTool<Commands.Get_Children_Count(); iTool++)
1112 {
1113 const CSG_MetaData &Tool = Commands[iTool];
1114
1115 if( Tool.Cmp_Name("tool") )
1116 {
1117 for(int j=0; j<Tool.Get_Children_Count(); j++)
1118 {
1119 if( Tool[j].Cmp_Name("input") && Tool[j].Get_Content().Find(ListVarName) == 0 )
1120 {
1121 Tool(j)->Set_Content(ListVarName + CSG_String::Format("[%d]", iObject));
1122 }
1123 }
1124 }
1125
1126 bResult = Tool_Run(Tool, bIgnoreErrors);
1127 }
1128
1129 if( !bResult && bIgnoreErrors )
1130 {
1131 bResult = true;
1132 }
1133 }
1134 }
1135
1136 //-----------------------------------------------------
1137 else if( pList->Get_Type() == PARAMETER_TYPE_Grids )
1138 {
1139 for(int iObject=0; bResult && iObject<pList->asGrids()->Get_Grid_Count(); iObject++)
1140 {
1141 for(int iTool=0; bResult && iTool<Commands.Get_Children_Count(); iTool++)
1142 {
1143 const CSG_MetaData &Tool = Commands[iTool];
1144
1145 if( Tool.Cmp_Name("tool") )
1146 {
1147 for(int j=0; j<Tool.Get_Children_Count(); j++)
1148 {
1149 if( Tool[j].Cmp_Name("input") && Tool[j].Get_Content().Find(ListVarName) == 0 )
1150 {
1151 Tool(j)->Set_Content(ListVarName + CSG_String::Format("[%d]", iObject));
1152 }
1153 }
1154 }
1155
1156 bResult = Tool_Run(Tool, bIgnoreErrors);
1157 }
1158
1159 if( !bResult && bIgnoreErrors )
1160 {
1161 bResult = true;
1162 }
1163 }
1164 }
1165
1166 return( bResult );
1167}
1168
1169//---------------------------------------------------------
1170bool CSG_Tool_Chain::ForEach_File(const CSG_MetaData &Commands, const CSG_String &ListVarName, bool bIgnoreErrors)
1171{
1172 CSG_Parameter *pList = Parameters(ListVarName);
1173
1174 if( !pList || pList->Get_Type() != PARAMETER_TYPE_FilePath )
1175 {
1176 return( false );
1177 }
1178
1179 CSG_Strings Files;
1180
1181 pList->asFilePath()->Get_FilePaths(Files);
1182
1183 //-----------------------------------------------------
1184 bool bResult = true;
1185
1186 for(int iFile=0; bResult && iFile<Files.Get_Count(); iFile++)
1187 {
1188 for(int iTool=0; bResult && iTool<Commands.Get_Children_Count(); iTool++)
1189 {
1190 const CSG_MetaData &Tool = Commands[iTool];
1191
1192 if( Tool.Cmp_Name("tool") )
1193 {
1194 CSG_Array_Int Input;
1195
1196 for(int j=0; j<Tool.Get_Children_Count(); j++)
1197 {
1198 if( Tool[j].Cmp_Name("option") && Tool[j].Get_Content().Find(ListVarName) == 0 && IS_TRUE_PROPERTY(Tool[j], "varname") )
1199 {
1200 Tool(j)->Set_Content(Files[iFile]);
1201 Tool(j)->Set_Property("varname", "false");
1202
1203 Input += j;
1204 }
1205 }
1206
1207 bResult = Tool_Run(Tool, bIgnoreErrors);
1208
1209 for(size_t i=0; i<Input.Get_uSize(); i++)
1210 {
1211 Tool(Input[i])->Set_Content(ListVarName);
1212 Tool(Input[i])->Set_Property("varname", "true");
1213 }
1214 }
1215 else
1216 {
1217 bResult = Tool_Run(Tool, bIgnoreErrors);
1218 }
1219
1220 if( !bResult && bIgnoreErrors )
1221 {
1222 bResult = true;
1223 }
1224 }
1225 }
1226
1227 return( bResult );
1228}
1229
1230
1232// //
1234
1235//---------------------------------------------------------
1236bool CSG_Tool_Chain::Tool_Run(const CSG_MetaData &Tool, bool bShowError)
1237{
1238 if( Tool.Cmp_Name("message") )
1239 {
1240 Message(Tool);
1241
1242 return( true );
1243 }
1244
1245 //-----------------------------------------------------
1246 if( Tool.Cmp_Name("comment") )
1247 {
1248 return( true );
1249 }
1250
1251 //-----------------------------------------------------
1252 if( Tool.Cmp_Name("datalist") )
1253 {
1254 return( Data_Add_TempList(Tool.Get_Content(), Tool.Get_Property("type")) );
1255 }
1256
1257 if( Tool.Cmp_Name("delete") )
1258 {
1259 return( Data_Del_Temp(Tool.Get_Content(), IS_TRUE_PROPERTY(Tool, "data")) );
1260 }
1261
1262 if( Tool.Cmp_Name("update") )
1263 {
1264 return( Data_Update(Tool.Get_Content(), IS_TRUE_PROPERTY(Tool, "show")) );
1265 }
1266
1267 //-----------------------------------------------------
1268 if( Tool.Cmp_Name("condition") )
1269 {
1270 const CSG_MetaData *pTools = (!Check_Condition(Tool, &m_Data) || !Check_Condition(Tool, &Parameters))
1271 ? Tool("else") : (Tool("if") ? Tool("if") : &Tool);
1272
1273 for(int i=0; pTools && i<pTools->Get_Children_Count(); i++)
1274 {
1275 if( !Tool_Run((*pTools)[i]) )
1276 {
1277 return( false );
1278 }
1279 }
1280
1281 return( true );
1282 }
1283
1284 //-----------------------------------------------------
1285 if( Tool.Cmp_Name("foreach") )
1286 {
1287 return( ForEach(Tool) );
1288 }
1289
1290 //-----------------------------------------------------
1291 if( !Tool.Cmp_Name("tool") )
1292 {
1293 return( true ); // only proceed, if it is tagged as tool...
1294 }
1295
1296 if( !Tool.Get_Property("library") || !(Tool.Get_Property("tool") || Tool.Get_Property("module")) )
1297 {
1298 if( bShowError ) Error_Set(_TL("invalid tool definition"));
1299
1300 return( false );
1301 }
1302
1303 //-----------------------------------------------------
1304 const SG_Char *Name = Tool.Get_Property("tool") ? Tool.Get_Property("tool") : Tool.Get_Property("module");
1305
1306 CSG_Tool *pTool = SG_Get_Tool_Library_Manager().Create_Tool(Tool.Get_Property("library"), Name,
1307 IS_TRUE_PROPERTY(Tool, "with_gui") // this option allows to run a tool in 'gui-mode', e.g. to popup variogram dialogs for kriging interpolation
1308 );
1309
1310 if( !pTool )
1311 {
1312 if( bShowError ) Error_Fmt("%s [%s].[%s]", _TL("could not find tool"), Tool.Get_Property("library"), Name);
1313
1314 return( false );
1315 }
1316
1317 //-----------------------------------------------------
1318 Process_Set_Text(pTool->Get_Name());
1319
1320 pTool->Settings_Push(&m_Data_Manager);
1321
1322 bool bResult = false;
1323
1324 if( !pTool->On_Before_Execution() )
1325 {
1326 if( bShowError ) Error_Fmt("%s [%s].[%s]", _TL("before tool execution check failed"), pTool->Get_Library().c_str(), pTool->Get_Name().c_str());
1327 }
1328 else if( !Tool_Initialize(Tool, pTool) )
1329 {
1330 if( bShowError ) Error_Fmt("%s [%s].[%s]", _TL("tool initialization failed" ), pTool->Get_Library().c_str(), pTool->Get_Name().c_str());
1331 }
1332 else if( !(bResult = pTool->Execute(m_bAddHistory)) )
1333 {
1334 if( bShowError ) Error_Fmt("%s [%s].[%s]", _TL("tool execution failed" ), pTool->Get_Library().c_str(), pTool->Get_Name().c_str());
1335 }
1336
1337 if( bResult )
1338 {
1339 pTool->On_After_Execution();
1340 }
1341
1342 Tool_Finalize(Tool, pTool);
1343
1344 pTool->Settings_Pop();
1345
1347
1348 return( bResult );
1349}
1350
1351
1353// //
1355
1356//---------------------------------------------------------
1357bool CSG_Tool_Chain::Tool_Check_Condition(const CSG_MetaData &Tool)
1358{
1359 if( Tool("condition") )
1360 {
1361 for(int i=0; i<Tool.Get_Children_Count(); i++) // there might be more than one condition to be checked
1362 {
1363 if( !Check_Condition(Tool[i], &m_Data) )
1364 {
1365 return( false );
1366 }
1367 }
1368 }
1369
1370 return( true );
1371}
1372
1373
1375// //
1377
1378//---------------------------------------------------------
1379bool CSG_Tool_Chain::Tool_Get_Parameter(CSG_String ID, CSG_Parameters *pParameters, CSG_Parameter **ppParameter, CSG_Parameter **ppOwner)
1380{
1381 CSG_Parameter *pParameter = (*pParameters)(ID.BeforeFirst('.'));
1382
1383 if( pParameter )
1384 {
1385 switch( pParameter->Get_Type() )
1386 {
1387 default:
1388 *ppParameter = pParameter;
1389
1390 return( true );
1391
1393 *ppOwner = pParameter;
1394
1395 return( Tool_Get_Parameter(ID.AfterFirst('.'), pParameter->asParameters(), ppParameter, ppOwner) );
1396
1398 if( !ID.AfterFirst('.').CmpNoCase("min") || !ID.AfterFirst('.').CmpNoCase("minimum") )
1399 {
1400 *ppParameter = pParameter->asRange()->Get_Min_Parameter();
1401 *ppOwner = pParameter;
1402 }
1403 else if( !ID.AfterFirst('.').CmpNoCase("max") || !ID.AfterFirst('.').CmpNoCase("maximum") )
1404 {
1405 *ppParameter = pParameter->asRange()->Get_Max_Parameter();
1406 *ppOwner = pParameter;
1407 }
1408 else
1409 {
1410 *ppParameter = pParameter;
1411 }
1412
1413 return( true );
1414 }
1415 }
1416
1417 return( false );
1418}
1419
1420//---------------------------------------------------------
1421bool CSG_Tool_Chain::Tool_Get_Parameter(const CSG_MetaData &Parameter, CSG_Tool *pTool, CSG_Parameter **ppParameter, CSG_Parameter **ppOwner)
1422{
1423 CSG_String ID(Parameter.Get_Property("parms"));
1424
1425 if( !ID.is_Empty() )
1426 {
1427 ID += '.';
1428 }
1429
1430 ID += Parameter.Get_Property("id");
1431
1432 //-----------------------------------------------------
1433 CSG_Parameter *pOwner; if( !ppOwner ) { ppOwner = &pOwner; } *ppOwner = NULL;
1434
1435 CSG_Parameters *pParameters = pTool->Get_Parameters(ID.BeforeFirst('.'));
1436
1437 if( pParameters )
1438 {
1439 ID = ID.AfterFirst('.');
1440 }
1441 else
1442 {
1443 pParameters = pTool->Get_Parameters();
1444 }
1445
1446 return( Tool_Get_Parameter(ID, pParameters, ppParameter, ppOwner) );
1447}
1448
1449//---------------------------------------------------------
1450bool CSG_Tool_Chain::Tool_Initialize(const CSG_MetaData &Tool, CSG_Tool *pTool)
1451{
1452 //-----------------------------------------------------
1453 for(int i=0; i<Tool.Get_Children_Count(); i++) // check for invalid parameters...
1454 {
1455 const CSG_MetaData &Parameter = Tool[i]; if( Parameter.Cmp_Name("comment") ) { continue; }
1456
1457 if( Parameter.Cmp_Name("message") )
1458 {
1459 Message(Parameter);
1460
1461 continue;
1462 }
1463
1464 CSG_Parameter *pParameter, *pOwner;
1465
1466 if( !Tool_Get_Parameter(Parameter, pTool, &pParameter, &pOwner) )
1467 {
1468 Error_Fmt("%s: %s", _TL("parameter not found"), Parameter.Get_Property("id"));
1469
1470 return( false );
1471 }
1472 }
1473
1474 //-----------------------------------------------------
1475 if( Tool.Get_Property("grid_system") )
1476 {
1477 CSG_Parameter *pParameter = Parameters(Tool.Get_Property("grid_system"));
1478
1479 if( pParameter && pParameter->asGrid_System() )
1480 {
1481 if( !pTool->Set_Grid_System(*pParameter->asGrid_System()) )
1482 {
1483 Message_Fmt("\n%s: %s\n", _TL("Warning"), _TL("failed to set tool's grid system"));
1484 }
1485 }
1486 }
1487
1488 //-----------------------------------------------------
1489 for(int i=0; i<Tool.Get_Children_Count(); i++) // initialize all options first, some might en-/disable mandatory input data
1490 {
1491 const CSG_MetaData &Parameter = Tool[i]; if( !Parameter.Cmp_Name("option") ) { continue; }
1492
1493 CSG_Parameter *pParameter, *pOwner; Tool_Get_Parameter(Parameter, pTool, &pParameter, &pOwner);
1494
1495 if( pParameter->Get_Type() == PARAMETER_TYPE_Grid_System )
1496 {
1497 CSG_Parameter *pData = m_Data(Parameter.Get_Content());
1498
1499 if( pData && pData->asDataObject() && pData->asDataObject()->asGrid() && pData->asDataObject()->asGrid()->Get_System().is_Valid() )
1500 {
1501 pParameter->asGrid_System()->Create(pData->asDataObject()->asGrid()->Get_System());
1502
1503 continue;
1504 }
1505 }
1506
1507 if( IS_TRUE_PROPERTY(Parameter, "varname")
1508 ? pParameter->Set_Value(Parameters(Parameter.Get_Content()))
1509 : pParameter->Set_Value( Parameter.Get_Content() ) )
1510 {
1511 pParameter->has_Changed(); if( pOwner ) { pOwner->has_Changed(); }
1512 }
1513 }
1514
1515 //-----------------------------------------------------
1516 for(int i=0; i<Tool.Get_Children_Count(); i++) // set data input first
1517 {
1518 const CSG_MetaData &Parameter = Tool[i]; if( !Parameter.Cmp_Name("input") ) { continue; }
1519
1520 CSG_Parameter *pParameter, *pOwner; Tool_Get_Parameter(Parameter, pTool, &pParameter, &pOwner);
1521
1522 int Index;
1523
1524 if( Parameter.Get_Content().Find('[') < 1 || !Parameter.Get_Content().AfterFirst('[').asInt(Index) )
1525 {
1526 Index = -1;
1527 }
1528
1529 bool bResult = false;
1530
1531 CSG_Parameter *pData = m_Data(Index < 0 ? Parameter.Get_Content() : Parameter.Get_Content().BeforeFirst('['));
1532
1533 if( pData && (pParameter->is_DataObject() || pParameter->is_DataObject_List()) )
1534 {
1535 if( Index >= 0 && (pData->is_DataObject_List() || pData->asGrids()) )
1536 {
1537 CSG_Data_Object *pObject = pData->is_DataObject_List()
1538 ? pData->asList ()->Get_Item (Index)
1539 : pData->asGrids()->Get_Grid_Ptr(Index);
1540
1541 if( pParameter->is_DataObject() )
1542 {
1543 bResult = pParameter->Set_Value(pObject);
1544 }
1545 if( pParameter->is_DataObject_List() )
1546 {
1547 bResult = pParameter->asList()->Add_Item(pObject);
1548 }
1549 }
1550 else if( pParameter->Get_Type() == pData->Get_Type() )
1551 {
1552 if( pParameter->is_DataObject_List() && pParameter->asList()->Get_Item_Count() > 0 )
1553 {
1554 bResult = true;
1555
1556 for(int i=0; bResult && i<pData->asList()->Get_Item_Count(); i++)
1557 {
1558 bResult = pParameter->asList()->Add_Item(pData->asList()->Get_Item(i));
1559 }
1560 }
1561 else
1562 {
1563 bResult = pParameter->Assign(pData);
1564 }
1565 }
1566 else if( pParameter->is_DataObject_List() && pData->is_DataObject() )
1567 {
1568 bResult = pParameter->asList()->Add_Item(pData->asDataObject());
1569 }
1570 else if( Parameter_isCompatible(pParameter->Get_Type(), pData->Get_Type()) )
1571 {
1572 bResult = pParameter->Set_Value(pData->asDataObject());
1573 }
1574 }
1575
1576 if( bResult )
1577 {
1578 pParameter->has_Changed(); if( pOwner ) { pOwner->has_Changed(); }
1579 }
1580 else if( pParameter->is_Enabled() )
1581 {
1582 Error_Fmt("%s: %s", _TL("set input"), Parameter.Get_Property("id"));
1583
1584 return( false );
1585 }
1586 }
1587
1588 //-----------------------------------------------------
1589 for(int i=0; i<Tool.Get_Children_Count(); i++) // now set all options
1590 {
1591 const CSG_MetaData &Parameter = Tool[i]; if( !Parameter.Cmp_Name("option") ) { continue; }
1592
1593 CSG_Parameter *pParameter, *pOwner; Tool_Get_Parameter(Parameter, pTool, &pParameter, &pOwner);
1594
1595 if( IS_TRUE_PROPERTY(Parameter, "varname") )
1596 { // does option want a value from tool chain parameters and do these provide one ?
1597 switch( pParameter->Get_Type() )
1598 {
1599 default:
1600 pParameter->Set_Value(Parameters(Parameter.Get_Content()));
1601 break;
1602
1604 if( m_Data(Parameter.Get_Content()) && pParameter->asTable()->Assign_Values(m_Data(Parameter.Get_Content())->asTable()) )
1605 {
1606 pParameter->has_Changed();
1607 }
1608 break;
1609 }
1610 }
1611 else
1612 {
1613 switch( pParameter->Get_Type() )
1614 {
1616 if( Parameter("OPTION") )
1617 {
1618 pParameter->Serialize(*Parameter("OPTION"), false);
1619 }
1620 break;
1621
1622 default: {
1623 CSG_String Value(Parameter.Get_Content());
1624
1625 if( Value.Find("$(") >= 0 )
1626 {
1627 for(int j=0; j<Parameters.Get_Count(); j++)
1628 {
1629 CSG_String Var; Var.Printf("$(%s)", Parameters(j)->Get_Identifier());
1630
1631 if( Value.Find(Var) >= 0 )
1632 {
1633 Value.Replace(Var, Parameters(j)->asString());
1634 }
1635 }
1636 }
1637
1638 pParameter->Set_Value(Value);
1639
1640 if( pOwner )
1641 {
1642 pOwner->has_Changed();
1643 }
1644
1645 break; }
1646 }
1647 }
1648 }
1649
1650 //-----------------------------------------------------
1651 for(int i=0; i<Tool.Get_Children_Count(); i++) // finally set the data output
1652 {
1653 const CSG_MetaData &Parameter = Tool[i]; if( !Parameter.Cmp_Name("output") ) { continue; }
1654
1655 CSG_Parameter *pParameter, *pOwner; Tool_Get_Parameter(Parameter, pTool, &pParameter, &pOwner);
1656
1657 if( !pParameter->Assign(m_Data(Parameter.Get_Content())) )
1658 {
1659 if( pParameter->is_DataObject() )
1660 {
1661 pParameter->Set_Value(DATAOBJECT_CREATE);
1662 }
1663 else if( pParameter->is_DataObject_List() )
1664 {
1665 pParameter->asList()->Del_Items();
1666 }
1667 else if( pParameter->asGrids() )
1668 {
1669 pParameter->asGrids()->Del_Grids();
1670 }
1671 }
1672 }
1673
1674 //-----------------------------------------------------
1675 return( true );
1676}
1677
1678//---------------------------------------------------------
1679bool CSG_Tool_Chain::Tool_Finalize(const CSG_MetaData &Tool, CSG_Tool *pTool)
1680{
1681 for(int i=0; i<Tool.Get_Children_Count(); i++) // add all data objects declared as output to variable list
1682 {
1683 const CSG_MetaData &Parameter = Tool[i];
1684
1685 if( Parameter.Cmp_Name("output") && !Parameter.Get_Content().is_Empty() )
1686 { // content provides parameter id used in tool chain ...if empty, it is not requested and can be ignored!
1687 CSG_String ID (Parameter.Get_Property("id" ));
1688 CSG_String ID_parms(Parameter.Get_Property("parms"));
1689
1690 CSG_Parameter *pParameter = pTool->Get_Parameters(ID_parms)
1691 ? (*pTool->Get_Parameters(ID_parms))(ID)
1692 : (*pTool->Get_Parameters( ))(ID);
1693
1694 if( !pParameter || !Data_Add(Parameter.Get_Content(), pParameter) )
1695 {
1696 return( false );
1697 }
1698 }
1699 }
1700
1701 //-----------------------------------------------------
1702 for(int i=-1; i<pTool->Get_Parameters_Count(); i++) // save memory: free all data objects that have not been added to variable list
1703 {
1704 CSG_Parameters *pParameters = i < 0 ? pTool->Get_Parameters() : pTool->Get_Parameters(i);
1705
1706 for(int j=0; j<pParameters->Get_Count(); j++)
1707 {
1708 CSG_Parameter *pParameter = (*pParameters)(j);
1709
1710 if( pParameter->is_Output() )
1711 {
1712 if( pParameter->is_DataObject() )
1713 {
1714 if( !Data_Exists(pParameter->asDataObject()) )
1715 {
1716 m_Data_Manager.Delete(pParameter->asDataObject());
1717 }
1718 }
1719 else if( pParameter->is_DataObject_List() )
1720 {
1721 for(int k=0; k<pParameter->asList()->Get_Item_Count(); k++)
1722 {
1723 if( !Data_Exists(pParameter->asList()->Get_Item(k)) )
1724 {
1725 m_Data_Manager.Delete(pParameter->asList()->Get_Item(k));
1726 }
1727 }
1728 }
1729 }
1730 }
1731 }
1732
1733 //-----------------------------------------------------
1734 return( true );
1735}
1736
1737
1739// //
1740// //
1741// //
1743
1744//---------------------------------------------------------
1745CSG_String CSG_Tool_Chain::Get_Script(CSG_Tool *pTool, bool bHeader, bool bAllParameters)
1746{
1747 CSG_MetaData Tool; Tool.Set_Name("tool");
1748
1749 Tool.Add_Property("library", pTool->Get_Library());
1750 Tool.Add_Property("tool" , pTool->Get_ID ());
1751 Tool.Add_Property("name" , pTool->Get_Name ());
1752
1753 _Get_Script_Tool(Tool, pTool->Get_Parameters(), bAllParameters, "", bHeader);
1754
1755 for(int i=0; i<pTool->Get_Parameters_Count(); i++)
1756 {
1757 _Get_Script_Tool(Tool, pTool->Get_Parameters(i), bAllParameters, pTool->Get_Parameters(i)->Get_Identifier() + '.', bHeader);
1758 }
1759
1760 if( !bHeader )
1761 {
1762 return( Tool.asText(1) );
1763 }
1764
1765 //-----------------------------------------------------
1767
1768 _Get_Script_Parameters(Parameters, pTool->Get_Parameters(), "");
1769
1770 for(int i=0; i<pTool->Get_Parameters_Count(); i++)
1771 {
1772 _Get_Script_Parameters(Parameters, pTool->Get_Parameters(i), pTool->Get_Parameters(i)->Get_Identifier() + '.');
1773 }
1774
1775 //-----------------------------------------------------
1776 CSG_MetaData Tools; Tools.Set_Name("toolchain");
1777
1778 Tools.Add_Property("saga-version", SAGA_VERSION);
1779
1780 Tools.Add_Child("group" );
1781 Tools.Add_Child("identifier" , "define-a-unique-tool-identifier-here");
1782 Tools.Add_Child("name" , pTool->Get_Name() + " [Tool Chain]");
1783 Tools.Add_Child("author" );
1784 Tools.Add_Child("description");
1785 Tools.Add_Child("menu" , pTool->Get_MenuPath(true))->Add_Property("absolute", "true");
1786 Tools.Add_Child("crs_sync" , "true");
1787 Tools.Add_Child("parameters" )->Add_Children(Parameters);
1788 Tools.Add_Child("tools" )->Add_Child(Tool);
1789 Tools ("tools" )->Add_Property("history", "false");
1790
1791 return( Tools.asText(1) );
1792}
1793
1794//---------------------------------------------------------
1795bool CSG_Tool_Chain::_Get_Script_Tool(CSG_MetaData &Tool, CSG_Parameters *pParameters, bool bAllParameters, const CSG_String &Prefix, bool bVarNames)
1796{
1797 for(int iParameter=0; iParameter<pParameters->Get_Count(); iParameter++)
1798 {
1799 CSG_Parameter &P = *pParameters->Get_Parameter(iParameter);
1800
1801 if( !bAllParameters && (!P.is_Enabled(false) || P.is_Information()) )
1802 {
1803 continue;
1804 }
1805
1806 CSG_MetaData *pChild = NULL;
1807
1808 switch( P.Get_Type() )
1809 {
1811 _Get_Script_Tool(Tool, P.asParameters(), bAllParameters, Prefix + P.Get_Identifier() + '.', true);
1812 break;
1813
1814 case PARAMETER_TYPE_Bool :
1815 pChild = Tool.Add_Child("option", P.asBool() ? "true" : "false");
1816 break;
1817
1818 case PARAMETER_TYPE_Int :
1821 case PARAMETER_TYPE_Date :
1824 case PARAMETER_TYPE_Text :
1829 pChild = Tool.Add_Child("option", P.asString());
1830 break;
1831
1834 pChild = Tool.Add_Child("option", P.asInt());
1835 break;
1836
1838 pChild = Tool.Add_Child("option");
1839 P.Serialize(*pChild, true);
1840 break;
1841
1843 if( P.Get_Children_Count() == 0 )
1844 {
1845 pChild = Tool.Add_Child("option", P.asString());
1846 }
1847 break;
1848
1849 default:
1850 if( P.is_Input() )
1851 {
1852 pChild = Tool.Add_Child("input");
1853 pChild->Set_Content(P.is_Optional() ? "INPUT_OPTIONAL" : "INPUT");
1854 }
1855 else if( P.is_Output() )
1856 {
1857 pChild = Tool.Add_Child("output");
1858 pChild->Set_Content("OUTPUT");
1859 }
1860 break;
1861 }
1862
1863 if( pChild )
1864 {
1865 pChild->Add_Property("id", Prefix + P.Get_Identifier());
1866
1867 if( bVarNames )
1868 {
1869 if( P.is_Option() )
1870 {
1871 pChild->Add_Property("varname", "true");
1872 }
1873
1874 pChild->Set_Content(Prefix + P.Get_Identifier());
1875 }
1876 }
1877 }
1878
1879 return( true );
1880}
1881
1882//---------------------------------------------------------
1883bool CSG_Tool_Chain::_Get_Script_Parameters(CSG_MetaData &Parameters, CSG_Parameters *pParameters, const CSG_String &Prefix)
1884{
1885 for(int i=0; i<pParameters->Get_Count(); i++)
1886 {
1887 CSG_Parameter &P = *pParameters->Get_Parameter(i);
1888
1890 {
1891 _Get_Script_Parameters(Parameters, P.asParameters(), Prefix + P.Get_Identifier() + '.');
1892
1893 continue; // no support for sub-parameter-lists in here
1894 }
1895
1896 CSG_MetaData &Parameter = *Parameters.Add_Child(
1897 P.is_Option() ? "option" :
1898 P.is_Output() ? "output" : "input"
1899 );
1900
1901 Parameter.Add_Property("varname" , P.Get_Identifier ());
1903 Parameter.Add_Child ("name" , P.Get_Name ());
1904 Parameter.Add_Child ("description", P.Get_Description());
1905
1906 if( P.Get_Parent() )
1907 {
1908 Parameter.Add_Property("parent", P.Get_Parent()->Get_Identifier());
1909 }
1910
1911 if( P.Get_Type() == PARAMETER_TYPE_Node
1913 {
1914 continue; // nothing more to do for these types
1915 }
1916
1917 if( P.is_Option() )
1918 {
1919 CSG_MetaData &Value = *Parameter.Add_Child("value", P.asString());
1920
1921 if( P.asValue() )
1922 {
1923 if( P.asValue()->has_Minimum() ) Value.Add_Property("min", P.asValue()->Get_Minimum());
1924 if( P.asValue()->has_Maximum() ) Value.Add_Property("max", P.asValue()->Get_Maximum());
1925 }
1926
1927 if( P.asChoice () ) Parameter.Add_Child("choices", P.asChoice ()->Get_Items());
1928 if( P.asChoices() ) Parameter.Add_Child("choices", P.asChoices()->Get_Items());
1929
1930 if( P.asFilePath() )
1931 {
1932 Parameter.Add_Property("save" , P.asFilePath()->is_Save () ? "true" : "false");
1933 Parameter.Add_Property("directory", P.asFilePath()->is_Directory() ? "true" : "false");
1934 Parameter.Add_Property("multiple" , P.asFilePath()->is_Multiple () ? "true" : "false");
1935 Parameter.Add_Child ("filter" , P.asFilePath()->Get_Filter());
1936 }
1937
1939 {
1940 P.Serialize(Parameter, true);
1941 }
1942
1944 {
1945 Value.Set_Content(P.is_Optional() ? "true" : "false");
1946 }
1947 }
1948 else // data objects
1949 {
1950 if( P.is_Optional() )
1951 {
1952 Parameter.Add_Property("optional", "true");
1953 }
1954
1956 {
1957 switch( ((CSG_Parameter_Data_Object_Output *)&P)->Get_DataObject_Type() )
1958 {
1961 Parameter.Add_Property("target", "none");
1962 break;
1963
1966 Parameter.Add_Property("target", "none");
1967 break;
1968
1969 default:
1970 break;
1971 }
1972 }
1973
1974 if( P.Get_Type() == PARAMETER_TYPE_Shapes )
1975 {
1976 switch( ((CSG_Parameter_Shapes *)&P)->Get_Shape_Type() )
1977 {
1978 case SHAPE_TYPE_Point : Parameter.Add_Property("feature_type", "point" ); break;
1979 case SHAPE_TYPE_Points : Parameter.Add_Property("feature_type", "points" ); break;
1980 case SHAPE_TYPE_Line : Parameter.Add_Property("feature_type", "line" ); break;
1981 case SHAPE_TYPE_Polygon: Parameter.Add_Property("feature_type", "polygon"); break;
1982 default: break;
1983 }
1984 }
1985
1987 && !((CSG_Parameter_Grid_List *)&P)->Get_System() )
1988 {
1989 Parameter.Add_Property("no_system", "true");
1990 }
1991
1993 && !((CSG_Parameter_Grid_List *)&P)->Get_System() )
1994 {
1995 Parameter.Add_Property("no_system", "true");
1996 }
1997 }
1998 }
1999
2000 return( true );
2001}
2002
2003
2005// //
2006// //
2007// //
2009
2010//---------------------------------------------------------
2012{
2013 m_Library_Name = Library_Name;
2014
2015 //-----------------------------------------------------
2016 if( m_Library_Name.is_Empty() || !m_Library_Name.Cmp("toolchains") )
2017 {
2018 m_Library_Name = "_tool_chains_uncategorized";
2019 m_Name = _TL("Uncategorized Tool Chains");
2020 m_Description = _TL("Uncategorized Tool Chains");
2021 m_Menu = _TL("Uncategorized Tool Chains");
2022 }
2023
2024 //-----------------------------------------------------
2025 else
2026 {
2027 CSG_MetaData XML(SG_File_Make_Path(Path, Library_Name, "xml"));
2028
2029 if( !XML.Cmp_Name("toolchains") )
2030 {
2031 XML.Destroy();
2032 }
2033
2034 m_Name = GET_XML_CONTENT(XML, "name" , m_Library_Name , true);
2035 m_Description = GET_XML_CONTENT(XML, "description", _TL("no description"), true);
2036 m_Menu = GET_XML_CONTENT(XML, "menu" , _TL("Tool Chains" ), true);
2037
2038 m_Description.Replace("[[", "<"); // support for xml/html tags
2039 m_Description.Replace("]]", ">");
2040
2041 // add references...
2042 for(int i=0; i<XML.Get_Children_Count(); i++)
2043 {
2044 if( !XML[i].Get_Name().CmpNoCase("REFERENCE") )
2045 {
2046 CSG_String Authors, Year, Title, Where, Link, Link_Text, DOI;
2047
2048 if( XML[i]("AUTHORS" ) ) Authors = XML[i].Get_Content("AUTHORS" );
2049 if( XML[i]("YEAR" ) ) Year = XML[i].Get_Content("YEAR" );
2050 if( XML[i]("TITLE" ) ) Title = XML[i].Get_Content("TITLE" );
2051 if( XML[i]("WHERE" ) ) Where = XML[i].Get_Content("WHERE" );
2052 if( XML[i]("LINK" ) ) Link = XML[i].Get_Content("LINK" );
2053 if( XML[i]("LINK_TEXT") ) Link_Text = XML[i].Get_Content("LINK_TEXT");
2054 if( XML[i]("DOI" ) ) DOI = XML[i].Get_Content("DOI" );
2055
2056 if( !DOI.is_Empty() )
2057 {
2058 Link = "https://doi.org/" + DOI; Link_Text = "doi:" + DOI;
2059 }
2060
2061 if( !Authors.is_Empty() && !Year.is_Empty() && !Title.is_Empty() )
2062 {
2063 Add_Reference(Authors, Year, Title, Where, Link.c_str(), Link_Text.c_str());
2064 }
2065 else if( !Link.is_Empty() )
2066 {
2067 Add_Reference(Link, Link_Text.c_str());
2068 }
2069 }
2070 }
2071 }
2072}
2073
2074//---------------------------------------------------------
2076{
2077 Delete_Tools();
2078
2079 for(size_t i=0; i<m_Tools.Get_uSize(); i++)
2080 {
2081 delete((CSG_Tool_Chain *)m_Tools[i]);
2082 }
2083}
2084
2085
2087// //
2089
2090//---------------------------------------------------------
2092{
2093 static CSG_String Dummy, Category;
2094
2095 switch( Type )
2096 {
2097 case TLB_INFO_Name : return( m_Name );
2098 case TLB_INFO_Description: return( m_Description );
2099 case TLB_INFO_Menu_Path : return( m_Menu );
2100 case TLB_INFO_Category : Category = _TL("Tool Chains"); return( Category );
2101 }
2102
2103 return( Dummy );
2104}
2105
2106//---------------------------------------------------------
2108{
2109 m_Tools.Add(pTool);
2110
2112
2113 return( true );
2114}
2115
2116//---------------------------------------------------------
2118{
2119 CSG_Tool *pTool = Index >= 0 && Index < Get_Count() ? (CSG_Tool_Chain *)m_Tools[Index] : NULL;
2120
2121 return( pTool && (Type == TOOL_TYPE_Base || Type == pTool->Get_Type()) ? pTool : NULL );
2122}
2123
2124
2126// //
2128
2129//---------------------------------------------------------
2130CSG_Tool * CSG_Tool_Chains::Create_Tool(const CSG_String &Name, bool bWithGUI, bool bWithCMD)
2131{
2132 CSG_Tool *pTool = CSG_Tool_Library::Get_Tool(Name);
2133
2134 if( pTool && pTool->Get_Type() == TOOL_TYPE_Chain )
2135 {
2136 m_xTools.Add(pTool = new CSG_Tool_Chain(*((CSG_Tool_Chain *)pTool), bWithGUI, bWithCMD));
2137
2138 return( pTool );
2139 }
2140
2141 return( NULL );
2142}
2143
2144//---------------------------------------------------------
2146{
2147 if( m_xTools.Del(pTool) || m_Tools.Del(pTool) )
2148 {
2149 delete((CSG_Tool_Chain *)pTool);
2150
2151 return( true );
2152 }
2153
2154 return( false );
2155}
2156
2157//---------------------------------------------------------
2159{
2160 for(size_t i=0; i<m_xTools.Get_uSize(); i++)
2161 {
2162 delete((CSG_Tool_Chain *)m_xTools[i]);
2163 }
2164
2165 m_xTools.Destroy();
2166
2167 return( true );
2168}
2169
2170
2172// //
2173// //
2174// //
2176
2177//---------------------------------------------------------
2179{
2180 if( SG_Compare_Version(History.Get_Property("saga-version"), "2.1.3") < 0 || !(History("TOOL") || History("MODULE")) )
2181 {
2182 return( false );
2183 }
2184
2185 const CSG_MetaData &Tool(History("TOOL") ? History["TOOL"] : History["MODULE"]);
2186
2187 if( !Tool("OUTPUT") )
2188 {
2189 return( false );
2190 }
2191
2192 //-----------------------------------------------------
2194
2195 Chain.Set_Name ("toolchain" );
2196 Chain.Add_Property("saga-version", SAGA_VERSION);
2197
2198 Chain.Add_Child ("group" , "toolchains");
2199 Chain.Add_Child ("identifier" , SG_File_Get_Name(File, false));
2200 Chain.Add_Child ("name" , SG_File_Get_Name(File, false));
2201 Chain.Add_Child ("description", _TL("created from history"));
2202
2203 Chain.Add_Child ("parameters" );
2204 Chain.Add_Child ("tools" );
2205
2206 _Save_History_Add_Tool(Tool, *Chain("parameters"), *Chain("tools"), true);
2207
2208 for(int i=0; i<Chain["tools"].Get_Children_Count(); i++)
2209 {
2210 Chain["tools"](i)->Del_Property("id");
2211 }
2212
2213 return( Chain.Save(File) );
2214}
2215
2216//---------------------------------------------------------
2217bool CSG_Tool_Chain::_Save_History_Add_Tool(const CSG_MetaData &History, CSG_MetaData &Parms, CSG_MetaData &Tools, bool bAddOutput)
2218{
2219 if( !History("OUTPUT") || !History["OUTPUT"].Get_Property("id") )
2220 {
2221 return( false );
2222 }
2223
2224 //-----------------------------------------------------
2225 CSG_MetaData *pParameter, &Tool = *Tools.Ins_Child("tool", 0);
2226
2227 CSG_String Tool_ID(CSG_String::Format("tool_%02d", Tools.Get_Children_Count()));
2228
2229 Tool.Add_Property("id" , Tool_ID);
2230 Tool.Add_Property("library", History.Get_Property("library"));
2231 Tool.Add_Property("tool" , History.Get_Property("id" ));
2232 Tool.Add_Property("name" , History.Get_Property("name" ));
2233
2234 //-----------------------------------------------------
2235 const CSG_MetaData &Output = History["OUTPUT"];
2236
2237 CSG_String VarName = CSG_String::Format("%s__%s", Tool_ID.c_str(), Output.Get_Property("id"));
2238
2239 pParameter = Tool.Add_Child("output", VarName);
2240 pParameter->Add_Property("parms", Output.Get_Property("parms"));
2241 pParameter->Add_Property("id" , Output.Get_Property("id" ));
2242
2243 if( bAddOutput )
2244 {
2245 pParameter = Parms.Add_Child("output");
2246
2247 pParameter->Add_Property("varname" , VarName);
2248 pParameter->Add_Property("type" , Output.Get_Property("type"));
2249 pParameter->Add_Child ("name" , Output.Get_Property("name"));
2250 // pParameter->Add_Child ("description", Output.Get_Property("name"));
2251 }
2252
2253 //-----------------------------------------------------
2254 for(int i=0; i<History.Get_Children_Count(); i++) // Options and Input
2255 {
2256 CSG_MetaData *pChild = History.Get_Child(i);
2257
2258 if( !pChild->Get_Name().Cmp("OPTION") )
2259 {
2260 pParameter = NULL;
2261
2262 switch( SG_Parameter_Type_Get_Type(pChild->Get_Property("type")) )
2263 {
2264 case PARAMETER_TYPE_Bool :
2265 case PARAMETER_TYPE_Int :
2268 case PARAMETER_TYPE_Date :
2271 case PARAMETER_TYPE_Text :
2276 pParameter = Tool.Add_Child("option", pChild->Get_Content());
2277 break;
2278
2281 pParameter = Tool.Add_Child("option", pChild->Get_Property("index"));
2282 break;
2283
2285 if( pChild->Get_Children_Count() == 0 )
2286 {
2287 pParameter = Tool.Add_Child("option", pChild->Get_Content());
2288 }
2289 break;
2290
2291 default: break;
2292 }
2293
2294 if( pParameter )
2295 {
2296 pParameter->Add_Property("parms", pChild->Get_Property("parms"));
2297 pParameter->Add_Property("id" , pChild->Get_Property("id" ));
2298 }
2299 }
2300 else if( !pChild->Get_Name().Cmp("INPUT") )
2301 {
2302 _Save_History_Add_Input(*pChild, Parms, Tool);
2303 }
2304 else if( !pChild->Get_Name().Cmp("INPUT_LIST") )
2305 {
2306 for(int j=0; j<pChild->Get_Children_Count(); j++)
2307 {
2308 _Save_History_Add_Input(*pChild->Get_Child(j), Parms, Tool);
2309 }
2310 }
2311 }
2312
2313 return( true );
2314}
2315
2316//---------------------------------------------------------
2317bool CSG_Tool_Chain::_Save_History_Add_Input(const CSG_MetaData &History, CSG_MetaData &Parms, CSG_MetaData &Tool)
2318{
2319 CSG_MetaData *pInput = Tool.Add_Child("input");
2320
2321 pInput->Add_Property("parms", History.Get_Property("parms"));
2322 pInput->Add_Property("id" , History.Get_Property("id" ));
2323
2324 if( History("TOOL") || History("MODULE") )
2325 {
2326 const CSG_MetaData &History_Tool(History("TOOL") ? History["TOOL"] : History["MODULE"]);
2327
2328 if( History_Tool("OUTPUT") && History_Tool["OUTPUT"].Get_Property("id") )
2329 {
2330 pInput->Fmt_Content("tool_%02d__%s", Tool.Get_Parent()->Get_Children_Count() + 1, History_Tool["OUTPUT"].Get_Property("id"));
2331
2332 return( _Save_History_Add_Tool(History_Tool, Parms, *Tool.Get_Parent()) );
2333 }
2334 }
2335
2336 CSG_String VarName = CSG_String::Format("%s__%s", Tool.Get_Property("id"), History.Get_Property("id"));
2337
2338 pInput->Set_Content(VarName);
2339
2340 CSG_MetaData *pParameter = Parms.Ins_Child("input", 0);
2341
2342 pParameter->Add_Property("varname" , VarName);
2343 pParameter->Add_Property("type" , History.Get_Property("type"));
2344 pParameter->Add_Child ("name" , History.Get_Property("name"));
2345// pParameter->Add_Child ("description", History.Get_Property("name"));
2346
2347 return( true );
2348}
2349
2350
2352// //
2353// //
2354// //
2356
2357//---------------------------------------------------------
void SG_UI_Msg_Add(const char *Message, bool bNewLine, TSG_UI_MSG_STYLE Style)
bool SG_UI_DataObject_Add(CSG_Data_Object *pDataObject, int Show)
@ SG_UI_MSG_STYLE_FAILURE
Definition api_core.h:1627
@ SG_UI_MSG_STYLE_SUCCESS
Definition api_core.h:1626
SAGA_API_DLL_EXPORT bool SG_File_Cmp_Extension(const CSG_String &File, const CSG_String &Extension)
SAGA_API_DLL_EXPORT const SG_Char * SG_Translate(const CSG_String &Text)
#define SG_T(s)
Definition api_core.h:537
SAGA_API_DLL_EXPORT CSG_String SG_File_Make_Path(const CSG_String &Directory, const CSG_String &Name)
SAGA_API_DLL_EXPORT CSG_String SG_File_Get_Name(const CSG_String &full_Path, bool bExtension)
@ SG_UI_DATAOBJECT_SHOW_MAP
Definition api_core.h:1640
@ SG_UI_DATAOBJECT_UPDATE
Definition api_core.h:1639
#define SG_Char
Definition api_core.h:536
#define _TL(s)
Definition api_core.h:1610
size_t Get_uSize(void) const
Definition api_core.h:437
const SG_Char * Get_Name(void) const
void Set_Name(const CSG_String &Name)
virtual bool is_Valid(void) const =0
class CSG_Grid * asGrid(bool bPolymorph=false) const
bool Create(const CSG_Grid_System &System, int Precision=-1)
bool is_Valid(void) const
const CSG_Grid_System & Get_System(void) const
Definition grid.h:559
bool Del_Grids(bool bDetach=false)
Definition grids.cpp:891
CSG_Grid * Get_Grid_Ptr(int i) const
Definition grids.h:263
void Fmt_Content(const char *Format,...)
Definition metadata.cpp:510
bool Cmp_Name(const CSG_String &String, bool bNoCase=true) const
Definition metadata.cpp:461
const CSG_String & Get_Name(void) const
Definition metadata.h:132
int Get_Children_Count(void) const
Definition metadata.h:148
CSG_MetaData * Get_Child(int Index) const
Definition metadata.h:149
bool Set_Property(const CSG_String &Name, const CSG_String &Value, bool bAddIfNotExists=true)
Definition metadata.cpp:615
bool Cmp_Property(const CSG_String &Name, const CSG_String &String, bool bNoCase=false) const
Definition metadata.cpp:671
bool Add_Children(const CSG_MetaData &MetaData)
Definition metadata.cpp:359
CSG_MetaData * Get_Parent(void) const
Definition metadata.h:145
const CSG_String & Get_Content(void) const
Definition metadata.h:133
const SG_Char * Get_Property(int Index) const
Definition metadata.h:181
void Set_Name(const CSG_String &Name)
Definition metadata.h:130
CSG_String asText(int Flags=0) const
Definition metadata.cpp:698
void Set_Content(const CSG_String &Content)
Definition metadata.h:140
CSG_MetaData * Add_Child(void)
Definition metadata.cpp:166
void Destroy(void)
Definition metadata.cpp:140
CSG_MetaData * Ins_Child(int Position)
Definition metadata.cpp:207
bool Add_Property(const CSG_String &Name, const CSG_String &Value)
Definition metadata.cpp:559
CSG_String Get_Items(bool bIncludeData=false) const
CSG_String Get_Items(void) const
virtual TSG_Parameter_Type Get_Type(void) const
bool is_Directory(void) const
Definition parameters.h:877
bool is_Multiple(void) const
Definition parameters.h:874
bool is_Save(void) const
Definition parameters.h:871
bool Get_FilePaths(CSG_Strings &FilePaths) const
const SG_Char * Get_Filter(void) const
virtual TSG_Parameter_Type Get_Type(void) const
virtual bool Del_Items(void)
CSG_Data_Object * Get_Item(int Index) const
virtual bool Add_Item(CSG_Data_Object *pItem)
int Get_Item_Count(void) const
CSG_Parameter_Double * Get_Min_Parameter(void) const
Definition parameters.h:628
CSG_Parameter_Double * Get_Max_Parameter(void) const
Definition parameters.h:632
virtual TSG_Parameter_Type Get_Type(void) const
double Get_Minimum(void) const
Definition parameters.h:448
double Get_Maximum(void) const
Definition parameters.h:452
bool has_Maximum(void) const
Definition parameters.h:453
bool has_Minimum(void) const
Definition parameters.h:449
const SG_Char * Get_Identifier(void) const
bool is_DataObject(void) const
class CSG_Parameters * asParameters(void) const
bool Assign(CSG_Parameter *pSource)
CSG_Grids * asGrids(void) const
CSG_String Get_Type_Identifier(void) const
bool is_Optional(void) const
Definition parameters.h:238
TSG_Data_Object_Type Get_DataObject_Type(void) const
bool Serialize(CSG_MetaData &MetaData, bool bSave)
int Get_Children_Count(void) const
Definition parameters.h:259
class CSG_Parameter_Choice * asChoice(void) const
class CSG_Parameter_Value * asValue(void) const
double asDouble(void) const
Definition parameters.h:289
CSG_Parameter * Get_Parent(void) const
virtual TSG_Parameter_Type Get_Type(void) const =0
bool asBool(void) const
Definition parameters.h:286
bool is_Input(void) const
Definition parameters.h:236
const SG_Char * Get_Name(void) const
class CSG_Parameter_Choices * asChoices(void) const
bool is_Enabled(bool bCheckEnv=true) const
bool is_Option(void) const
virtual bool Set_Value(int Value)
class CSG_Parameter_List * asList(void) const
CSG_Grid_System * asGrid_System(void) const
CSG_Data_Object * asDataObject(void) const
class CSG_Parameter_Range * asRange(void) const
bool is_Output(void) const
Definition parameters.h:237
bool has_Changed(int Check_Flags=PARAMETER_CHECK_ALL)
class CSG_Parameter_File_Name * asFilePath(void) const
bool is_Information(void) const
Definition parameters.h:239
const SG_Char * asString(void) const
Definition parameters.h:290
CSG_Table * asTable(void) const
const SG_Char * Get_Description(void) const
bool is_DataObject_List(void) const
int asInt(void) const
Definition parameters.h:287
const CSG_String & Get_Identifier(void) const
int Get_Count(void) const
bool Del_Parameters(void)
CSG_Parameter * Get_Parameter(int i) const
CSG_String AfterFirst(char Character) const
int CmpNoCase(const CSG_String &String) const
int Cmp(const CSG_String &String) const
void Clear(void)
CSG_String BeforeFirst(char Character) const
size_t Replace(const CSG_String &Old, const CSG_String &New, bool bReplaceAll=true)
static CSG_String Format(const char *Format,...)
int Find(char Character, bool fromEnd=false) const
CSG_String Right(size_t count) const
int asInt(void) const
const SG_Char * c_str(void) const
CSG_String & Make_Lower(void)
int Printf(const char *Format,...)
bool is_Empty(void) const
double asDouble(void) const
int Get_Count(void) const
Definition api_core.h:719
bool Assign_Values(const CSG_Table &Table)
Definition table.cpp:378
virtual int On_Parameters_Enable(CSG_Parameters *pParameters, CSG_Parameter *pParameter)
bool is_Okay(void) const
Definition tool_chain.h:96
void Set_Library_Menu(const CSG_String &Menu)
static CSG_String Get_Script(CSG_Tool *pTool, bool bHeader, bool bAllParameters=true)
bool Create(const CSG_Tool_Chain &Tool, bool bWithGUI, bool bWithCMD)
virtual ~CSG_Tool_Chain(void)
virtual bool On_Execute(void)
static bool Save_History_to_Model(const CSG_MetaData &History, const CSG_String &File)
virtual bool do_Sync_Projections(void) const
virtual CSG_Tool * Create_Tool(const CSG_String &Name, bool bWithGUI=false, bool bWithCMD=true)
virtual ~CSG_Tool_Chains(void)
CSG_Tool_Chains(const CSG_String &Library_Name, const CSG_String &Path)
virtual int Get_Count(void) const
Definition tool_chain.h:185
virtual const CSG_String & Get_Info(int Type) const
virtual bool Delete_Tools(void)
virtual bool Delete_Tool(CSG_Tool *pTool)
bool Add_Tool(CSG_Tool_Chain *pTool)
virtual CSG_Tool * Get_Tool(int Index, TSG_Tool_Type Type=TOOL_TYPE_Base) const
bool Delete_Tool(CSG_Tool *pTool) const
CSG_Tool * Create_Tool(const CSG_String &Library, int Index, bool bWithGUI=false, bool bWithCMD=true) const
void Add_Reference(const CSG_String &Authors, const CSG_String &Date, const CSG_String &Title, const CSG_String &Source, const CSG_String &Link="", const CSG_String &Link_Text="")
virtual CSG_Tool * Get_Tool(int Index, TSG_Tool_Type Type=TOOL_TYPE_Base) const
const CSG_String & Get_Name(void) const
CSG_String m_Library_Name
const CSG_String & Get_Library(void) const
Definition tool.cpp:129
bool Del_References(void)
Definition tool.cpp:321
bool Set_Grid_System(const CSG_Grid_System &System)
Definition tool.cpp:1725
int Get_Parameters_Count(void) const
Definition tool.h:177
virtual bool On_After_Execution(void)
Definition tool.h:240
bool Settings_Pop(void)
Definition tool.cpp:938
bool has_GUI(void) const
Definition tool.cpp:274
CSG_Parameters * Get_Parameters(void)
Definition tool.h:175
void Add_Reference(const CSG_String &Authors, const CSG_String &Date, const CSG_String &Title, const CSG_String &Source, const CSG_String &Link="", const CSG_String &Link_Text="")
Definition tool.cpp:294
static bool DataObject_Set_Colors(CSG_Data_Object *pDataObject, const CSG_Colors &Colors)
Definition tool.cpp:1305
const CSG_String & Get_Name(void) const
Definition tool.cpp:146
static void Process_Set_Text(const CSG_String &Text)
Definition tool.cpp:1156
bool Settings_Push(class CSG_Data_Manager *pManager=NULL)
Definition tool.cpp:925
virtual bool On_Before_Execution(void)
Definition tool.h:239
CSG_Parameters Parameters
Definition tool.h:266
virtual TSG_Tool_Type Get_Type(void) const
Definition tool.h:148
CSG_Tool(void)
Definition tool.cpp:67
virtual CSG_String Get_MenuPath(void)
Definition tool.h:167
void Set_Description(const CSG_String &String)
Definition tool.cpp:174
static bool DataObject_Set_Parameters(CSG_Data_Object *pDataObject, CSG_Parameters &Parameters)
Definition tool.cpp:1326
bool Execute(bool bAddHistory=false)
Definition tool.cpp:562
void Message_Fmt(const char *Format,...)
Definition tool.cpp:1225
void Set_Author(const CSG_String &String)
Definition tool.cpp:152
const CSG_String & Get_Description(void) const
Definition tool.cpp:188
const CSG_String & Get_ID(void) const
Definition tool.h:150
bool Error_Set(TSG_Tool_Error Error_ID=TOOL_ERROR_Unknown)
Definition tool.cpp:1009
bool Error_Fmt(const char *Format,...)
Definition tool.cpp:1046
virtual int On_Parameters_Enable(CSG_Parameters *pParameters, CSG_Parameter *pParameter)
Definition tool.cpp:786
void Set_Version(const CSG_String &String)
Definition tool.cpp:163
void Message_Dlg(const CSG_String &Text, const SG_Char *Caption=NULL)
Definition tool.cpp:997
void Set_Name(const CSG_String &String)
Definition tool.cpp:141
@ SG_DATAOBJECT_TYPE_PointCloud
Definition dataobject.h:123
@ SG_DATAOBJECT_TYPE_Grids
Definition dataobject.h:119
@ SG_DATAOBJECT_TYPE_TIN
Definition dataobject.h:122
@ SG_DATAOBJECT_TYPE_Shapes
Definition dataobject.h:121
@ SG_DATAOBJECT_TYPE_Grid
Definition dataobject.h:118
@ SG_DATAOBJECT_TYPE_Table
Definition dataobject.h:120
#define DATAOBJECT_CREATE
Definition dataobject.h:130
#define B
#define A
TSG_Parameter_Type SG_Parameter_Type_Get_Type(const CSG_String &Identifier)
CSG_String SG_Parameter_Type_Get_Identifier(TSG_Parameter_Type Type)
#define PARAMETER_INPUT_OPTIONAL
Definition parameters.h:103
#define PARAMETER_OUTPUT_OPTIONAL
Definition parameters.h:104
TSG_Parameter_Type
Definition parameters.h:123
@ PARAMETER_TYPE_Degree
Definition parameters.h:129
@ PARAMETER_TYPE_FixedTable
Definition parameters.h:142
@ PARAMETER_TYPE_Node
Definition parameters.h:124
@ PARAMETER_TYPE_Grid
Definition parameters.h:149
@ PARAMETER_TYPE_Grid_List
Definition parameters.h:155
@ PARAMETER_TYPE_Text
Definition parameters.h:136
@ PARAMETER_TYPE_TIN
Definition parameters.h:153
@ PARAMETER_TYPE_Table
Definition parameters.h:151
@ PARAMETER_TYPE_Int
Definition parameters.h:127
@ PARAMETER_TYPE_Table_Fields
Definition parameters.h:146
@ PARAMETER_TYPE_Grids
Definition parameters.h:150
@ PARAMETER_TYPE_Color
Definition parameters.h:140
@ PARAMETER_TYPE_Colors
Definition parameters.h:141
@ PARAMETER_TYPE_DataObject_Output
Definition parameters.h:162
@ PARAMETER_TYPE_Table_List
Definition parameters.h:157
@ PARAMETER_TYPE_Double
Definition parameters.h:128
@ PARAMETER_TYPE_TIN_List
Definition parameters.h:159
@ PARAMETER_TYPE_Grid_System
Definition parameters.h:144
@ PARAMETER_TYPE_Font
Definition parameters.h:139
@ PARAMETER_TYPE_Date
Definition parameters.h:130
@ PARAMETER_TYPE_PointCloud_List
Definition parameters.h:160
@ PARAMETER_TYPE_Choices
Definition parameters.h:134
@ PARAMETER_TYPE_Data_Type
Definition parameters.h:132
@ PARAMETER_TYPE_Shapes
Definition parameters.h:152
@ PARAMETER_TYPE_Shapes_List
Definition parameters.h:158
@ PARAMETER_TYPE_Range
Definition parameters.h:131
@ PARAMETER_TYPE_PointCloud
Definition parameters.h:148
@ PARAMETER_TYPE_Table_Field
Definition parameters.h:145
@ PARAMETER_TYPE_Parameters
Definition parameters.h:164
@ PARAMETER_TYPE_FilePath
Definition parameters.h:137
@ PARAMETER_TYPE_Bool
Definition parameters.h:126
@ PARAMETER_TYPE_Grids_List
Definition parameters.h:156
@ PARAMETER_TYPE_String
Definition parameters.h:135
@ PARAMETER_TYPE_Choice
Definition parameters.h:133
#define PARAMETER_OUTPUT
Definition parameters.h:95
#define PARAMETER_INPUT
Definition parameters.h:94
int SG_Compare_Version(const CSG_String &Version, int Major, int Minor, int Release)
Definition saga_api.cpp:82
#define SAGA_VERSION
@ SHAPE_TYPE_Polygon
Definition shapes.h:105
@ SHAPE_TYPE_Line
Definition shapes.h:104
@ SHAPE_TYPE_Points
Definition shapes.h:103
@ SHAPE_TYPE_Point
Definition shapes.h:102
@ SHAPE_TYPE_Undefined
Definition shapes.h:101
@ TLB_INFO_Menu_Path
Definition tool.h:661
@ TLB_INFO_Name
Definition tool.h:657
@ TLB_INFO_Category
Definition tool.h:662
@ TLB_INFO_Description
Definition tool.h:658
TSG_Tool_Type
Definition tool.h:101
@ TOOL_TYPE_Base
Definition tool.h:102
@ TOOL_TYPE_Chain
Definition tool.h:106
#define IS_TRUE_PROPERTY(Item, Property)
#define IS_TRUE_STRING(String)
#define GET_XML_CONTENT(XML, ID, DEFAULT, TRANSLATE)
CSG_Tool_Library_Manager & SG_Get_Tool_Library_Manager(void)