55from  typing  import  Type , Union 
66
77import  hightime  as  ht 
8- import  numpy 
8+ import  nitypes .bintime  as  bt 
9+ import  numpy  as  np 
910from  ni .protobuf .types  import  scalar_pb2 
1011from  ni_measurement_plugin_sdk_service ._internal .stubs .ni .protobuf .types .precision_timestamp_pb2  import  (
1112    PrecisionTimestamp ,
1415    DoubleAnalogWaveform ,
1516    WaveformAttributeValue ,
1617)
17- from  nitypes .bintime  import  DateTime , TimeValueTuple 
1818from  nitypes .scalar  import  Scalar 
1919from  nitypes .time  import  convert_datetime 
2020from  nitypes .waveform  import  (
2121    AnalogWaveform ,
2222    ExtendedPropertyDictionary ,
23+     ExtendedPropertyValue ,
2324    NoneScaleMode ,
2425    SampleIntervalMode ,
2526    Timing ,
3738}
3839
3940
40- class  DoubleAnalogWaveformConverter (Converter [AnalogWaveform [numpy .float64 ], DoubleAnalogWaveform ]):
41+ class  DoubleAnalogWaveformConverter (Converter [AnalogWaveform [np .float64 ], DoubleAnalogWaveform ]):
4142    """A converter for AnalogWaveform types with scaled data (double).""" 
4243
44+     def  __init__ (self ) ->  None :
45+         """Initialize a DoubleAnalogWaveformConverter object.""" 
46+         self ._pt_converter  =  PrecisionTimestampConverter ()
47+ 
4348    @property  
4449    def  python_typename (self ) ->  str :
4550        """The Python type that this converter handles.""" 
@@ -50,16 +55,13 @@ def protobuf_message(self) -> Type[DoubleAnalogWaveform]:
5055        """The type-specific protobuf message for the Python type.""" 
5156        return  DoubleAnalogWaveform 
5257
53-     def  to_protobuf_message (
54-         self , python_value : AnalogWaveform [numpy .float64 ]
55-     ) ->  DoubleAnalogWaveform :
58+     def  to_protobuf_message (self , python_value : AnalogWaveform [np .float64 ]) ->  DoubleAnalogWaveform :
5659        """Convert the Python AnalogWaveform to a protobuf DoubleAnalogWaveform.""" 
5760        if  python_value .timing .has_timestamp :
58-             pt_converter  =  PrecisionTimestampConverter ()
59-             bin_datetime  =  DateTime (python_value .timing .start_time )
60-             precision_timestamp  =  pt_converter .to_protobuf_message (bin_datetime )
61+             bin_datetime  =  convert_datetime (bt .DateTime , python_value .timing .start_time )
62+             precision_timestamp  =  self ._pt_converter .to_protobuf_message (bin_datetime )
6163        else :
62-             precision_timestamp  =  PrecisionTimestamp ( seconds = 0 ,  fractional_seconds = 0 ) 
64+             precision_timestamp  =  None 
6365
6466        if  python_value .timing .has_sample_interval :
6567            time_interval  =  python_value .timing .sample_interval .total_seconds ()
@@ -79,48 +81,41 @@ def _extended_properties_to_attributes(
7981        self ,
8082        extended_properties : ExtendedPropertyDictionary ,
8183    ) ->  collections .abc .Mapping [str , WaveformAttributeValue ]:
82-         attributes  =  {}
83-         for  key , value  in  extended_properties .items ():
84-             attr_value  =  WaveformAttributeValue ()
85-             if  isinstance (value , bool ):
86-                 attr_value .bool_value  =  value 
87-             elif  isinstance (value , int ):
88-                 attr_value .integer_value  =  value 
89-             elif  isinstance (value , float ):
90-                 attr_value .double_value  =  value 
91-             elif  isinstance (value , str ):
92-                 attr_value .string_value  =  value 
93-             else :
94-                 raise  TypeError (f"Unexpected type for extended property value { type (value )}  " )
95- 
96-             attributes [key ] =  attr_value 
84+         return  {key : self ._value_to_attribute (value ) for  key , value  in  extended_properties .items ()}
85+ 
86+     def  _value_to_attribute (self , value : ExtendedPropertyValue ) ->  WaveformAttributeValue :
87+         attr_value  =  WaveformAttributeValue ()
88+         if  isinstance (value , bool ):
89+             attr_value .bool_value  =  value 
90+         elif  isinstance (value , int ):
91+             attr_value .integer_value  =  value 
92+         elif  isinstance (value , float ):
93+             attr_value .double_value  =  value 
94+         elif  isinstance (value , str ):
95+             attr_value .string_value  =  value 
96+         else :
97+             raise  TypeError (f"Unexpected type for extended property value { type (value )}  " )
9798
98-         return  attributes 
99+         return  attr_value 
99100
100-     def  to_python_value (
101-         self , protobuf_value : DoubleAnalogWaveform 
102-     ) ->  AnalogWaveform [numpy .float64 ]:
101+     def  to_python_value (self , protobuf_message : DoubleAnalogWaveform ) ->  AnalogWaveform [np .float64 ]:
103102        """Convert the protobuf DoubleAnalogWaveform to a Python AnalogWaveform.""" 
104-         if  (
105-             not  protobuf_value .dt 
106-             and  not  protobuf_value .t0 .seconds 
107-             and  not  protobuf_value .t0 .fractional_seconds 
108-         ):
109-             # If both dt and t0 and unset, use Timing.empty. 
103+         if  not  protobuf_message .dt  and  not  protobuf_message .HasField ("t0" ):
104+             # If both dt and t0 are unset, use Timing.empty. 
110105            timing  =  Timing .empty 
111106        else :
112107            # Timestamp 
113108            pt_converter  =  PrecisionTimestampConverter ()
114-             bin_datetime  =  pt_converter .to_python_value (protobuf_value .t0 )
109+             bin_datetime  =  pt_converter .to_python_value (protobuf_message .t0 )
115110            timestamp  =  convert_datetime (dt .datetime , bin_datetime )
116111
117112            # Sample Interval 
118-             if  not  protobuf_value .dt :
113+             if  not  protobuf_message .dt :
119114                sample_interval_mode  =  SampleIntervalMode .NONE 
120115                sample_interval  =  None 
121116            else :
122117                sample_interval_mode  =  SampleIntervalMode .REGULAR 
123-                 sample_interval  =  ht .timedelta (seconds = protobuf_value .dt )
118+                 sample_interval  =  ht .timedelta (seconds = protobuf_message .dt )
124119
125120            timing  =  Timing (
126121                sample_interval_mode = sample_interval_mode ,
@@ -129,46 +124,48 @@ def to_python_value(
129124            )
130125
131126        extended_properties  =  {}
132-         for  key , value  in  protobuf_value .attributes .items ():
127+         for  key , value  in  protobuf_message .attributes .items ():
133128            attr_type  =  value .WhichOneof ("attribute" )
134129            extended_properties [key ] =  getattr (value , str (attr_type ))
135130
136-         data_list  =  list ( protobuf_value .y_data )
131+         data_array  =  np . array ( protobuf_message .y_data )
137132        return  AnalogWaveform (
138-             sample_count = len ( data_list ) ,
139-             dtype = numpy .float64 ,
140-             raw_data = numpy . array ( data_list ) ,
133+             sample_count = data_array . size ,
134+             dtype = np .float64 ,
135+             raw_data = data_array ,
141136            start_index = 0 ,
142-             capacity = len ( data_list ) ,
137+             capacity = data_array . size ,
143138            extended_properties = extended_properties ,
144139            copy_extended_properties = True ,
145140            timing = timing ,
146141            scale_mode = NoneScaleMode (),
147142        )
148143
149144
150- class  PrecisionTimestampConverter (Converter [DateTime , PrecisionTimestamp ]):
145+ class  PrecisionTimestampConverter (Converter [bt . DateTime , PrecisionTimestamp ]):
151146    """A converter for bintime.DateTime types.""" 
152147
153148    @property  
154149    def  python_typename (self ) ->  str :
155150        """The Python type that this converter handles.""" 
156-         return  DateTime .__name__ 
151+         return  bt . DateTime .__name__ 
157152
158153    @property  
159154    def  protobuf_message (self ) ->  Type [PrecisionTimestamp ]:
160155        """The type-specific protobuf message for the Python type.""" 
161156        return  PrecisionTimestamp 
162157
163-     def  to_protobuf_message (self , python_value : DateTime ) ->  PrecisionTimestamp :
158+     def  to_protobuf_message (self , python_value : bt . DateTime ) ->  PrecisionTimestamp :
164159        """Convert the Python DateTime to a protobuf PrecisionTimestamp.""" 
165160        seconds , fractional_seconds  =  python_value .to_tuple ()
166161        return  self .protobuf_message (seconds = seconds , fractional_seconds = fractional_seconds )
167162
168-     def  to_python_value (self , protobuf_value : PrecisionTimestamp ) ->  DateTime :
163+     def  to_python_value (self , protobuf_message : PrecisionTimestamp ) ->  bt . DateTime :
169164        """Convert the protobuf PrecisionTimestamp to a Python DateTime.""" 
170-         time_value_tuple  =  TimeValueTuple (protobuf_value .seconds , protobuf_value .fractional_seconds )
171-         return  DateTime .from_tuple (time_value_tuple )
165+         time_value_tuple  =  bt .TimeValueTuple (
166+             protobuf_message .seconds , protobuf_message .fractional_seconds 
167+         )
168+         return  bt .DateTime .from_tuple (time_value_tuple )
172169
173170
174171class  ScalarConverter (Converter [Scalar [_AnyScalarType ], scalar_pb2 .ScalarData ]):
0 commit comments