Exemple #1
0
def test_coordinate_system_manager_with_data(copy_arrays, lazy_load):
    """Test if data attached to a CSM is stored and read correctly."""
    csm = tf.CoordinateSystemManager("root", "csm")
    csm.create_cs("cs_1", "root", coordinates=[1, 1, 1])
    csm.create_cs("cs_2", "root", coordinates=[-1, -1, -1])
    csm.create_cs("cs_11", "cs_1", coordinates=[1, 1, 1])

    data_11 = SpatialData(
        coordinates=np.array([[1.0, 2.0, 3.0], [3.0, 2.0, 1.0]]))
    data_2 = SpatialData(
        coordinates=np.array([
            [0.0, 0.0, 0.0],
            [1.0, 0.0, 0.0],
            [1.0, 1.0, 0.0],
            [0.0, 1.0, 0.0],
        ]),
        triangles=np.array([[0, 1, 2], [0, 2, 3]], dtype="uint32"),
    )

    csm.assign_data(data_11, "data_11", "cs_11")
    csm.assign_data(data_2, "data_2", "cs_2")

    tree = {"csm": csm}
    buffer = write_read_buffer(tree,
                               open_kwargs={
                                   "copy_arrays": copy_arrays,
                                   "lazy_load": lazy_load
                               })
    csm_buffer = buffer["csm"]

    for data_name in csm.data_names:
        sd = csm.get_data(data_name)
        sd_buffer = csm_buffer.get_data(data_name)
        assert sd == sd_buffer
Exemple #2
0
def test_coordinate_system_manager_time_dependencies(copy_arrays, lazy_load,
                                                     csm_time_ref):
    """Test serialization of time components from CSM and its attached LCS."""
    lcs_tdp_1_time_ref = None
    if csm_time_ref is None:
        lcs_tdp_1_time_ref = pd.Timestamp("2000-03-17")
    lcs_tdp_1 = tf.LocalCoordinateSystem(
        coordinates=[[1, 2, 3], [4, 5, 6]],
        time=pd.TimedeltaIndex([1, 2], "D"),
        time_ref=lcs_tdp_1_time_ref,
    )
    lcs_tdp_2 = tf.LocalCoordinateSystem(
        coordinates=[[3, 7, 3], [9, 5, 8]],
        time=pd.TimedeltaIndex([1, 2], "D"),
        time_ref=pd.Timestamp("2000-03-21"),
    )

    csm_root = tf.CoordinateSystemManager("root", "csm_root", csm_time_ref)
    csm_root.add_cs("cs_1", "root", lcs_tdp_2)

    csm_sub_1 = tf.CoordinateSystemManager("cs_2", "csm_sub_1", csm_time_ref)
    csm_sub_1.add_cs("cs_1", "cs_2", lcs_tdp_2)
    csm_sub_1.add_cs("cs_3", "cs_2", lcs_tdp_1)

    csm_sub_2 = tf.CoordinateSystemManager("cs_4", "csm_sub_2")
    csm_sub_2.create_cs("cs_1", "cs_4")

    csm_root.merge(csm_sub_1)
    csm_root.merge(csm_sub_2)

    tree = {"cs_hierarchy": csm_root}
    data = write_read_buffer(tree,
                             open_kwargs={
                                 "copy_arrays": copy_arrays,
                                 "lazy_load": lazy_load
                             })
    csm_file = data["cs_hierarchy"]
    assert csm_root == csm_file
Exemple #3
0
def get_example_coordinate_system_manager():
    """Get a consistent CoordinateSystemManager instance for test purposes."""
    csm = tf.CoordinateSystemManager("root")
    csm.create_cs("lcs_01", "root", coordinates=[1, 2, 3])
    csm.create_cs(
        "lcs_02",
        "root",
        orientation=WXRotation.from_euler("z", np.pi / 3).as_matrix(),
        coordinates=[4, -7, 8],
    )
    csm.create_cs(
        "lcs_03",
        "lcs_02",
        orientation=WXRotation.from_euler("y", np.pi / 11),
        coordinates=[4, -7, 8],
    )
    return csm
Exemple #4
0
def get_coordinate_system_manager_with_subsystems(nested: bool):
    lcs = [
        tf.LocalCoordinateSystem(coordinates=[i, -i, -i]) for i in range(12)
    ]

    # create global system
    csm_global = tf.CoordinateSystemManager("base", "Global System",
                                            "2000-06-08")
    csm_global.add_cs("robot", "base", lcs[0])
    csm_global.add_cs("specimen", "base", lcs[1])

    # robot system
    csm_robot = tf.CoordinateSystemManager("robot", "Robot system")
    csm_robot.add_cs("head", "robot", lcs[2])

    # robot head system
    csm_head = tf.CoordinateSystemManager("head", "Head system")
    csm_head.add_cs("torch tcp", "head", lcs[3])
    csm_head.add_cs("camera tcp", "head", lcs[4], lsc_child_in_parent=False)
    csm_head.add_cs("scanner 1 tcp", "head", lcs[5])
    csm_head.add_cs("scanner 2 tcp", "head", lcs[6])

    # scanner system 1
    csm_scanner_1 = tf.CoordinateSystemManager("scanner 1", "Scanner 1 system")
    csm_scanner_1.add_cs("scanner 1 tcp", "scanner 1", lcs[7])

    # scanner system 2
    csm_scanner_2 = tf.CoordinateSystemManager("scanner 2", "Scanner 2 system")
    csm_scanner_2.add_cs("scanner 2 tcp", "scanner 2", lcs[8])

    # specimen system
    csm_specimen = tf.CoordinateSystemManager("specimen", "Specimen system")
    csm_specimen.add_cs("thermocouple 1", "specimen", lcs[9])
    csm_specimen.add_cs("thermocouple 2", "specimen", lcs[10])
    csm_specimen.add_cs("thermocouple 3", "thermocouple 2", lcs[11])

    if nested:
        csm_head.merge(csm_scanner_1)
        csm_head.merge(csm_scanner_2)
        csm_robot.merge(csm_head)
        csm_global.merge(csm_robot)
        csm_global.merge(csm_specimen)
    else:
        csm_global.merge(csm_specimen)
        csm_global.merge(csm_robot)
        csm_global.merge(csm_head)
        csm_global.merge(csm_scanner_1)
        csm_global.merge(csm_scanner_2)

    return csm_global
Exemple #5
0
def single_pass_weld_example(
    out_file: Optional[Union[str, BytesIO]] = "single_pass_weld_example.asdf",
) -> Optional[tuple[BytesIO, dict]]:
    """Create ASDF file containing all required fields of the single_pass_weld schema.

    Parameters
    ----------
    out_file :
        destination file, if None returns a BytesIO buffer.

    Returns
    -------
    buff, tree
        When writing to memory, return the buffer and the tree (as dictionary).

    """
    # Imports
    import asdf
    import numpy as np
    import pandas as pd
    from asdf.tags.core import Software

    import weldx.geometry as geo
    import weldx.measurement as msm

    # importing the weldx package with prevalent default abbreviations
    import weldx.transformations as tf
    from weldx.asdf.util import get_schema_path, write_buffer, write_read_buffer
    from weldx.constants import META_ATTR, Q_
    from weldx.core import MathematicalExpression, TimeSeries
    from weldx.tags.aws.process.gas_component import GasComponent
    from weldx.tags.aws.process.shielding_gas_for_procedure import (
        ShieldingGasForProcedure, )
    from weldx.tags.aws.process.shielding_gas_type import ShieldingGasType
    from weldx.tags.processes.process import GmawProcess
    from weldx.transformations.local_cs import LocalCoordinateSystem as lcs
    from weldx.transformations.rotation import WXRotation
    from weldx.welding.groove.iso_9692_1 import get_groove
    from weldx.welding.util import sine

    # Timestamp
    reference_timestamp = pd.Timestamp("2020-11-09 12:00:00")

    # Geometry
    # groove + trace = geometry
    groove = get_groove(
        groove_type="VGroove",
        workpiece_thickness=Q_(5, "mm"),
        groove_angle=Q_(50, "deg"),
        root_face=Q_(1, "mm"),
        root_gap=Q_(1, "mm"),
    )

    # define the weld seam length in mm
    seam_length = Q_(300, "mm")

    # create a linear trace segment a the complete weld seam trace
    trace_segment = geo.LinearHorizontalTraceSegment(seam_length)
    trace = geo.Trace(trace_segment)

    geometry = dict(groove_shape=groove, seam_length=seam_length)

    base_metal = dict(common_name="S355J2+N", standard="DIN EN 10225-2:2011")

    workpiece = dict(base_metal=base_metal, geometry=geometry)

    # Setup the Coordinate System Manager (CSM)
    # crete a new coordinate system manager with default base coordinate system
    csm = tf.CoordinateSystemManager("base")

    # add the workpiece coordinate system
    csm.add_cs(
        coordinate_system_name="workpiece",
        reference_system_name="base",
        lcs=trace.coordinate_system,
    )

    tcp_start_point = Q_([5.0, 0.0, 2.0], "mm")
    tcp_end_point = Q_([-5.0, 0.0, 2.0], "mm") + np.append(
        seam_length, Q_([0, 0], "mm"))

    v_weld = Q_(10, "mm/s")
    s_weld = (tcp_end_point - tcp_start_point)[0]  # length of the weld
    t_weld = s_weld / v_weld

    t_start = pd.Timedelta("0s")
    t_end = pd.Timedelta(str(t_weld.to_base_units()))

    rot = WXRotation.from_euler(seq="x", angles=180, degrees=True)

    coords = [tcp_start_point.magnitude, tcp_end_point.magnitude]

    tcp_wire = lcs(coordinates=coords, orientation=rot, time=[t_start, t_end])

    # add the workpiece coordinate system
    csm.add_cs(
        coordinate_system_name="tcp_wire",
        reference_system_name="workpiece",
        lcs=tcp_wire,
    )

    tcp_contact = lcs(coordinates=[0, 0, -10])

    # add the workpiece coordinate system
    csm.add_cs(
        coordinate_system_name="tcp_contact",
        reference_system_name="tcp_wire",
        lcs=tcp_contact,
    )

    TCP_reference = csm.get_cs("tcp_contact", "workpiece")

    # Measurements
    # time
    time = pd.timedelta_range(start="0s", end="10s", freq="2s")

    # current data
    I_ts = sine(f=Q_(10, "1/s"), amp=Q_(20, "A"), bias=Q_(300, "A"))
    current_data = TimeSeries(I_ts.interp_time(time).data, time)

    # voltage data
    U_ts = sine(f=Q_(10, "1/s"),
                amp=Q_(3, "V"),
                bias=Q_(40, "V"),
                phase=Q_(0.1, "rad"))
    voltage_data = TimeSeries(U_ts.interp_time(time).data, time)

    # define current source and transformations

    src_current = msm.SignalSource(
        name="Current Sensor",
        output_signal=msm.Signal(signal_type="analog", units="V", data=None),
        error=msm.Error(Q_(0.1, "percent")),
    )

    current_AD_transform = msm.SignalTransformation(
        name="AD conversion current measurement",
        error=msm.Error(Q_(0.01, "percent")),
        func=MathematicalExpression(
            "a * x + b", dict(a=Q_(32768.0 / 10.0, "1/V"), b=Q_(0.0, ""))),
        type_transformation="AD",
    )

    current_calib_transform = msm.SignalTransformation(
        name="Calibration current measurement",
        error=msm.Error(0.0),
        func=MathematicalExpression(
            "a * x + b", dict(a=Q_(1000.0 / 32768.0, "A"), b=Q_(0.0, "A"))),
    )

    # define voltage source and transformations

    src_voltage = msm.SignalSource(
        name="Voltage Sensor",
        output_signal=msm.Signal("analog", "V", data=None),
        error=msm.Error(Q_(0.1, "percent")),
    )

    voltage_AD_transform = msm.SignalTransformation(
        name="AD conversion voltage measurement",
        error=msm.Error(Q_(0.01, "percent")),
        func=MathematicalExpression(
            "a * x + b", dict(a=Q_(32768.0 / 10.0, "1/V"), b=Q_(0.0, ""))),
        type_transformation="AD",
    )

    voltage_calib_transform = msm.SignalTransformation(
        name="Calibration voltage measurement",
        error=msm.Error(0.0),
        func=MathematicalExpression(
            "a * x + b", dict(a=Q_(100.0 / 32768.0, "V"), b=Q_(0.0, "V"))),
    )

    # Define lab equipment

    HKS_sensor = msm.MeasurementEquipment(
        name="HKS P1000-S3",
        sources=[src_current, src_voltage],
    )
    BH_ELM = msm.MeasurementEquipment(
        name="Beckhoff ELM3002-0000",
        transformations=[current_AD_transform, voltage_AD_transform],
    )

    twincat_scope = Software(name="Beckhoff TwinCAT ScopeView",
                             version="3.4.3143")
    setattr(current_calib_transform, META_ATTR, dict(software=twincat_scope))
    setattr(voltage_calib_transform, META_ATTR, dict(software=twincat_scope))

    # Define current measurement chain

    welding_current_chain = msm.MeasurementChain.from_equipment(
        name="welding current measurement chain",
        equipment=HKS_sensor,
        source_name="Current Sensor",
    )
    welding_current_chain.add_transformation_from_equipment(
        equipment=BH_ELM,
        transformation_name="AD conversion current measurement",
    )
    welding_current_chain.add_transformation(
        transformation=current_calib_transform,
        data=current_data,
    )

    # Define voltage measurement chain

    welding_voltage_chain = msm.MeasurementChain.from_equipment(
        name="welding voltage measurement chain",
        equipment=HKS_sensor,
        source_name="Voltage Sensor",
    )
    welding_voltage_chain.add_transformation_from_equipment(
        equipment=BH_ELM,
        transformation_name="AD conversion voltage measurement",
    )
    welding_voltage_chain.add_transformation(
        transformation=voltage_calib_transform,
        data=voltage_data,
    )

    # Define measurements

    welding_current = msm.Measurement(
        name="welding current measurement",
        data=[current_data],
        measurement_chain=welding_current_chain,
    )

    welding_voltage = msm.Measurement(
        name="welding voltage measurement",
        data=[voltage_data],
        measurement_chain=welding_voltage_chain,
    )

    # GMAW Process
    params_pulse = dict(
        wire_feedrate=Q_(10.0, "m/min"),
        pulse_voltage=Q_(40.0, "V"),
        pulse_duration=Q_(5.0, "ms"),
        pulse_frequency=Q_(100.0, "Hz"),
        base_current=Q_(60.0, "A"),
    )
    process_pulse = GmawProcess(
        "pulse",
        "CLOOS",
        "Quinto",
        params_pulse,
        tag="CLOOS/pulse",
        meta={"modulation": "UI"},
    )

    gas_comp = [
        GasComponent("argon", Q_(82, "percent")),
        GasComponent("carbon dioxide", Q_(18, "percent")),
    ]
    gas_type = ShieldingGasType(gas_component=gas_comp, common_name="SG")

    gas_for_procedure = ShieldingGasForProcedure(
        use_torch_shielding_gas=True,
        torch_shielding_gas=gas_type,
        torch_shielding_gas_flowrate=Q_(20, "l / min"),
    )

    process = dict(
        welding_process=process_pulse,
        shielding_gas=gas_for_procedure,
        weld_speed=TimeSeries(v_weld),
        welding_wire={"diameter": Q_(1.2, "mm")},
    )

    # ASDF file
    tree = dict(
        reference_timestamp=reference_timestamp,
        equipment=[HKS_sensor, BH_ELM],
        measurements=[welding_current, welding_voltage],
        welding_current=welding_current_chain.get_signal(
            "Calibration current measurement").data,
        welding_voltage=welding_voltage_chain.get_signal(
            "Calibration voltage measurement").data,
        coordinate_systems=csm,
        TCP=TCP_reference,
        workpiece=workpiece,
        process=process,
    )
    tree[META_ATTR] = {"welder": "A.W. Elder"}

    model_path = get_schema_path("single_pass_weld-0.1.0.yaml")

    # pre-validate?
    write_read_buffer(
        tree,
        asdffile_kwargs=dict(custom_schema=str(model_path)),
    )

    if out_file:
        with asdf.AsdfFile(
                tree,
                custom_schema=str(model_path),
        ) as ff:
            ff.write_to(out_file, all_array_storage="inline")
    else:
        return (
            write_buffer(
                tree,
                asdffile_kwargs=dict(custom_schema=str(model_path)),
                write_kwargs=dict(all_array_storage="inline"),
            ),
            tree,
        )