Skip to content

ExcelConceptEV #500

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 11 commits into
base: main
Choose a base branch
from
Open
6 changes: 5 additions & 1 deletion pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -31,14 +31,18 @@ dependencies = [
"requests >= 2.27.1",
"packaging >= 21.3",
"importlib-metadata>=4.0",
"openpyxl >=3.1.5",
]

[project.optional-dependencies]
tests = [
"pytest==8.3.5",
"pytest-cov==6.0.0",
"ansys.platform.instancemanagement>=1.0.2",
"matplotlib>=3.6.3"
"matplotlib>=3.6.3",
"scipy",
"openpyxl >=3.1.5",

]
doc = [
"Sphinx==8.1.3",
Expand Down
169 changes: 169 additions & 0 deletions src/ansys/motorcad/core/methods/rpc_methods_lab.py
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,17 @@
k_custom_loss_voltage_function_external_lab = "CustomLoss_VoltageFunction_External_Lab"


from openpyxl import Workbook

try:
import numpy as np
from scipy.io import loadmat

Num_Sci_py_AVAILABLE = True
except ImportError:
Num_Sci_py_AVAILABLE = False


class _RpcMethodsLab:
def __init__(self, mc_connection):
self.connection = mc_connection
Expand Down Expand Up @@ -304,3 +315,161 @@ def export_lab_model(self, file_path):
method = "ExportLabModel"
params = [file_path]
return self.connection.send_and_receive(method, params)

def _write_excel_IM_speed(data, sheets, DC_voltage_list, i, wb):
i_len, j_len = data["Speed"].shape
for sheet in sheets:
ws = wb.create_sheet("Newsheet")
ws.title = "Voltages"
if len(DC_voltage_list) > 1:
ws.title = sheet + str(i + 1)
else:
ws.title = sheet
if sheet == "Speed":
for jj, col in enumerate(ws.iter_cols(min_col=0, max_col=j_len, max_row=i_len)):
for ii, cell in enumerate(col):
if data[sheet][ii][jj] == 1:
ws[cell.coordinate] = 0
else:
ws[cell.coordinate] = data[sheet][ii][jj]
else:
for jj, col in enumerate(ws.iter_cols(min_col=0, max_col=j_len, max_row=i_len)):
for ii, cell in enumerate(col):
ws[cell.coordinate] = data[sheet][ii][jj]
return wb

def _write_excel_BPM(data, sheets, DC_voltage_list, i, wb):
i_len, j_len = data["Speed"].shape
for sheet in sheets:
ws = wb.create_sheet("Newsheet")
ws.title = "Voltages"
if len(DC_voltage_list) > 1:
ws.title = sheet + str(i + 1)
else:
ws.title = sheet
for jj, col in enumerate(ws.iter_cols(min_col=0, max_col=j_len, max_row=i_len)):
for ii, cell in enumerate(col):
ws[cell.coordinate] = data[sheet][ii][jj]
return wb

def _set_model_parameters(self, **kwargs):
if "Max_speed" in kwargs:
self.set_variable("SpeedMax_MotorLAB", kwargs["Max_speed"])
if "Min_speed" in kwargs:
if self.get_variable("Motor_Type") == 1 and kwargs["Min_speed"] == 0:
self.set_variable("SpeedMin_MotorLAB", 1)
else:
self.set_variable("SpeedMin_MotorLAB", kwargs["Min_speed"])
if "Speed_Step" in kwargs:
self.set_variable("Speedinc_MotorLAB", kwargs["Speed_Step"])

Current_def = self.get_variable("CurrentSpec_MotorLAB")
if Current_def == 0: # peak
if "I_max" in kwargs:
if self.get_variable("Motor_Type") == 6: # Sync
self.set_variable("Sync_StatorCurrentMax_Lab", kwargs["I_max"])
else:
self.set_variable("Imax_MotorLAB", kwargs["I_max"])
if "I_min" in kwargs:
self.set_variable("Imin_MotorLAB", kwargs["I_min"])
# if "I_inc" in kwargs:
# self.set_variable("Iinc_MotorLAB",kwargs["I_inc"])
else: # RMS
if "I_max" in kwargs:
if self.get_variable("Motor_Type") == 6: # Sync
self.set_variable("Sync_StatorCurrentMax_RMS_Lab", kwargs["I_max"])
else:
self.set_variable("Imax_RMS_MotorLAB", kwargs["I_max"])
if "I_min" in kwargs:
self.set_variable("Imin_RMS_MotorLAB", kwargs["I_min"])
if "I_inc" in kwargs:
if self.get_variable("Motor_Type") == 6: # Sync machine
print("sync executed")
self.set_variable("Sync_CurrentIncs_Lab", kwargs["I_inc"])
else:
self.set_variable("Iinc_MotorLAB", kwargs["I_inc"])

# choose motoring, generating or both modes
if "Rotor_current_max" in kwargs:
self.set_variable("Sync_RotorCurrentMax_Lab", kwargs["Rotor_current_max"])

if "Op_mode" in kwargs:
self.set_variable("OperatingMode_Lab", kwargs["Op_mode"])

def export_concept_ev_model(self, **kwargs):
"""Export efficiency map in concept ev excel format.

Parameters
----------
Max_speed : int
Maximum speed in electromagnetic calculation
Min_speed : int
Minimum speed in electromagnetic calculation
Speed_step : int
Speed increment in electromagnetic calculation
I_max : float
Maximum current (peak or rms based on settings)
I_min : float
Minimum current (peak or rms based on settings)
I_inc : float
Current increment in electromagnetic calculation
Rotor_current_max: float
Maximum rotor current in electromagnetic calculation (only in Sync machines)
Op_mode: int
0 Motor, 1 Generator, 2 Motor / Generator mode
DC_voltage_list: list
List of DC bus voltages
"""
if not Num_Sci_py_AVAILABLE:
raise ImportError(
"Failed to export concept_ev_model. Please ensure Numpy and Scipy are installed"
)

self.set_variable("MessageDisplayState", 2)
self.set_motorlab_context()
file_path = self.get_variable("ResultsPath_MotorLAB") + "ConceptEV_elecdata.xlsx"
# set model parameters
_RpcMethodsLab._set_model_parameters(self, **kwargs)
wb = Workbook()
# choose number of DC bus voltages (list as user input)
if "DC_voltage_list" in kwargs:
DC_voltage_list = kwargs["DC_voltage_list"]
else:
DC_voltage_list = [self.get_variable("DCBusVoltage")]

ws = wb.active
ws.title = "Voltages"
ws["A1"] = "Index"
ws["B1"] = "Voltages"
for i, DC_voltage in enumerate(DC_voltage_list):
ws["A" + str(i + 2)] = i + 1
ws["B" + str(i + 2)] = DC_voltage_list[i]

# Units sheet

# set _calcualtion type Efficiency Map
self.set_variable("EmagneticCalcType_Lab", 1)
sheets = ["Speed", "Shaft_Torque", "Stator_Current_Line_RMS", "Total_Loss", "Power_Factor"]
for i, DC_voltage in enumerate(DC_voltage_list):
self.set_variable("DCBusVoltage", DC_voltage)
# run Efficiency Map calculation
self.calculate_magnetic_lab()
# read the lab data .mat file
data_file_path = self.get_variable("ResultsPath_MotorLAB") + "MotorLAB_elecdata.mat"
data = loadmat(data_file_path)
if "Min_speed" in kwargs:
if self.get_variable("Motor_Type") == 1 and kwargs["Min_speed"] == 0:
wb = _RpcMethodsLab._write_excel_IM_speed(data, sheets, DC_voltage_list, i, wb)
else:
wb = _RpcMethodsLab._write_excel_BPM(data, sheets, DC_voltage_list, i, wb)
else:
wb = _RpcMethodsLab._write_excel_BPM(data, sheets, DC_voltage_list, i, wb)

units = ["Power_Factor", "Total_Loss", "Stator_Current_Line_RMS", "Shaft_Torque", "Speed"]
ws = wb.create_sheet("Newsheet")
ws.title = "Units"
for i, unit in enumerate(units):
ws["A" + str(i + 1)] = unit
index = np.where(np.strings.find(data["varStr"], unit) == 0)[0]
ws["B" + str(i + 1)] = data["varUnits"][index][0]
wb.save(file_path)
28 changes: 27 additions & 1 deletion tests/test_lab.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,9 +23,12 @@
# from os import path, remove
# import time

import os

from openpyxl import load_workbook
import pytest

from RPC_Test_Common import reset_to_default_file # (get_dir_path,
from RPC_Test_Common import almost_equal_percentage, reset_to_default_file # (get_dir_path,


def test_model_build_lab(mc):
Expand Down Expand Up @@ -172,6 +175,29 @@ def test_external_custom_loss_functions(mc):
assert mc.get_variable("NumCustomLossesExternal_Lab") == no_external_losses + 1


def test_export_concept_ev_model(mc):
mc.set_variable("MessageDisplayState", 2)
mc.load_template("e9")
# run Efficiency Map calculation
mc.calculate_magnetic_lab()
file_path = mc.get_variable("ResultsPath_MotorLAB") + "ConceptEV_elecdata.xlsx"
mc.export_concept_ev_model()
assert os.path.exists(file_path) is True
wb = load_workbook(file_path)
assert "Shaft_Torque" in wb.sheetnames
assert "Voltages" in wb.sheetnames
assert "Speed" in wb.sheetnames
assert "Stator_Current_Line_RMS" in wb.sheetnames
assert "Total_Loss" in wb.sheetnames
assert "Power_Factor" in wb.sheetnames
assert "Units" in wb.sheetnames
speed_sheet = wb["Speed"]
assert speed_sheet.max_row == 21
assert speed_sheet.max_column == 60
torque_sheet = wb["Shaft_Torque"]
assert almost_equal_percentage(torque_sheet.cell(row=1, column=1).value, 274.16, 0.1)


# def test_lab_model_export(mc):
# mc.set_variable("MessageDisplayState", 2)
# file_path = get_dir_path() + r"\test_files\temp_files\lab_model_export.lab"
Expand Down
Loading