pyedb 0.47.1__py3-none-any.whl → 0.49.0__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of pyedb might be problematic. Click here for more details.

Files changed (37) hide show
  1. pyedb/__init__.py +1 -1
  2. pyedb/configuration/cfg_stackup.py +35 -1
  3. pyedb/configuration/configuration.py +13 -13
  4. pyedb/dotnet/database/cell/hierarchy/component.py +61 -5
  5. pyedb/dotnet/database/cell/hierarchy/s_parameter_model.py +7 -0
  6. pyedb/dotnet/database/cell/primitive/primitive.py +8 -1
  7. pyedb/dotnet/database/cell/terminal/terminal.py +25 -7
  8. pyedb/dotnet/database/components.py +87 -46
  9. pyedb/dotnet/database/definition/package_def.py +29 -5
  10. pyedb/dotnet/database/dotnet/database.py +18 -0
  11. pyedb/dotnet/database/edb_data/padstacks_data.py +25 -5
  12. pyedb/dotnet/database/edb_data/ports.py +14 -0
  13. pyedb/dotnet/database/edb_data/utilities.py +1 -1
  14. pyedb/dotnet/database/geometry/polygon_data.py +15 -2
  15. pyedb/dotnet/database/hfss.py +11 -1
  16. pyedb/dotnet/database/materials.py +78 -0
  17. pyedb/dotnet/database/modeler.py +21 -10
  18. pyedb/dotnet/database/padstack.py +7 -5
  19. pyedb/dotnet/database/sim_setup_data/data/mesh_operation.py +24 -0
  20. pyedb/dotnet/database/siwave.py +37 -33
  21. pyedb/dotnet/database/utilities/simulation_setup.py +51 -9
  22. pyedb/dotnet/database/utilities/siwave_simulation_setup.py +3 -1
  23. pyedb/dotnet/edb.py +67 -8
  24. pyedb/grpc/database/components.py +19 -13
  25. pyedb/grpc/database/hfss.py +3 -3
  26. pyedb/grpc/database/modeler.py +4 -4
  27. pyedb/grpc/database/padstacks.py +3 -1
  28. pyedb/grpc/database/ports/ports.py +4 -0
  29. pyedb/grpc/database/primitive/path.py +2 -2
  30. pyedb/grpc/database/primitive/primitive.py +6 -1
  31. pyedb/grpc/database/source_excitations.py +16 -8
  32. pyedb/grpc/database/terminal/bundle_terminal.py +1 -1
  33. pyedb/grpc/edb.py +125 -32
  34. {pyedb-0.47.1.dist-info → pyedb-0.49.0.dist-info}/METADATA +1 -1
  35. {pyedb-0.47.1.dist-info → pyedb-0.49.0.dist-info}/RECORD +37 -37
  36. {pyedb-0.47.1.dist-info → pyedb-0.49.0.dist-info}/LICENSE +0 -0
  37. {pyedb-0.47.1.dist-info → pyedb-0.49.0.dist-info}/WHEEL +0 -0
@@ -261,21 +261,25 @@ class EdbSiwave(object):
261
261
  >>> edbapp.siwave.create_circuit_port_on_pin(pins[0], pins[1], 50, "port_name")
262
262
  """
263
263
  circuit_port = CircuitPort()
264
- circuit_port.positive_node.net = pos_pin.GetNet().GetName()
265
- circuit_port.negative_node.net = neg_pin.GetNet().GetName()
264
+ if not isinstance(pos_pin, EDBPadstackInstance):
265
+ pos_pin = EDBPadstackInstance(pos_pin, self._pedb)
266
+ if not isinstance(neg_pin, EDBPadstackInstance):
267
+ neg_pin = EDBPadstackInstance(neg_pin, self._pedb)
268
+ circuit_port.positive_node.net = pos_pin.net_name
269
+ circuit_port.negative_node.net = neg_pin.net_name
266
270
  circuit_port.impedance = impedance
267
271
 
268
272
  if not port_name:
269
273
  port_name = "Port_{}_{}_{}_{}".format(
270
- pos_pin.GetComponent().GetName(),
271
- pos_pin.GetNet().GetName(),
272
- neg_pin.GetComponent().GetName(),
273
- neg_pin.GetNet().GetName(),
274
+ pos_pin.component.name,
275
+ pos_pin.net_name,
276
+ neg_pin.component.name,
277
+ neg_pin.net_name,
274
278
  )
275
279
  circuit_port.name = port_name
276
- circuit_port.positive_node.component_node = pos_pin.GetComponent()
280
+ circuit_port.positive_node.component_node = pos_pin.component
277
281
  circuit_port.positive_node.node_pins = pos_pin
278
- circuit_port.negative_node.component_node = neg_pin.GetComponent()
282
+ circuit_port.negative_node.component_node = neg_pin.component
279
283
  circuit_port.negative_node.node_pins = neg_pin
280
284
  return self._create_terminal_on_pins(circuit_port)
281
285
 
@@ -386,22 +390,22 @@ class EdbSiwave(object):
386
390
  """
387
391
 
388
392
  voltage_source = VoltageSource()
389
- voltage_source.positive_node.net = pos_pin.GetNet().GetName()
390
- voltage_source.negative_node.net = neg_pin.GetNet().GetName()
393
+ voltage_source.positive_node.net = pos_pin.net_name
394
+ voltage_source.negative_node.net = neg_pin.net_name
391
395
  voltage_source.magnitude = voltage_value
392
396
  voltage_source.phase = phase_value
393
397
  if not source_name:
394
398
  source_name = "VSource_{}_{}_{}_{}".format(
395
- pos_pin.GetComponent().GetName(),
396
- pos_pin.GetNet().GetName(),
397
- neg_pin.GetComponent().GetName(),
398
- neg_pin.GetNet().GetName(),
399
+ pos_pin.component.name,
400
+ pos_pin.net_name,
401
+ neg_pin.component.name,
402
+ neg_pin.net_name,
399
403
  )
400
404
  voltage_source.name = source_name
401
- voltage_source.positive_node.component_node = pos_pin.GetComponent()
405
+ voltage_source.positive_node.component_node = pos_pin.component
402
406
  voltage_source.positive_node.node_pins = pos_pin
403
- voltage_source.negative_node.component_node = neg_pin.GetComponent()
404
- voltage_source.negative_node.node_pins = pos_pin
407
+ voltage_source.negative_node.component_node = neg_pin.component
408
+ voltage_source.negative_node.node_pins = neg_pin
405
409
  return self._create_terminal_on_pins(voltage_source)
406
410
 
407
411
  def create_current_source_on_pin(self, pos_pin, neg_pin, current_value=0.1, phase_value=0, source_name=""):
@@ -434,21 +438,21 @@ class EdbSiwave(object):
434
438
  >>> edbapp.siwave.create_current_source_on_pin(pins[0], pins[1], 50, "source_name")
435
439
  """
436
440
  current_source = CurrentSource()
437
- current_source.positive_node.net = pos_pin.GetNet().GetName()
438
- current_source.negative_node.net = neg_pin.GetNet().GetName()
441
+ current_source.positive_node.net = pos_pin.net_name
442
+ current_source.negative_node.net = neg_pin.net_name
439
443
  current_source.magnitude = current_value
440
444
  current_source.phase = phase_value
441
445
  if not source_name:
442
446
  source_name = "ISource_{}_{}_{}_{}".format(
443
- pos_pin.GetComponent().GetName(),
444
- pos_pin.GetNet().GetName(),
445
- neg_pin.GetComponent().GetName(),
446
- neg_pin.GetNet().GetName(),
447
+ pos_pin.component.name,
448
+ pos_pin.net_name,
449
+ neg_pin.component.name,
450
+ neg_pin.net_name,
447
451
  )
448
452
  current_source.name = source_name
449
- current_source.positive_node.component_node = pos_pin.GetComponent()
453
+ current_source.positive_node.component_node = pos_pin.component
450
454
  current_source.positive_node.node_pins = pos_pin
451
- current_source.negative_node.component_node = neg_pin.GetComponent()
455
+ current_source.negative_node.component_node = neg_pin.component
452
456
  current_source.negative_node.node_pins = neg_pin
453
457
  return self._create_terminal_on_pins(current_source)
454
458
 
@@ -480,20 +484,20 @@ class EdbSiwave(object):
480
484
  >>> edbapp.siwave.create_resistor_on_pin(pins[0], pins[1],50,"res_name")
481
485
  """
482
486
  resistor = ResistorSource()
483
- resistor.positive_node.net = pos_pin.GetNet().GetName()
484
- resistor.negative_node.net = neg_pin.GetNet().GetName()
487
+ resistor.positive_node.net = pos_pin.net_name
488
+ resistor.negative_node.net = neg_pin.net_name
485
489
  resistor.rvalue = rvalue
486
490
  if not resistor_name:
487
491
  resistor_name = "Res_{}_{}_{}_{}".format(
488
- pos_pin.GetComponent().GetName(),
489
- pos_pin.GetNet().GetName(),
490
- neg_pin.GetComponent().GetName(),
491
- neg_pin.GetNet().GetName(),
492
+ pos_pin.component.name,
493
+ pos_pin.net_name,
494
+ neg_pin.component.name,
495
+ neg_pin.net_name,
492
496
  )
493
497
  resistor.name = resistor_name
494
- resistor.positive_node.component_node = pos_pin.GetComponent()
498
+ resistor.positive_node.component_node = pos_pin.component
495
499
  resistor.positive_node.node_pins = pos_pin
496
- resistor.negative_node.component_node = neg_pin.GetComponent()
500
+ resistor.negative_node.component_node = neg_pin.component
497
501
  resistor.negative_node.node_pins = neg_pin
498
502
  return self._create_terminal_on_pins(resistor)
499
503
 
@@ -109,6 +109,11 @@ class SimulationSetup(object):
109
109
  warnings.warn("Use new property :func:`sim_setup_info` instead.", DeprecationWarning)
110
110
  return self.sim_setup_info._edb_object
111
111
 
112
+ @property
113
+ def is_null(self):
114
+ """Adding this property for compatibility with grpc."""
115
+ return self._edb_object.IsNull()
116
+
112
117
  def get_simulation_settings(self):
113
118
  sim_settings = self.sim_setup_info.simulation_settings
114
119
  properties = {}
@@ -237,13 +242,43 @@ class SimulationSetup(object):
237
242
  """List of frequency sweeps."""
238
243
  return {i.name: i for i in self.sim_setup_info.sweep_data_list}
239
244
 
240
- def add_sweep(self, name: str = None, frequency_set: list = None, sweep_type: str = "interpolation", **kwargs):
245
+ @property
246
+ def sweep_data(self):
247
+ """Adding property for compatibility with grpc."""
248
+ return list(self.sweeps.values())
249
+
250
+ @sweep_data.setter
251
+ def sweep_data(self, sweep_data):
252
+ for sweep in self.sweep_data:
253
+ self.delete_frequency_sweep(sweep)
254
+ for sweep in sweep_data:
255
+ self._add_frequency_sweep(sweep)
256
+
257
+ def add_sweep(
258
+ self,
259
+ name: str = None,
260
+ distribution: str = None,
261
+ start_freq: str = None,
262
+ stop_freq: str = None,
263
+ step=None,
264
+ frequency_set: list = None,
265
+ sweep_type: str = "interpolation",
266
+ **kwargs,
267
+ ):
241
268
  """Add frequency sweep.
242
269
 
243
270
  Parameters
244
271
  ----------
245
272
  name : str, optional
246
273
  Name of the frequency sweep. The default is ``None``.
274
+ distribution : str, optional
275
+ Added for grpc compatibility.
276
+ start_freq : str, optional
277
+ Added for rpc compatibility.
278
+ stop_freq : str, optional
279
+ Added for grpc compatibility.
280
+ step : optional
281
+ Added for grpc compatibility.
247
282
  frequency_set : list, optional
248
283
  List of frequency points. The default is ``None``.
249
284
  sweep_type : str, optional
@@ -261,21 +296,28 @@ class SimulationSetup(object):
261
296
  raise ValueError("Sweep {} already exists.".format(name))
262
297
 
263
298
  sweep_data = SweepData(self._pedb, name=name, sim_setup=self)
264
- for k, v in kwargs.items():
265
- if k in dir(sweep_data):
266
- setattr(sweep_data, k, v)
267
- sweep_data.type = sweep_type
299
+ # adding grpc compatibility
300
+ if distribution and start_freq and stop_freq and step:
301
+ if distribution == "linear":
302
+ distribution = "linear_scale" # to be compatible with grpc
303
+ frequency_set = [[distribution, start_freq, stop_freq, step]]
268
304
 
269
305
  if frequency_set in [None, []]:
270
- sweep_type = "linear_scale"
306
+ distribution = "linear_scale"
271
307
  start, stop, increment = "50MHz", "5GHz", "50MHz"
272
- frequency_set = [[sweep_type, start, stop, increment]]
308
+ frequency_set = [[distribution, start, stop, increment]]
273
309
  elif not isinstance(frequency_set[0], list):
274
310
  frequency_set = [frequency_set]
275
311
 
276
312
  for fs in frequency_set:
277
- sweep_type, start, stop, increment = fs
278
- sweep_data.add(sweep_type, start, stop, increment)
313
+ distribution, start, stop, increment = fs
314
+ sweep_data.add(distribution, start, stop, increment)
315
+
316
+ for k, v in kwargs.items():
317
+ if k in dir(sweep_data):
318
+ setattr(sweep_data, k, v)
319
+ sweep_data.type = sweep_type
320
+
279
321
  return sweep_data
280
322
 
281
323
  def delete(self):
@@ -269,7 +269,9 @@ class SiwaveSimulationSetup(SimulationSetup):
269
269
  >>> setup1 = edbapp.create_siwave_syz_setup("setup1")
270
270
  >>> setup1.add_sweep(name="sw1", frequency_set=["linear count", "1MHz", "100MHz", 10])
271
271
  """
272
- sweep_data = SimulationSetup.add_sweep(self, name, frequency_set, sweep_type, **kwargs)
272
+ sweep_data = SimulationSetup.add_sweep(
273
+ self, name=name, frequency_set=frequency_set, sweep_type=sweep_type, **kwargs
274
+ )
273
275
  self._siwave_sweeps_list.append(sweep_data)
274
276
  return sweep_data
275
277
 
pyedb/dotnet/edb.py CHANGED
@@ -1451,13 +1451,28 @@ class Edb(Database):
1451
1451
  def close_edb(self):
1452
1452
  """Close EDB and cleanup variables.
1453
1453
 
1454
+ . deprecated:: pyedb 0.47.0
1455
+ Use: func:`close` instead.
1456
+
1457
+ Returns
1458
+ -------
1459
+ bool
1460
+ ``True`` when successful, ``False`` when failed.
1461
+
1462
+ """
1463
+ warnings.warn("Use new property :func:`close` instead.", DeprecationWarning)
1464
+ return self.close()
1465
+
1466
+ def close(self):
1467
+ """Close EDB and cleanup variables.
1468
+
1454
1469
  Returns
1455
1470
  -------
1456
1471
  bool
1457
1472
  ``True`` when successful, ``False`` when failed.
1458
1473
 
1459
1474
  """
1460
- self.close()
1475
+ Database.close(self)
1461
1476
 
1462
1477
  if self.log_name and settings.enable_local_log_file:
1463
1478
  self._logger.remove_all_file_loggers()
@@ -1471,25 +1486,62 @@ class Edb(Database):
1471
1486
  def save_edb(self):
1472
1487
  """Save the EDB file.
1473
1488
 
1489
+ . deprecated:: pyedb 0.47.0
1490
+ Use: func:`save` instead.
1491
+
1492
+ Returns
1493
+ -------
1494
+ bool
1495
+ ``True`` when successful, ``False`` when failed.
1496
+
1497
+ """
1498
+ warnings.warn("Use new method :func:`save` instead.", DeprecationWarning)
1499
+ return self.save()
1500
+
1501
+ def save(self):
1502
+ """Save the EDB file.
1503
+
1474
1504
  Returns
1475
1505
  -------
1476
1506
  bool
1477
1507
  ``True`` when successful, ``False`` when failed.
1478
1508
 
1479
1509
  """
1480
- self.save()
1510
+
1511
+ Database.save(self)
1481
1512
  start_time = time.time()
1482
1513
  self._wait_for_file_release()
1483
1514
  elapsed_time = time.time() - start_time
1484
1515
  self.logger.info("EDB file save time: {0:.2f}ms".format(elapsed_time * 1000.0))
1485
1516
  return True
1486
1517
 
1487
- def save_edb_as(self, fname):
1518
+ def save_edb_as(self, path):
1519
+ """Save the EDB file as another file.
1520
+
1521
+ . deprecated:: pyedb 0.47.0
1522
+ Use: func:`save_as` instead.
1523
+
1524
+
1525
+ Parameters
1526
+ ----------
1527
+ path : str
1528
+ Name of the new file to save to.
1529
+
1530
+ Returns
1531
+ -------
1532
+ bool
1533
+ ``True`` when successful, ``False`` when failed.
1534
+
1535
+ """
1536
+ warnings.warn("Use new property :func:`save_as` instead.", DeprecationWarning)
1537
+ return self.save_as(path)
1538
+
1539
+ def save_as(self, path, version=""):
1488
1540
  """Save the EDB file as another file.
1489
1541
 
1490
1542
  Parameters
1491
1543
  ----------
1492
- fname : str
1544
+ path : str
1493
1545
  Name of the new file to save to.
1494
1546
 
1495
1547
  Returns
@@ -1499,7 +1551,7 @@ class Edb(Database):
1499
1551
 
1500
1552
  """
1501
1553
  origin_name = "pyedb_" + os.path.splitext(os.path.split(self.edbpath)[-1])[0]
1502
- self.save_as(fname)
1554
+ Database.save_as(self, path)
1503
1555
  start_time = time.time()
1504
1556
  self._wait_for_file_release()
1505
1557
  elapsed_time = time.time() - start_time
@@ -1509,8 +1561,8 @@ class Edb(Database):
1509
1561
  self._logger.remove_file_logger(os.path.splitext(os.path.split(self.log_name)[-1])[0])
1510
1562
 
1511
1563
  self.log_name = os.path.join(
1512
- os.path.dirname(fname),
1513
- "pyedb_" + os.path.splitext(os.path.split(fname)[-1])[0] + ".log",
1564
+ os.path.dirname(path),
1565
+ "pyedb_" + os.path.splitext(os.path.split(path)[-1])[0] + ".log",
1514
1566
  )
1515
1567
  if settings.enable_local_log_file:
1516
1568
  self._logger.add_file_logger(self.log_name, "Edb")
@@ -1800,7 +1852,7 @@ class Edb(Database):
1800
1852
  output_aedb_path=None,
1801
1853
  open_cutout_at_end=True,
1802
1854
  use_pyaedt_cutout=True,
1803
- number_of_threads=4,
1855
+ number_of_threads=1,
1804
1856
  use_pyaedt_extent_computing=True,
1805
1857
  extent_defeature=0,
1806
1858
  remove_single_pin_components=False,
@@ -4668,3 +4720,10 @@ class Edb(Database):
4668
4720
  ET.indent(tree, space="\t", level=0)
4669
4721
  tree.write(control_path)
4670
4722
  return True if os.path.exists(control_path) else False
4723
+
4724
+ def get_variable_value(self, variable_name):
4725
+ """Added to get closer architecture as for grpc."""
4726
+ if variable_name in self.variables:
4727
+ return self.variables[variable_name].value
4728
+ else:
4729
+ return False
@@ -276,20 +276,26 @@ class Components(object):
276
276
  self._others = {}
277
277
  for i in self._pedb.layout.groups:
278
278
  self._cmp[i.name] = i
279
- if i.type == "resistor":
280
- self._res[i.name] = i
281
- elif i.type == "capacitor":
282
- self._cap[i.name] = i
283
- elif i.type == "inductor":
284
- self._ind[i.name] = i
285
- elif i.type == "ic":
286
- self._ics[i.name] = i
287
- elif i.type == "io":
288
- self._ios[i.name] = i
289
- elif i.type == "other":
279
+ try:
280
+ if i.type == "resistor":
281
+ self._res[i.name] = i
282
+ elif i.type == "capacitor":
283
+ self._cap[i.name] = i
284
+ elif i.type == "inductor":
285
+ self._ind[i.name] = i
286
+ elif i.type == "ic":
287
+ self._ics[i.name] = i
288
+ elif i.type == "io":
289
+ self._ios[i.name] = i
290
+ elif i.type == "other":
291
+ self._others[i.name] = i
292
+ else:
293
+ self._logger.warning(
294
+ f"Unknown component type {i.name} found while refreshing components, will ignore"
295
+ )
296
+ except:
297
+ self._logger.warning(f"Assigning component {i.name} as default type other.")
290
298
  self._others[i.name] = i
291
- else:
292
- self._logger.warning(f"Unknown component type {i.name} found while refreshing components, will ignore")
293
299
  return True
294
300
 
295
301
  @property
@@ -527,7 +527,7 @@ class Hfss(object):
527
527
  "`pyedb.grpc.core.excitations.create_differential_wave_port` instead.",
528
528
  DeprecationWarning,
529
529
  )
530
- return self._pedb.excitations.create_differential_wave_port(
530
+ return self._pedb.source_excitation.create_differential_wave_port(
531
531
  positive_primitive_id,
532
532
  positive_points_on_edge,
533
533
  negative_primitive_id,
@@ -579,7 +579,7 @@ class Hfss(object):
579
579
  "`pyedb.grpc.core.excitations.create_bundle_wave_port` instead.",
580
580
  DeprecationWarning,
581
581
  )
582
- self._pedb.excitations.create_bundle_wave_port(
582
+ return self._pedb.source_excitation.create_bundle_wave_port(
583
583
  primitives_id, points_on_edge, port_name, horizontal_extent_factor, vertical_extent_factor, pec_launch_width
584
584
  )
585
585
 
@@ -720,7 +720,7 @@ class Hfss(object):
720
720
  "`pyedb.grpc.core.excitations.create_source_on_component` instead.",
721
721
  DeprecationWarning,
722
722
  )
723
- self._pedb.source_excitation.create_wave_port(
723
+ return self._pedb.source_excitation.create_wave_port(
724
724
  prim_id,
725
725
  point_on_edge,
726
726
  port_name,
@@ -1272,7 +1272,7 @@ class Modeler(object):
1272
1272
  stat_model.num_resistors = len(self._pedb.components.resistors)
1273
1273
  stat_model.num_inductors = len(self._pedb.components.inductors)
1274
1274
  bbox = self._pedb._hfss.get_layout_bounding_box(self._active_layout)
1275
- stat_model._layout_size = bbox[2] - bbox[0], bbox[3] - bbox[1]
1275
+ stat_model._layout_size = round(bbox[2] - bbox[0], 6), round(bbox[3] - bbox[1], 6)
1276
1276
  stat_model.num_discrete_components = (
1277
1277
  len(self._pedb.components.Others) + len(self._pedb.components.ICs) + len(self._pedb.components.IOs)
1278
1278
  )
@@ -1283,7 +1283,7 @@ class Modeler(object):
1283
1283
  stat_model.num_traces = len(self._pedb.modeler.paths)
1284
1284
  stat_model.num_polygons = len(self._pedb.modeler.polygons)
1285
1285
  stat_model.num_vias = len(self._pedb.padstacks.instances)
1286
- stat_model.stackup_thickness = self._pedb.stackup.get_layout_thickness()
1286
+ stat_model.stackup_thickness = round(self._pedb.stackup.get_layout_thickness(), 6)
1287
1287
  if evaluate_area:
1288
1288
  outline_surface = stat_model.layout_size[0] * stat_model.layout_size[1]
1289
1289
  if net_list:
@@ -1298,8 +1298,8 @@ class Modeler(object):
1298
1298
  surface += Path(self._pedb, prim).length * prim.cast().width.value
1299
1299
  if prim.primitive_type.name == "POLYGON":
1300
1300
  surface += prim.polygon_data.area()
1301
- stat_model.occupying_surface[layer] = surface
1302
- stat_model.occupying_ratio[layer] = surface / outline_surface
1301
+ stat_model.occupying_surface[layer] = round(surface, 6)
1302
+ stat_model.occupying_ratio[layer] = round(surface / outline_surface, 6)
1303
1303
  return stat_model
1304
1304
 
1305
1305
  def create_bondwire(
@@ -506,7 +506,9 @@ class Padstacks(object):
506
506
  "`pyedb.grpc.core.excitations.create_coax_port` instead.",
507
507
  DeprecationWarning,
508
508
  )
509
- self._pedb.excitations.create_coax_port(self, padstackinstance, use_dot_separator=use_dot_separator, name=name)
509
+ self._pedb.source_excitation.create_coax_port(
510
+ self, padstackinstance, use_dot_separator=use_dot_separator, name=name
511
+ )
510
512
 
511
513
  def get_pin_from_component_and_net(self, refdes=None, netname=None):
512
514
  """Retrieve pins given a component's reference designator and net name.
@@ -108,6 +108,10 @@ class GapPort(EdgeTerminal):
108
108
  self._edb_object.port_post_processing_prop.renormalizion_z0[1],
109
109
  )
110
110
 
111
+ @property
112
+ def terminal_type(self):
113
+ return self._edb_object.terminal_type
114
+
111
115
 
112
116
  class CircuitPort(GapPort):
113
117
  """Manages gap port properties.
@@ -62,7 +62,7 @@ class Path(GrpcPath, Primitive):
62
62
  """
63
63
  center_line_arcs = self._edb_object.cast().center_line.arc_data
64
64
  path_length = 0.0
65
- for arc in center_line_arcs:
65
+ for arc in center_line_arcs[: int(len(center_line_arcs) / 2)]:
66
66
  path_length += arc.length
67
67
  end_cap_style = self.get_end_cap_style()
68
68
  if end_cap_style:
@@ -181,7 +181,7 @@ class Path(GrpcPath, Primitive):
181
181
  # )
182
182
  # else:
183
183
  return self._pedb.hfss.create_edge_port_vertical(
184
- self.id,
184
+ self.edb_uid,
185
185
  pos,
186
186
  name,
187
187
  50,
@@ -253,7 +253,12 @@ class Primitive(GrpcPrimitive):
253
253
 
254
254
  """
255
255
  bbox = self.cast().polygon_data.bbox()
256
- return [bbox[0].x.value, bbox[0].y.value, bbox[1].x.value, bbox[1].y.value]
256
+ return [
257
+ round(bbox[0].x.value, 6),
258
+ round(bbox[0].y.value, 6),
259
+ round(bbox[1].x.value, 6),
260
+ round(bbox[1].y.value, 6),
261
+ ]
257
262
 
258
263
  def convert_to_polygon(self):
259
264
  """Convert path to polygon.
@@ -353,6 +353,14 @@ class SourceExcitation:
353
353
  >>> port_type=SourceType.CoaxPort, do_pingroup=False, refnet="GND")
354
354
 
355
355
  """
356
+ if isinstance(port_type, int):
357
+ # Adding DotNet backward compatibility with SourceType
358
+ type_mapping = {0: "coax_port", 1: "circuit_port"}
359
+ if port_type in type_mapping:
360
+ port_type = type_mapping[port_type]
361
+ else:
362
+ self._logger.error(f"unsupported port type with method.")
363
+ return False
356
364
  if isinstance(component, str):
357
365
  component = self._pedb.components.instances[component]
358
366
  if not isinstance(net_list, list):
@@ -395,7 +403,7 @@ class SourceExcitation:
395
403
  "outside the component when not found if argument extend_reference_pins_outside_component is True."
396
404
  )
397
405
  return False
398
- pad_params = self._pedb.padstack.get_pad_parameters(pin=cmp_pins[0], layername=pin_layers[0], pad_type=0)
406
+ pad_params = self._pedb.padstacks.get_pad_parameters(pin=cmp_pins[0], layername=pin_layers[0], pad_type=0)
399
407
  if not pad_params[0] == 7:
400
408
  if not solder_balls_size: # pragma no cover
401
409
  sball_diam = min([GrpcValue(val).value for val in pad_params[1]])
@@ -431,7 +439,7 @@ class SourceExcitation:
431
439
  shape=sball_shape,
432
440
  )
433
441
  for pin in cmp_pins:
434
- self._pedb.padstack.create_coax_port(padstackinstance=pin, name=port_name)
442
+ self._pedb.source_excitation.create_coax_port(padstackinstance=pin, name=port_name)
435
443
 
436
444
  elif port_type == "circuit_port": # pragma no cover
437
445
  ref_pins = [p for p in list(component.pins.values()) if p.net_name in reference_net]
@@ -794,7 +802,7 @@ class SourceExcitation:
794
802
  port_name = generate_unique_name(port_name, n=2)
795
803
  self._logger.info("An existing port already has this same name. Renaming to {}.".format(port_name))
796
804
  PadstackInstanceTerminal.create(
797
- layout=self._pedb._active_layout,
805
+ layout=self._pedb.active_layout,
798
806
  name=port_name,
799
807
  padstack_instance=padstackinstance,
800
808
  layer=terminal_layer,
@@ -831,7 +839,7 @@ class SourceExcitation:
831
839
  terminal_name = generate_unique_name("Terminal_")
832
840
  if isinstance(point_on_edge, tuple):
833
841
  point_on_edge = GrpcPointData(point_on_edge)
834
- prim = [i for i in self._pedb.modeler.primitives if i.id == prim_id]
842
+ prim = [i for i in self._pedb.modeler.primitives if i.edb_uid == prim_id]
835
843
  if not prim:
836
844
  self._pedb.logger.error(f"No primitive found for ID {prim_id}")
837
845
  return False
@@ -1580,10 +1588,10 @@ class SourceExcitation:
1580
1588
  port_name = generate_unique_name("diff")
1581
1589
 
1582
1590
  if isinstance(positive_primitive_id, Primitive):
1583
- positive_primitive_id = positive_primitive_id.id
1591
+ positive_primitive_id = positive_primitive_id.edb_uid
1584
1592
 
1585
1593
  if isinstance(negative_primitive_id, Primitive):
1586
- negative_primitive_id = negative_primitive_id.id
1594
+ negative_primitive_id = negative_primitive_id.edb_uid
1587
1595
 
1588
1596
  _, pos_term = self.create_wave_port(
1589
1597
  positive_primitive_id,
@@ -1652,7 +1660,7 @@ class SourceExcitation:
1652
1660
  port_name = generate_unique_name("Terminal_")
1653
1661
 
1654
1662
  if isinstance(prim_id, Primitive):
1655
- prim_id = prim_id.id
1663
+ prim_id = prim_id.edb_uid
1656
1664
  pos_edge_term = self._create_edge_terminal(prim_id, point_on_edge, port_name)
1657
1665
  pos_edge_term.impedance = GrpcValue(impedance)
1658
1666
  wave_port = WavePort(self._pedb, pos_edge_term)
@@ -2027,7 +2035,7 @@ class SourceExcitation:
2027
2035
  port_name = generate_unique_name("bundle_port")
2028
2036
 
2029
2037
  if isinstance(primitives_id[0], Primitive):
2030
- primitives_id = [i.id for i in primitives_id]
2038
+ primitives_id = [i.edb_uid for i in primitives_id]
2031
2039
 
2032
2040
  terminals = []
2033
2041
  _port_name = port_name
@@ -46,7 +46,7 @@ class BundleTerminal(GrpcBundleTerminal):
46
46
  """
47
47
 
48
48
  def __init__(self, pedb, edb_object):
49
- super().__init__(edb_object)
49
+ super().__init__(edb_object.msg)
50
50
  self._pedb = pedb
51
51
  self._edb_object = edb_object
52
52