From e6834ef3865664135ee90ad93b9689b895a11009 Mon Sep 17 00:00:00 2001 From: Gobot1234 Date: Wed, 4 Feb 2026 01:30:14 +0000 Subject: [PATCH 1/9] Update examples to use modern API. Mostly untested and not currently functional due to various settings API and other github side pull requests not being merged or fixed - We use the much more descriptive object oriented API with ORM style `create()` and `get()` methods that are more clear in intent - I've tried to get rid of TUI based examples and where not possible I've at least described what the parameters are - I've colocated the units next to their values - Removed the dictionary state assignment based APIs in favour of direct attribute access as it will leave users in a more recoverable state and is easier to type (both type hinting and on the keyboard) - Used tuples for vectors rather than lists to allow for better type hinting in the future checking 2D vs 3D cases - Used pathlib instead of os.path - Added calls to solver.upload(filename) after the example is downloaded if the mode is Meshing for based workflows - Changed all the pyfluent.lanuch_fluent to it's appropriate pyfluent.ModeClass.from_install - Stored the results of .create() and use that to apply next variable assignments if appropriate rather than performing another lookup - I've tried to reduce the stringly-typedness of the API by reusing objects (where things are explicitly suffixed with name I've tried to use the `name()` method though. In practice though i don't like this and we should be instead passing round the full objects e.g. `custom_field_function_name=omega_r.name()` where `omega_r` is a `custom_field_function`. I think it makes more sense to pass a str | custom_field_function to a parameter called `custom_field_function` than passing the same type to `custom_field_function_name` which would work if you use another one of my PRs) - I've tried to update fields to use VariableCatalog though many are missing due to the fields not existing in VariableCatalog or VariableCatalog.fluent - Improved general pythonicness of code/algorithms/loops etc NB I've updated some of the examples @MohammedAnsys has PRs open for that looked like they were ready for merging NBB I 've not switched the save locations for all these to examples_path, though that might be a good idea in the future --- examples/00-fluent/DOE_ML.py | 198 +++---- .../Electrolysis_Modeling_workflow.py | 202 +++---- .../Modeling_solidification_workflow.py | 223 ++++---- examples/00-fluent/ahmed_body_workflow.py | 248 ++++---- examples/00-fluent/battery_pack.py | 216 ++++--- examples/00-fluent/brake.py | 305 ++++------ .../00-fluent/catalytic_converter_workflow.py | 423 +++++++------- examples/00-fluent/conjugate_heat_transfer.py | 457 ++++++--------- .../00-fluent/exhaust_system_settings_api.py | 188 +++--- .../00-fluent/external_compressible_flow.py | 116 ++-- examples/00-fluent/frozen_rotor_workflow.py | 264 ++++----- examples/00-fluent/fsi_1way_workflow.py | 121 ++-- examples/00-fluent/lunar_lander_thermal.py | 308 +++++----- .../00-fluent/mixing_elbow_settings_api.py | 107 ++-- examples/00-fluent/mixing_tank_workflow.py | 317 +++++----- examples/00-fluent/modeling_ablation.py | 417 ++++++-------- examples/00-fluent/modeling_cavitation.py | 285 ++++----- .../00-fluent/parametric_static_mixer_1.py | 284 +++++---- examples/00-fluent/radiation_headlamp.py | 257 ++++----- .../00-fluent/single_battery_cell_workflow.py | 539 +++++++++--------- examples/00-fluent/species_transport.py | 212 ++++--- examples/00-fluent/steady_vortex.py | 344 ++++++----- .../transient_compressible_nozzle_workflow.py | 188 +++--- examples/00-fluent/tyler_sofrin_modes.py | 72 ++- 24 files changed, 2864 insertions(+), 3427 deletions(-) diff --git a/examples/00-fluent/DOE_ML.py b/examples/00-fluent/DOE_ML.py index 02876c9778f..5c876de8721 100644 --- a/examples/00-fluent/DOE_ML.py +++ b/examples/00-fluent/DOE_ML.py @@ -62,20 +62,28 @@ # flake8: noqa: E402 -import os +import itertools +import json from pathlib import Path +from typing import TYPE_CHECKING, cast +from ansys.units import Quantity +from ansys.units.quantity import ArrayLike import matplotlib.pyplot as plt import numpy as np import pandas as pd -import plotly.express as px -import plotly.graph_objects as go -import seaborn as sns -import tensorflow as tf -from tensorflow import keras +# import plotly.express as px +# import plotly.graph_objects as go +# import seaborn as sns +# import tensorflow as tf +# from tensorflow import keras import ansys.fluent.core as pyfluent from ansys.fluent.core import examples +from ansys.fluent.core.generated.solver.settings_builtin import SurfaceIntegrals +from ansys.fluent.core.generated.solver.settings_builtin_261 import iterate, read_case +from ansys.fluent.core.solver import Initialization, VelocityInlet, RunCalculation +from ansys.units.common import m, s ########################################################################### # Specifying save path @@ -84,7 +92,7 @@ import_filename = examples.download_file( "elbow.cas.h5", "pyfluent/examples/DOE-ML-Mixing-Elbow", - save_path=os.getcwd(), + save_path=Path.cwd(), ) ####################### @@ -95,69 +103,67 @@ # Launch Fluent session with solver mode and print Fluent version # =============================================================== -solver_session = pyfluent.launch_fluent( - precision="double", +solver = pyfluent.Solver.from_install( + precision=pyfluent.Precision.SINGLE, processor_count=4, ) -print(solver_session.get_fluent_version()) +print(solver.get_fluent_version()) ############################################################################# # Read case # ========= -solver_session.settings.file.read_case(file_name=import_filename) +solver.upload(import_filename) +read_case(solver, file_name=import_filename) ############################################################################################## # Design of Experiments # ===================== # Specify inlet velocities for the cold and hot streams. -# Each pair of (coldVel, hotVel) will be used to run one Fluent case. -coldVelArr = np.array([0.1, 0.2, 0.3, 0.4, 0.5, 0.6, 0.7]) -hotVelArr = np.array([0.8, 1.0, 1.2, 1.4, 1.6, 1.8, 2.0]) +# Each pair of (cold_value, hot_value) will be used to run one Fluent case. +cold_velocities = [0.1, 0.2, 0.3, 0.4, 0.5, 0.6, 0.7] * m / s + +hot_velocities = [0.8, 1.0, 1.2, 1.4, 1.6, 1.8, 2.0] * m / s + # Allocate a results array. Entry (i, j) will hold the Mass‑Weighted -# Average Temperature at the outlet for coldVelArr[i] and hotVelArr[j]. -resArr = np.zeros((coldVelArr.size, hotVelArr.size)) - -for idx1, coldVel in np.ndenumerate(coldVelArr): - for idx2, hotVel in np.ndenumerate(hotVelArr): - cold_inlet = solver_session.settings.setup.boundary_conditions.velocity_inlet[ - "cold-inlet" - ] - cold_inlet.momentum.velocity.value = coldVel - - hot_inlet = solver_session.settings.setup.boundary_conditions.velocity_inlet[ - "hot-inlet" - ] - hot_inlet.momentum.velocity.value = hotVel - - solver_session.settings.solution.initialization.initialization_type = "standard" - solver_session.settings.solution.initialization.standard_initialize() - solver_session.settings.solution.run_calculation.iterate(iter_count=200) - - res_tui = solver_session.scheme.exec( - ( - "(ti-menu-load-string " - '"/report/surface-integrals/mass-weighted-avg outlet () ' - 'temperature no")', - ) - ) - resArr[idx1][idx2] = eval(res_tui.split(" ")[-1]) +# Average Temperature at the outlet for cold_velocities[i] and hot_velocities[j]. +results = np.zeros((len(cold_velocities), len(hot_velocities))) + +for (idx1, cold_value), (idx2, hot_value) in itertools.product( + enumerate(cold_velocities), enumerate(hot_velocities) +): + cold_inlet = VelocityInlet.get(solver, name="cold-inlet") + cold_inlet.momentum.velocity = cold_value + + hot_inlet = VelocityInlet.get(solver, name="hot-inlet") + hot_inlet.momentum.velocity = hot_value + + initialize = Initialization(solver) + initialize.initialization_type = "standard" + initialize.standard_initialize() + + iterate(solver,iter_count=200) + + temperatures = SurfaceIntegrals(solver).get_mass_weighted_avg( + surface_names=["outlet"], report_of="temperature" + ) + results[idx1][idx2] = temperatures["outlet"] ############################################################################################## # Close the session # ================= -solver_session.exit() +solver.exit() #################################### # Plot Response Surface using Plotly # ================================== -fig = go.Figure(data=[go.Surface(z=resArr.T, x=coldVelArr, y=hotVelArr)]) +fig = go.Figure(data=[go.Surface(z=results.T, x=cold_velocities, y=hot_velocities)]) fig.update_layout( title={ @@ -170,14 +176,14 @@ ) fig.update_layout( - scene=dict( - xaxis_title="Cold Inlet Vel (m/s)", - yaxis_title="Hot Inlet Vel (m/s)", - zaxis_title="Outlet Temperature (K)", - ), + scene={ + "xaxis_title": "Cold Inlet Vel (m/s)", + "yaxis_title": "Hot Inlet Vel (m/s)", + "zaxis_title": "Outlet Temperature (K)", + }, width=600, height=600, - margin=dict(l=80, r=80, b=80, t=80), + margin={"l": 80, "r": 80, "b": 80, "t": 80}, ) fig.show() @@ -189,19 +195,16 @@ ############################################ # Create Pandas Dataframe for ML Model Input # ========================================== -coldVelList = [] -hotVelList = [] -ResultList = [] +df = pd.DataFrame({"cold_velocities": [], "hot_velocities": [], "result": []}) -for idx1, coldVel in np.ndenumerate(coldVelArr): - for idx2, hotVel in np.ndenumerate(hotVelArr): - coldVelList.append(coldVel) - hotVelList.append(hotVel) - ResultList.append(resArr[idx1][idx2]) -tempDict = {"coldVel": coldVelList, "hotVel": hotVelList, "Result": ResultList} +for (idx1, cold_vel_val), (idx2, hot_vel_val) in itertools.product( + enumerate(cold_velocities), enumerate(hot_velocities) +): + df["cold_velocities"].append(cold_vel_val) + df["hot_velocities"].append(hot_vel_val) + df["result"].append(results[idx1][idx2]) -df = pd.DataFrame.from_dict(tempDict) from sklearn.compose import ColumnTransformer from sklearn.model_selection import train_test_split @@ -227,7 +230,7 @@ x_ct = ColumnTransformer( [ - ("transformer1", transformer1, ["coldVel", "hotVel"]), + ("transformer1", transformer1, ["cold_velocities", "hot_velocities"]), ], remainder="drop", ) @@ -237,8 +240,8 @@ X_train = x_ct.fit_transform(train_set) X_test = x_ct.fit_transform(test_set) -y_train = train_set["Result"] -y_test = test_set["Result"] +y_train = train_set["result"] +y_test = test_set["result"] y_train = np.ravel(y_train.T) y_test = np.ravel(y_test.T) @@ -258,18 +261,24 @@ # from sklearn.linear_model import LinearRegression from xgboost import XGBRegressor +if TYPE_CHECKING: + from sklearn.ensemble import RandomForestRegressor + from sklearn.linear_model import LinearRegression + from xgboost import XGBRegressor + np.set_printoptions(precision=2) +out_file = Path.cwd() / "PyFluent_Output.csv" -def display_scores(scores): +def display_scores(scores: np.ndarray): """Display scores.""" print("\nCross-Validation Scores:", scores) - print("Mean:%0.2f" % (scores.mean())) - print("Std. Dev.:%0.2f" % (scores.std())) + print(f"Mean:{scores.mean():0.2f}") + print(f"Std. Dev.:{scores.std():0.2f}") -def fit_and_predict(model): - """Fit abd predict.""" +def fit_and_predict(model: LinearRegression | XGBRegressor | RandomForestRegressor): + """Fit and predict.""" cv = RepeatedKFold(n_splits=5, n_repeats=3, random_state=42) cv_scores = cross_val_score( model, X_train, y_train, scoring="neg_mean_squared_error", cv=cv @@ -282,8 +291,8 @@ def fit_and_predict(model): test_predictions = model.predict(X_test) print(train_predictions.shape[0]) print("\n\nCoefficient Of Determination") - print("Train Data R2 Score: %0.3f" % (r2_score(train_predictions, y_train))) - print("Test Data R2 Score: %0.3f" % (r2_score(test_predictions, y_test))) + print(f"Train Data R2 Score: {r2_score(train_predictions, y_train):0.3f}") + print(f"Test Data R2 Score: {r2_score(test_predictions, y_test):0.3f}") print( "\n\nPredictions - Ground Truth (Kelvin): ", (test_predictions - y_test), "\n" ) @@ -291,24 +300,17 @@ def fit_and_predict(model): com_train_set = train_set com_test_set = test_set - train_list = [] - for i in range(train_predictions.shape[0]): - train_list.append("Train") + train_list = ["train"] * cast(int, train_predictions.shape[0]) + test_list = ["test"] * cast(int, test_predictions.shape[0]) - test_list = [] - for i in range(test_predictions.shape[0]): - test_list.append("Test") - - com_train_set["Result"] = train_predictions.tolist() - com_train_set["Set"] = train_list - com_test_set["Result"] = test_predictions.tolist() - com_test_set["Set"] = test_list + com_train_set["result"] = train_predictions.tolist() + com_train_set["set"] = train_list + com_test_set["result"] = test_predictions.tolist() + com_test_set["set"] = test_list df_combined = pd.concat([com_train_set, com_test_set]) - df_combined.to_csv( - os.path.join(os.getcwd(), "PyFluent_Output.csv"), header=True, index=False - ) + df_combined.to_csv(out_file, header=True, index=False) fig = plt.figure(figsize=(12, 5)) @@ -334,10 +336,10 @@ def fit_and_predict(model): # * Call fit_and_predict # model = LinearRegression() +# model = RandomForestRegressor(random_state=42) model = XGBRegressor( n_estimators=100, max_depth=10, eta=0.3, subsample=0.8, random_state=42 ) -# model = RandomForestRegressor(random_state=42) fit_and_predict(model) @@ -359,13 +361,15 @@ def fit_and_predict(model): # 3D Visualization of Model Predictions on Train & Test Set # ========================================================= -df = pd.read_csv("PyFluent_Output.csv") +df = pd.read_csv(out_file) -fig = px.scatter_3d(df, x="coldVel", y="hotVel", z="Result", color="Set") -fig.update_traces(marker=dict(size=4)) -fig.update_layout(legend=dict(yanchor="top", y=1, xanchor="left", x=0.0)) +fig = px.scatter_3d( + df, x="cold_velocities", y="hot_velocities", z="result", color="set" +) +fig.update_traces(marker={"size": 4}) +fig.update_layout(legend={"yanchor": "top", "y": 1, "xanchor": "left", "x": 0.0}) -fig.add_traces(go.Surface(z=resArr.T, x=coldVelArr, y=hotVelArr)) +fig.add_traces(go.Surface(z=results.T, x=cold_velocities, y=hot_velocities)) fig.update_layout( title={ @@ -378,14 +382,14 @@ def fit_and_predict(model): ) fig.update_layout( - scene=dict( - xaxis_title="Cold Inlet Vel (m/s)", - yaxis_title="Hot Inlet Vel (m/s)", - zaxis_title="Outlet Temperature (K)", - ), + scene={ + "xaxis_title": "Cold Inlet Vel (m/s)", + "yaxis_title": "Hot Inlet Vel (m/s)", + "zaxis_title": "Outlet Temperature (K)", + }, width=500, height=500, - margin=dict(l=80, r=80, b=80, t=80), + margin={"l": 80, "r": 80, "b": 80, "t": 80}, ) fig.show() @@ -451,8 +455,8 @@ def fit_and_predict(model): test_predictions = np.ravel(test_predictions.T) print(test_predictions.shape) -print("\n\nTrain R2: %0.3f" % (r2_score(train_predictions, y_train))) -print("Test R2: %0.3f" % (r2_score(test_predictions, y_test))) +print(f"\n\nTrain R2: {r2_score(train_predictions, y_train):0.3f}") +print(f"Test R2: {r2_score(test_predictions, y_test):0.3f}") print("Predictions - Ground Truth (Kelvin): ", (test_predictions - y_test)) fig = plt.figure(figsize=(12, 5)) diff --git a/examples/00-fluent/Electrolysis_Modeling_workflow.py b/examples/00-fluent/Electrolysis_Modeling_workflow.py index 23441455825..df79da2c3e7 100644 --- a/examples/00-fluent/Electrolysis_Modeling_workflow.py +++ b/examples/00-fluent/Electrolysis_Modeling_workflow.py @@ -74,21 +74,29 @@ # Importing the following classes offer streamlined access to key solver settings, # eliminating the need to manually browse through the full settings structure. -import os +from pathlib import Path import ansys.fluent.core as pyfluent from ansys.fluent.core import examples +from ansys.fluent.core.generated.solver.settings_builtin_261 import iterate, write_case_data from ansys.fluent.core.solver import ( BoundaryConditions, Contour, Controls, + EChemistry, Graphics, Initialization, + MassFlowInlet, Materials, Mesh, RunCalculation, Setup, + SolidMaterial, ) +from ansys.units.common import A, K, V, degree, m, ohm, s + +# a Siemen +S = 1 / ohm # %% # Launch Fluent session in solver mode @@ -105,9 +113,12 @@ mesh_file = examples.download_file( "electrolysis.msh.h5", "pyfluent/electrolysis", - save_path=os.getcwd(), + save_path=Path.cwd(), ) +# upload mesh to solver (required for some remote/meshing workflows) +solver.upload(mesh_file) + solver.settings.file.read_mesh(file_name=mesh_file) # %% @@ -136,117 +147,84 @@ # %% # Enable Electrolysis Model # ------------------------- -setup = Setup(solver) - -setup.models.echemistry = { - "potential": True, - "echemistry_enabled": True, - "electrolysis": { - "options": { - "bc_type": "Total voltage", - "tot_voltage": 1.730202, # V - }, - "parameters": { - "anode_jref": 1.36e-09, # A/m² - "anode_jea": 181411, # A/m² - "anode_exp": 0, # Concentration exponent - "cathode_jref": 200, # A/m² - "cathode_jea": 24359, # A/m² - "cathode_ex_a": 1, # Anodic transfer coefficient - "cathode_ex_c": 1, # Cathodic transfer coefficient - "open_voltage": 1.1999, # V - }, - "anode": { - "anode_cc_zone": { - "anode_cc_zone_list": ["anode_cc"], - "anode_cc_material": "collector-default", - }, - "anode_fc_zone": {"anode_fc_zone_list": ["anode_fc"]}, - "anode_pl_zone": { - "anode_pl_zone_list": ["anode_pl"], - "anode_pl_material": "porous-default", - "anode_pl_porosity": 0.75, # Porosity of porous layer - "anode_pl_kr": 4.9e-11, # m² Absolute permeability - "anode_pl_angle": 70, # Degrees - }, - "anode_cl_zone": { - "anode_cl_zone_list": ["anode_cl"], - "anode_cl_material": "catalyst-default", - "anode_cl_porosity": 0.2, # Catalyst layer porosity - "anode_cl_kr": 4.9e-12, # m² Catalyst layer permeability - "anode_cl_angle": 80, # Degrees - }, - }, - "electrolyte": { - "mem_zone": { - "mem_zone_list": ["mem"], - "mem_material": "electrolyte-default", - } - }, - "cathode": { - "cathode_cc_zone": { - "cathode_cc_zone_list": ["cathode_cc"], - "cathode_cc_material": "collector-default", - }, - "cathode_fc_zone": {"cathode_fc_zone_list": ["cathode_fc"]}, - "cathode_pl_zone": { - "cathode_pl_zone_list": ["cathode_pl"], - "cathode_pl_material": "porous-default", - "cathode_pl_porosity": 0.75, # Porosity - "cathode_pl_kr": 1e-11, # m² Permeability - }, - "cathode_cl_zone": { - "cathode_cl_zone_list": ["cathode_cl"], - "cathode_cl_material": "catalyst-default", - "cathode_cl_porosity": 0.2, # Catalyst layer porosity - "cathode_cl_kr": 2e-12, # m² Permeability - }, - }, - "electrical_tab": { - "anode_tab": ["anode_tab", "anode_tab.1", "anode_tab.1.1"], - "cathode_tab": ["cathode_tab", "cathode_tab.1", "cathode_tab.1.1"], - }, - }, -} +echem = EChemistry(solver) +echem.potential = True +echem.echemistry_enabled = True +echem.electrolysis.options.bc_type = echem.electrolysis.options.bc_type.TOTAL_VOLTAGE +echem.electrolysis.options.tot_voltage = 1.730202 * V + +electrolysis_params = echem.electrolysis.parameters +electrolysis_params.anode_jref = 1.36e-09 * A / m**2 +electrolysis_params.anode_jea = 181411 * A / m**2 +electrolysis_params.anode_exp = 0 +electrolysis_params.cathode_jref = 200 * A / m**2 +electrolysis_params.cathode_jea = 24359 * A / m**2 +electrolysis_params.cathode_ex_a = 1 +electrolysis_params.cathode_ex_c = 1 +electrolysis_params.open_voltage = 1.1999 * V + +anode = echem.electrolysis.anode +anode.anode_cc_zone.anode_cc_zone_list = ["anode_cc"] +anode.anode_cc_zone.anode_cc_material = "collector-default" + +anode.anode_fc_zone.anode_fc_zone_list = ["anode_fc"] + +anode.anode_pl_zone.anode_pl_zone_list = ["anode_pl"] +anode.anode_pl_zone.anode_pl_material = "porous-default" +anode.anode_pl_zone.anode_pl_porosity = 0.75 +anode.anode_pl_zone.anode_pl_kr = 4.9e-11 * m**2 +anode.anode_pl_zone.anode_pl_angle = 70 * degree + +anode.anode_cl_zone.anode_cl_zone_list = ["anode_cl"] +anode.anode_cl_zone.anode_cl_material = "catalyst-default" +anode.anode_cl_zone.anode_cl_porosity = 0.2 +anode.anode_cl_zone.anode_cl_kr = 4.9e-12 * m**2 +anode.anode_cl_zone.anode_cl_angle = 80 * degree + +electrolyte = echem.electrolysis.electrolyte +electrolyte.mem_zone.mem_zone_list = ["mem"] +electrolyte.mem_zone.mem_material = "electrolyte-default" + +cathode = echem.electrolysis.cathode +cathode.cathode_cc_zone.cathode_cc_zone_list = ["cathode_cc"] +cathode.cathode_cc_zone.cathode_cc_material = "collector-default" + +cathode.cathode_fc_zone.cathode_fc_zone_list = ["cathode_fc"] +cathode.cathode_pl_zone.cathode_pl_zone_list = ["cathode_pl"] +cathode.cathode_pl_zone.cathode_pl_material = "porous-default" +cathode.cathode_pl_zone.cathode_pl_porosity = 0.75 +cathode.cathode_pl_zone.cathode_pl_kr = 1e-11 * m**2 +cathode.cathode_pl_zone.cathode_pl_angle = 70 * degree +cathode.cathode_cl_zone.cathode_cl_zone_list = ["cathode_cl"] +cathode.cathode_cl_zone.cathode_cl_material = "catalyst-default" +cathode.cathode_cl_zone.cathode_cl_porosity = 0.2 +cathode.cathode_cl_zone.cathode_cl_kr = 2e-12 * m**2 +cathode.cathode_cl_zone.cathode_cl_angle = 80 * degree + +electrical_tab = echem.electrolysis.electrical_tab +electrical_tab.anode_tab = ["anode_tab", "anode_tab.1", "anode_tab.1.1"] +electrical_tab.cathode_tab = ["cathode_tab", "cathode_tab.1", "cathode_tab.1.1"] -# %% -# Define solid materials # ---------------------- materials = Materials(solver) -# Current collector -materials.solid["collector-default"] = { - "electric_conductivity": {"value": 20000} # S/m -} +SolidMaterial.create(solver, name="collector-default", electric_conductivity = 20000 * S / m) -# Porous layer -materials.solid["porous-default"] = {"electric_conductivity": {"value": 20000}} # S/m +SolidMaterial.create(solver, name="porous-default", electric_conductivity = 20000 * S / m) -# Catalyst layer: dual conductivity -materials.solid["catalyst-default"] = { - "electric_conductivity": {"value": 5000}, # S/m Electronic - "dual_electric_conductivity": {"value": 4.5}, # S/m Ionic in catalyst -} +SolidMaterial.create(solver, name="catalyst-default", electrical_conductivity = 5000 * S / m, dual_electric_conductivity = 4.5 * S / m) -# Membrane: ionic conductivity -materials.solid["electrolyte-default"] = { - "dual_electric_conductivity": {"value": 11} # S/m Proton conductivity -} +SolidMaterial.create(solver, name="electrolyte-default", dual_electric_conductivity = 11 * S / m) # %% # Boundary conditions # ------------------- conditions = BoundaryConditions(solver) -# Mixture phase: thermal condition -conditions.mass_flow_inlet["anode_in"] = { - "phase": {"mixture": {"thermal": {"total_temperature": {"value": 333.15}}}} # K -} - -# Phase-2 (liquid water): mass flow rate -conditions.mass_flow_inlet["anode_in"] = { - "phase": {"phase-2": {"momentum": {"mass_flow_rate": {"value": 0.000404}}}} # kg/s -} +# Configure mass flow inlet for anode using typed MassFlowInlet API +anode_in = MassFlowInlet(solver, name="anode_in") +anode_in.phase.mixture.thermal.total_temperature = 333.15 * K +anode_in.phase.phase_2.momentum.mass_flow_rate = 0.000404 # kg/s # %% # Solution controls @@ -254,7 +232,7 @@ controls = Controls(solver) -controls.under_relaxation = {"mp": 1} +controls.under_relaxation.mp = 1 # %% # Initialize solution @@ -262,27 +240,22 @@ initialize = Initialization(solver) initialize.initialization_type = "standard" -initialize.defaults = { - "temperature": 333.15, # K - "phase-2-mp": 1, # Initial volume fraction of liquid -} +initialize.defaults["temperature"] = 333.15 * K +initialize.defaults["phase-2-mp"] = 1 # %% # Run calculation # --------------- -calculation = RunCalculation(solver) - -calculation.iterate(iter_count=300) +iterate(solver, iter_count=300) # %% # Post-processing # --------------- -potential_contour = Contour(solver, new_instance_name="potential_contour") +potential_contour = Contour.create(solver, name="potential_contour", field = "potential", surfaces_list = ["zmid"]) + -potential_contour.field = "potential" -potential_contour.surfaces_list = ["zmid"] graphics.views.restore_view(view_name="front") potential_contour.display() @@ -294,10 +267,7 @@ # :align: center # :alt: Potential Contour -volume_fraction_contour = Contour(solver, new_instance_name="volume_fraction_contour") - -volume_fraction_contour.field = "phase-1-vof" -volume_fraction_contour.surfaces_list = ["zmid", "xmid"] +volume_fraction_contour = Contour.create(solver, name="volume_fraction_contour", field = "phase-1-vof", surfaces_list = ["zmid", "xmid"]) graphics.views.restore_view(view_name="isometric") volume_fraction_contour.display() @@ -310,7 +280,7 @@ # :alt: Volume Fraction Contour # save case and data file -solver.settings.file.write(file_type="case-data", file_name="electrolysis") +write_case_data(solver, file_name="electrolysis") # %% # Close session diff --git a/examples/00-fluent/Modeling_solidification_workflow.py b/examples/00-fluent/Modeling_solidification_workflow.py index 4361bd1b6c9..5bf0f62f44a 100644 --- a/examples/00-fluent/Modeling_solidification_workflow.py +++ b/examples/00-fluent/Modeling_solidification_workflow.py @@ -77,14 +77,17 @@ # Importing the following classes offer streamlined access to key solver settings, # eliminating the need to manually browse through the full settings structure. -import os +from pathlib import Path import ansys.fluent.core as pyfluent from ansys.fluent.core import examples from ansys.fluent.core.solver import ( - BoundaryConditions, + BoundaryCondition, Contour, Controls, + FluidCellZone, + write_case_data, + FluidMaterial, General, Graphics, Initialization, @@ -96,15 +99,19 @@ Setup, Solution, VelocityInlet, + WallBoundary, + Models, ) +from ansys.units import VariableCatalog +from ansys.units.common import J, K, N, Pa, W, kg, m, radian, s # %% # Launch Fluent session in solver mode # ------------------------------------ -solver = pyfluent.launch_fluent( +solver = pyfluent.Solver.from_install( precision=pyfluent.Precision.DOUBLE, - mode="solver", dimension=pyfluent.Dimension.TWO, + fluent_path=r"C:\ANSYSDev\v261\fluent\ntbin\win64\fluent.exe", ) # %% @@ -113,7 +120,7 @@ mesh_file = examples.download_file( "solid.msh", "pyfluent/solidification", - save_path=os.getcwd(), + save_path=Path.cwd(), ) solver.settings.file.read_mesh(file_name=mesh_file) @@ -122,8 +129,7 @@ # Display mesh # ------------ graphics = Graphics(solver) -mesh = Mesh(solver, new_instance_name="mesh-1") -boundary_conditions = BoundaryConditions(solver) +mesh = Mesh.create(solver) graphics.picture.x_resolution = 650 # Horizontal resolution for clear visualization graphics.picture.y_resolution = 450 # Vertical resolution matching typical aspect ratio @@ -134,7 +140,7 @@ mesh.options.edges = True mesh.display() -graphics.picture.save_picture(file_name="modeling_solidification_1.png") +# graphics.picture.save_picture(file_name="modeling_solidification_1.png") # %% # .. image:: ../../_static/modeling_solidification_1.png @@ -144,14 +150,12 @@ # %% # Configure solver # ---------------- -solver_general_settings = General(solver) +general = General(solver) -solver_general_settings.solver.two_dim_space = "swirl" +general.solver.two_dim_space = "swirl" -solver_general_settings.operating_conditions.gravity = { - "enable": True, - "components": [-9.81], -} +general.operating_conditions.gravity.enable = True +general.operating_conditions.gravity.components = [-9.81 * m / s**2] # %% # Enable models @@ -164,93 +168,92 @@ setup.models.viscous.model = "laminar" -# Enable the Solidification/Melting solver.tui.define.models.solidification_melting( - "yes", "constant", "100000", "yes", "no" # 100000 for the Mushy Zone Constant. + "yes", # Enable Solidification/Melting model + "constant", # Mushy Zone Parameter + "100000", # Mushy Zone Constant + "yes", # Include Pull Velocities + "no", # Compute Pull Velocities ) +Models(solver) + # %% # Define material # --------------- -materials = Materials(solver) - -materials.database.copy_by_name(type="fluid", name="air", new_name="liquid-metal") - -materials.fluid["liquid-metal"] = { - "density": { - "polynomial": { - "coefficients": [ - 8000, - -0.1, - ], # [Density (kg/m³), Linear temp coefficient (kg/(m³·K))] - "function_of": "temperature", - }, - "option": "polynomial", - }, - "viscosity": {"value": 0.00553}, # Pa·s - "specific_heat": {"value": 680.0}, # J/kg·K - "thermal_conductivity": {"value": 30.0}, # W/m·K - "melting_heat": {"value": 100000.0}, # J/kg - "tsolidus": {"value": 1150.0}, # K - "tliqidus": {"value": 1150.0}, # K -} - -# Assign material to fluid zone -setup.cell_zone_conditions.fluid["fluid"] = {"general": {"material": "liquid-metal"}} +Materials(solver).database.copy_by_name(type="fluid", name="air", new_name="liquid-metal") + +liquid_metal = FluidMaterial( + solver, + name="liquid-metal", + viscosity=0.00553 * Pa * s, + specific_heat=680.0 * J / kg / K, + thermal_conductivity=30.0 * W / m / K, + melting_heat=100000.0 * J / kg, + tsolidus=1150.0 * K, + tliqidus=1150.0 * K, +) +liquid_metal.density.option = "polynomial" +liquid_metal.density.polynomial.coefficients = [ + 8000, + -0.1, +] # [Density (kg/m³), Linear temp coefficient (kg/(m³·K))] + +# Assign material to fluid zone using a typed cell-zone object +fluid_zone = FluidCellZone.get(solver, name="fluid") +fluid_zone.general.material = liquid_metal # %% # Boundary conditions # ------------------- # Inlet: liquid injection -inlet = VelocityInlet(solver, name="inlet") +inlet = VelocityInlet.get(solver, name="inlet") -inlet.momentum.velocity_magnitude.value = 0.00101 # m/s -inlet.thermal.temperature.value = 1300 # K +inlet.momentum.velocity_magnitude = 0.00101 * m / s +inlet.thermal.temperature = 1300 * K # Outlet: solid pull-out (velocity inlet with axial + swirl) -outlet = VelocityInlet(solver, name="outlet") +outlet = VelocityInlet.get(solver, name="outlet") outlet.momentum.velocity_specification_method = "Components" -outlet.momentum.swirl_angular_velocity = 1 # rad/s -outlet.momentum.velocity_components = [0.001, 0, 0] # Axial = 0.001 m/s -outlet.thermal.temperature.value = 500 # K - - -conditions = BoundaryConditions(solver) +outlet.momentum.swirl_angular_velocity = 1 * radian / s +outlet.momentum.velocity_components = (0.001, 0, 0) * m / s # axial, radial, tangential +outlet.thermal.temperature.value = 500 * K # Bottom wall: fixed temperature -conditions.wall["bottom-wall"] = { - "thermal": {"thermal_condition": "Temperature", "temperature": 1300} # K -} +bottom_wall = WallBoundary.get(solver, name="bottom-wall") +bottom_wall.thermal.thermal_condition = ( + bottom_wall.thermal.thermal_condition.TEMPERATURE +) +bottom_wall.thermal.temperature = 1300 * K # Free surface: Marangoni stress + convection -conditions.wall["free-surface"] = { - "momentum": { - "shear_condition": "Marangoni Stress", - "surface_tension_gradient": -0.00036, # N/m·K - }, - "thermal": { - "thermal_condition": "Convection", - "free_stream_temp": 1500, # K - "heat_transfer_coeff": 100, # W/m²·K - }, -} +free_surface = WallBoundary.get(solver, name="free-surface") +free_surface.momentum.shear_condition = ( + free_surface.momentum.shear_condition.MARANGONI_STRESS +) +free_surface.momentum.surface_tension_gradient = -0.00036 * N / (m * K) +free_surface.thermal.thermal_condition = ( + free_surface.thermal.thermal_condition.CONVECTION +) +free_surface.thermal.convection.free_stream_temperature = 1500 * K +free_surface.thermal.convection.convective_heat_transfer_coefficient = ( + 100 * W / (m**2 * K) +) # Side wall: fixed temperature -conditions.wall["side-wall"] = { - "thermal": {"thermal_condition": "Temperature", "temperature": 1400} # K -} +side_wall = WallBoundary.get(solver, name="side-wall") +side_wall.thermal.thermal_condition = side_wall.thermal.thermal_condition.TEMPERATURE +side_wall.thermal.temperature = 1400 * K # Solid wall: rotating + cold -conditions.wall["solid-wall"] = { - "momentum": { - "wall_motion": "Moving Wall", - "velocity_spec": "Rotational", - "rotation_speed": 1, # rad/s - }, - "thermal": {"thermal_condition": "Temperature", "temperature": 500}, # K -} +solid_wall = WallBoundary.get(solver, name="solid-wall") +solid_wall.momentum.wall_motion = "Moving Wall" +solid_wall.momentum.velocity_spec = "Rotational" +solid_wall.momentum.rotation_speed = 1 * radian / s +solid_wall.thermal.thermal_condition = solid_wall.thermal.thermal_condition.TEMPERATURE +solid_wall.thermal.temperature = 500 * K # %% # Solution methods @@ -258,15 +261,16 @@ methods = Methods(solver) methods.p_v_coupling.flow_scheme = "Coupled" -methods.spatial_discretization.discretization_scheme = {"pressure": "presto!"} -methods.pseudo_time_method.formulation = {"coupled_solver": "global-time-step"} +methods.spatial_discretization.discretization_scheme["pressure"] = "presto!" +methods.pseudo_time_method.formulation.coupled_solver = "global-time-step" # %% # Disable flow equations # ---------------------- controls = Controls(solver) -controls.equations = {"flow": False, "w-swirl": False} +controls.equations["flow"] = False +controls.equations["w-swirl"] = False # %% @@ -280,8 +284,9 @@ # ---------------------------- results = Results(solver) -results.custom_field_functions.create( - name="omegar", custom_field_function="1 * radial_coordinate" # ω = 1 rad/s +omega_r = results.custom_field_functions.create( + name="omegar", + custom_field_function="1 * radial_coordinate", # ω = 1 rad/s ) # %% @@ -294,7 +299,7 @@ variable="x-pull-velocity", reference_frame="Relative to Cell Zone", use_custom_field_function=True, - custom_field_function_name="omegar", + custom_field_function_name=omega_r.name(), value=0.001, ) @@ -304,28 +309,27 @@ variable="z-pull-velocity", reference_frame="Relative to Cell Zone", use_custom_field_function=True, - custom_field_function_name="omegar", + custom_field_function_name=omega_r.name(), ) # %% # Pseudo-transient settings # ------------------------- -solver.settings.solution.run_calculation.pseudo_time_settings.time_step_method = { - "time_step_method": "user-specified", - "auto_time_size_calc_solid_zone": False, -} +calculation = RunCalculation(solver) + +calculation.pseudo_time_settings.time_step_method.time_step_method = "user-specified" +calculation.pseudo_time_settings.time_step_method.auto_time_size_calc_solid_zone = False -calculation = RunCalculation(solver) calculation.iterate(iter_count=20) # %% # Post-processing # --------------- -temp_contour = Contour(solver, new_instance_name="temperature_contour") - +temp_contour = Contour.create( + solver, name="temperature_contour", field=VariableCatalog.TEMPERATURE +) temp_contour.coloring.option = "banded" -temp_contour.field = "temperature" temp_contour.display() graphics.views.restore_view(view_name="front") @@ -337,13 +341,15 @@ # :alt: Temperature Contours -mushy_temp = Contour(solver, new_instance_name="temperature-mushy") +mushy_temp = Contour.create( + solver, name="temperature-mushy", field=VariableCatalog.TEMPERATURE +) mushy_temp.coloring.option = "banded" -mushy_temp.field = "temperature" -mushy_temp.range_option = { - "option": "auto-range-off", - "auto_range_off": {"clip_to_range": True, "minimum": 1100, "maximum": 1200}, -} +# set explicit contour range +mushy_temp.range.option = "auto-range-off" +mushy_temp.range.auto_range_off.clip_to_range = True +mushy_temp.range.auto_range_off.minimum = 1100 * K +mushy_temp.range.auto_range_off.maximum = 1200 * K mushy_temp.display() graphics.views.restore_view(view_name="front") @@ -356,17 +362,18 @@ # Save steady state case -solver.settings.file.write_case_data(file_name="steady_state") +write_case_data(file_name="steady_state") # %% # Enable transient flow and heat transfer # --------------------------------------- -solver_general_settings.solver.time = "unsteady-1st-order" # First-order implicit +general.solver.time = "unsteady-1st-order" # First-order implicit -controls.equations = {"flow": True, "w-swirl": True} +controls.equations["flow"] = True +controls.equations["w-swirl"] = True -controls.under_relaxation = {"delh": 0.1} +controls.under_relaxation["delh"] = 0.1 # %% # Transient controls @@ -378,9 +385,9 @@ solutions.run_calculation.calculate() # Liquid fraction at t = 0.2 s -liquid_fraction_contour = Contour(solver, new_instance_name="liquid-fraction") - -liquid_fraction_contour.field = "liquid-fraction" +liquid_fraction_contour = Contour.create( + solver, name="liquid-fraction", field="liquid-fraction" +) liquid_fraction_contour.display() graphics.picture.save_picture(file_name="modeling_solidification_4.png") @@ -396,9 +403,9 @@ solutions.run_calculation.calculate() # Liquid fraction at t = 5.0 s -liquid_fraction_contour_t_5_sec = Contour(solver, new_instance_name="liquid-fraction") - -liquid_fraction_contour_t_5_sec.field = "liquid-fraction" +liquid_fraction_contour_t_5_sec = Contour.create( + solver, name="liquid-fraction", field="liquid-fraction" +) liquid_fraction_contour_t_5_sec.display() graphics.picture.save_picture(file_name="modeling_solidification_5.png") @@ -409,7 +416,7 @@ # :alt: Liquid Fraction at t = 5 s # Save transient case -solver.settings.file.write_case_data(file_name="unsteady_state") +write_case_data(file_name="unsteady_state") # %% # Close session diff --git a/examples/00-fluent/ahmed_body_workflow.py b/examples/00-fluent/ahmed_body_workflow.py index a0318f5fb8b..b18adc3f3da 100644 --- a/examples/00-fluent/ahmed_body_workflow.py +++ b/examples/00-fluent/ahmed_body_workflow.py @@ -61,18 +61,36 @@ # Import required libraries/modules # ===================================================================================== -import os +from pathlib import Path import platform +from ansys.units import VariableCatalog + import ansys.fluent.core as pyfluent from ansys.fluent.core import examples +from ansys.fluent.core.solver import ( + Methods, + ReferenceValues, + Residual, + iterate, write_case, + FluidMaterial, + Initialization, + IsoSurface, + Monitor, + OutputParameters, + PressureOutlet, + ReportDefinitions, + VelocityInlet, + Viscous, +) from ansys.fluent.visualization import Contour, GraphicsWindow +from ansys.units.common import kg, m, s ####################################################################################### # Launch Fluent session with meshing mode and print Fluent version # ===================================================================================== -session = pyfluent.launch_fluent(mode="meshing", cleanup_on_exit=True) -print(session.get_fluent_version()) +meshing = pyfluent.Meshing.from_install(cleanup_on_exit=True, fluent_path=r"C:\ANSYSDev\v261\fluent\ntbin\win64\fluent.exe") +print(meshing.get_fluent_version()) ####################################################################################### # Meshing Workflow @@ -82,7 +100,7 @@ # Initialize the Meshing Workflow # ===================================================================================== -workflow = session.workflow +workflow = meshing.workflow filenames = { "Windows": "ahmed_body_20_0degree_boi_half.scdoc", @@ -92,54 +110,49 @@ geometry_filename = examples.download_file( filenames.get(platform.system(), filenames["Other"]), "pyfluent/examples/Ahmed-Body-Simulation", - save_path=os.getcwd(), + save_path=Path.cwd(), ) +meshing.upload(geometry_filename) workflow.InitializeWorkflow(WorkflowType="Watertight Geometry") -workflow.TaskObject["Import Geometry"].Arguments = dict(FileName=geometry_filename) +workflow.TaskObject["Import Geometry"].Arguments = {"FileName": geometry_filename} workflow.TaskObject["Import Geometry"].Execute() ####################################################################################### # Add Local Face Sizing # ===================================================================================== add_local_sizing = workflow.TaskObject["Add Local Sizing"] -add_local_sizing.Arguments = dict( - { - "AddChild": "yes", - "BOIControlName": "facesize_front", - "BOIFaceLabelList": ["wall_ahmed_body_front"], - "BOIGrowthRate": 1.15, - "BOISize": 8, - } -) +add_local_sizing.Arguments = { + "AddChild": "yes", + "BOIControlName": "facesize_front", + "BOIFaceLabelList": ["wall_ahmed_body_front"], + "BOIGrowthRate": 1.15, + "BOISize": 8, +} add_local_sizing.Execute() add_local_sizing.InsertCompoundChildTask() workflow.TaskObject["Add Local Sizing"].Execute() add_local_sizing = workflow.TaskObject["Add Local Sizing"] -add_local_sizing.Arguments = dict( - { - "AddChild": "yes", - "BOIControlName": "facesize_rear", - "BOIFaceLabelList": ["wall_ahmed_body_rear"], - "BOIGrowthRate": 1.15, - "BOISize": 5, - } -) +add_local_sizing.Arguments = { + "AddChild": "yes", + "BOIControlName": "facesize_rear", + "BOIFaceLabelList": ["wall_ahmed_body_rear"], + "BOIGrowthRate": 1.15, + "BOISize": 5, +} add_local_sizing.Execute() add_local_sizing.InsertCompoundChildTask() workflow.TaskObject["Add Local Sizing"].Execute() add_local_sizing = workflow.TaskObject["Add Local Sizing"] -add_local_sizing.Arguments = dict( - { - "AddChild": "yes", - "BOIControlName": "facesize_main", - "BOIFaceLabelList": ["wall_ahmed_body_main"], - "BOIGrowthRate": 1.15, - "BOISize": 12, - } -) +add_local_sizing.Arguments = { + "AddChild": "yes", + "BOIControlName": "facesize_main", + "BOIFaceLabelList": ["wall_ahmed_body_main"], + "BOIGrowthRate": 1.15, + "BOISize": 12, +} add_local_sizing.Execute() ####################################################################################### @@ -147,15 +160,13 @@ # ===================================================================================== add_boi_sizing = workflow.TaskObject["Add Local Sizing"] add_boi_sizing.InsertCompoundChildTask() -add_boi_sizing.Arguments = dict( - { - "AddChild": "yes", - "BOIControlName": "boi_1", - "BOIExecution": "Body Of Influence", - "BOIFaceLabelList": ["ahmed_body_20_0degree_boi_half-boi"], - "BOISize": 20, - } -) +add_boi_sizing.Arguments = { + "AddChild": "yes", + "BOIControlName": "boi_1", + "BOIExecution": "Body Of Influence", + "BOIFaceLabelList": ["ahmed_body_20_0degree_boi_half-boi"], + "BOISize": 20, +} add_boi_sizing.Execute() add_boi_sizing.InsertCompoundChildTask() @@ -164,17 +175,15 @@ # Add Surface Mesh Sizing # ===================================================================================== generate_surface_mesh = workflow.TaskObject["Generate the Surface Mesh"] -generate_surface_mesh.Arguments = dict( - { - "CFDSurfaceMeshControls": { - "CurvatureNormalAngle": 12, - "GrowthRate": 1.15, - "MaxSize": 50, - "MinSize": 1, - "SizeFunctions": "Curvature", - } +generate_surface_mesh.Arguments = { + "CFDSurfaceMeshControls": { + "CurvatureNormalAngle": 12, + "GrowthRate": 1.15, + "MaxSize": 50, + "MinSize": 1, + "SizeFunctions": "Curvature", } -) +} generate_surface_mesh.Execute() generate_surface_mesh.InsertNextTask(CommandName="ImproveSurfaceMesh") @@ -185,10 +194,10 @@ ####################################################################################### # Describe Geometry, Update Boundaries, Update Regions # ===================================================================================== -workflow.TaskObject["Describe Geometry"].Arguments = dict( - CappingRequired="Yes", - SetupType="The geometry consists of only fluid regions with no voids", -) +workflow.TaskObject["Describe Geometry"].Arguments = { + "CappingRequired": "Yes", + "SetupType": "The geometry consists of only fluid regions with no voids", +} workflow.TaskObject["Describe Geometry"].Execute() workflow.TaskObject["Update Boundaries"].Execute() workflow.TaskObject["Update Regions"].Execute() @@ -220,7 +229,7 @@ ####################################################################################### # Switch to the Solver Mode # ===================================================================================== -session = session.switch_to_solver() +solver = meshing.switch_to_solver() ####################################################################################### # Mesh Visualization @@ -243,107 +252,110 @@ ####################################################################################### # Define Constants # ===================================================================================== -density = 1.225 -inlet_velocity = 30 -inlet_area = 0.11203202 +density = 1.225 * kg / m**3 +inlet_velocity = 30 * m / s +inlet_area = 0.11203202 * m**2 ####################################################################################### # Define Materials # ===================================================================================== -session.tui.define.materials.change_create("air", "air", "yes", "constant", density) -session.settings.setup.models.viscous.model = "k-epsilon" -session.settings.setup.models.viscous.k_epsilon_model = "realizable" -session.settings.setup.models.viscous.options.curvature_correction = True +air = FluidMaterial.get(solver, name="air") +air.density = density + +viscous = Viscous(solver=solver) +viscous.model = viscous.model.K_EPSILON +viscous.k_epsilon_model = viscous.k_epsilon_model.REALIZABLE +viscous.options.curvature_correction = True ####################################################################################### # Define Boundary Conditions # ===================================================================================== -inlet = session.settings.setup.boundary_conditions.velocity_inlet["inlet"] +inlet = VelocityInlet.get(solver, name="inlet") inlet.turbulence.turb_intensity = 0.05 inlet.momentum.velocity.value = inlet_velocity inlet.turbulence.turb_viscosity_ratio = 5 -outlet = session.settings.setup.boundary_conditions.pressure_outlet["outlet"] +outlet = PressureOutlet.get(solver, name="outlet") outlet.turbulence.turb_intensity = 0.05 ####################################################################################### # Define Reference Values # ===================================================================================== -session.settings.setup.reference_values.area = inlet_area -session.settings.setup.reference_values.density = density -session.settings.setup.reference_values.velocity = inlet_velocity +ref_values = ReferenceValues(solver) +ref_values.area = inlet_area +ref_values.density = density +ref_values.velocity = inlet_velocity ####################################################################################### # Define Solver Settings # ===================================================================================== -session.tui.solve.set.p_v_coupling(24) - -session.tui.solve.set.discretization_scheme("pressure", 12) -session.tui.solve.set.discretization_scheme("k", 1) -session.tui.solve.set.discretization_scheme("epsilon", 1) -session.tui.solve.initialize.set_defaults("k", 0.000001) - -session.settings.solution.monitor.residual.equations["continuity"].absolute_criteria = ( - 0.0001 -) -session.settings.solution.monitor.residual.equations["x-velocity"].absolute_criteria = ( - 0.0001 -) -session.settings.solution.monitor.residual.equations["y-velocity"].absolute_criteria = ( - 0.0001 -) -session.settings.solution.monitor.residual.equations["z-velocity"].absolute_criteria = ( - 0.0001 -) -session.settings.solution.monitor.residual.equations["k"].absolute_criteria = 0.0001 -session.settings.solution.monitor.residual.equations["epsilon"].absolute_criteria = ( - 0.0001 -) +methods = Methods(solver) +methods.p_v_coupling.flow_scheme = "Coupled" + +discretization_scheme = methods.spatial_discretization.discretization_scheme +discretization_scheme["pressure"] = "second-order" +discretization_scheme["k"] = "second-order-upwind" +discretization_scheme["epsilon"] = "second-order-upwind" +initialization = Initialization(solver) +initialization.defaults.k = 0.000001 + +residual = Residual(solver) +for monitor in ( + "continuity", + "x-velocity", + "y-velocity", + "z-velocity", + "k", + "epsilon", +): + residual.equations[monitor].absolute_criteria = 1e-4 ####################################################################################### # Define Report Definitions # ===================================================================================== -session.settings.solution.report_definitions.drag["cd-mon1"] = {} -session.settings.solution.report_definitions.drag["cd-mon1"] = { - "zones": ["wall_ahmed_body_main", "wall_ahmed_body_front", "wall_ahmed_body_rear"], - "force_vector": [0, 0, 1], -} -session.settings.parameters.output_parameters.report_definitions.create( - name="parameter-1" +drag = ReportDefinitions(solver).drag.create( + name="cd-mon1", + zones=[ + "wall_ahmed_body_main", + "wall_ahmed_body_front", + "wall_ahmed_body_rear", + ], + force_vector=(0, 0, 1), ) -session.settings.parameters.output_parameters.report_definitions["parameter-1"] = { - "report_definition": "cd-mon1" -} -session.settings.solution.monitor.report_plots.create(name="cd-mon1") -session.settings.solution.monitor.report_plots["cd-mon1"] = {"report_defs": ["cd-mon1"]} +params_report_defs = OutputParameters(solver).report_definitions +param_1 = params_report_defs.create(report_def_name=drag) + +monitor = Monitor(solver) +plot_mon = monitor.report_plots.create(name=drag, print=True, report_defs=[drag]) ####################################################################################### # Initialize and Run Solver # ===================================================================================== -session.settings.solution.run_calculation.iter_count = 5 -session.settings.solution.initialization.initialization_type = "standard" -session.settings.solution.initialization.standard_initialize() -session.settings.solution.run_calculation.iterate(iter_count=5) +init = Initialization(solver) +init.initialization_type = "standard" +init.standard_initialize() +iterate(solver, iter_count=5) ####################################################################################### # Post-Processing Workflow # ===================================================================================== -session.settings.results.surfaces.iso_surface.create(name="xmid") -session.settings.results.surfaces.iso_surface["xmid"].field = "x-coordinate" -session.settings.results.surfaces.iso_surface["xmid"] = {"iso_values": [0]} +iso = IsoSurface.create(solver, name="xmid", field="x-coordinate", iso_values=[0 * m]) -contour1 = Contour(solver=session, field="velocity-magnitude", surfaces=["xmid"]) +velocity_mag = Contour( + solver=solver, field=VariableCatalog.VELOCITY_MAGNITUDE, surfaces=["xmid"] +) disp1 = GraphicsWindow() -disp1.add_graphics(contour1) +disp1.add_graphics(velocity_mag) disp1.show() -contour2 = Contour(solver=session, field="pressure-coefficient", surfaces=["xmid"]) -assert "pressure-coefficient" in contour2.field.allowed_values +pressure_coeff = Contour( + solver=solver, field=VariableCatalog.PRESSURE_COEFFICIENT, surfaces=["xmid"] +) disp2 = GraphicsWindow() -disp2.add_graphics(contour2) +disp2.add_graphics(pressure_coeff) disp2.show() ####################################################################################### @@ -369,12 +381,12 @@ ####################################################################################### # Save the case file # ===================================================================================== -session.settings.file.write(file_type="case-data", file_name="ahmed_body_final.cas.h5") +write_case(solver, file_name="ahmed_body_final.cas.h5") ####################################################################################### # Close the session # ===================================================================================== -session.exit() +solver.exit() ####################################################################################### diff --git a/examples/00-fluent/battery_pack.py b/examples/00-fluent/battery_pack.py index 2b94a025256..509324da4f4 100644 --- a/examples/00-fluent/battery_pack.py +++ b/examples/00-fluent/battery_pack.py @@ -72,14 +72,14 @@ # Importing the following classes offers streamlined access to key solver settings, # eliminating the need to manually browse through the full hierarchy of settings APIs structure. -import os +from pathlib import Path + +from ansys.units import VariableCatalog import ansys.fluent.core as pyfluent from ansys.fluent.core import examples from ansys.fluent.core.solver import ( Battery, - BoundaryConditions, - CellZoneConditions, Contour, Controls, General, @@ -89,18 +89,31 @@ Mesh, ReportDefinitions, RunCalculation, + SolidMaterial, Solution, Vector, + write_case_data, + WallBoundary, + SolidCellZone, + ReportPlot, + read_mesh, ) from ansys.fluent.visualization import GraphicsWindow, Monitor +from ansys.units.common import K, W, m, ohm + +# %% +# Define constants +# ---------------- + +S = 1 / ohm # a Siemen + # %% # Launch Fluent in solver mode # ---------------------------- -solver = pyfluent.launch_fluent( +solver = pyfluent.Solver.from_install( precision=pyfluent.Precision.DOUBLE, - mode=pyfluent.FluentMode.SOLVER, ) # %% @@ -110,23 +123,22 @@ mesh_file = examples.download_file( "1P3S_battery_pack.msh", "pyfluent/battery_pack", - save_path=os.getcwd(), + save_path=Path.cwd(), ) -solver.settings.file.read_mesh(file_name=mesh_file) +solver.setting.file.read_mesh(file_name=mesh_file) # %% # Display mesh # ------------ graphics = Graphics(solver) -mesh = Mesh(solver, new_instance_name="mesh-1") - -all_walls = mesh.surfaces_list.allowed_values() +mesh = Mesh.create(solver, name="mesh-1") graphics.picture.x_resolution = 650 # Horizontal resolution for clear visualization graphics.picture.y_resolution = 450 # Vertical resolution matching typical aspect ratio +all_walls = mesh.surfaces_list.allowed_values() mesh.surfaces_list = all_walls mesh.options.edges = True mesh.display() @@ -142,9 +154,9 @@ # Solver settings # --------------- -solver_general_settings = General(solver) +general = General(solver) -solver_general_settings.solver.time = "unsteady-1st-order" +general.solver.time = "unsteady-1st-order" # %% # Enable Battery Model (NTGK/DCIR) @@ -162,7 +174,7 @@ battery_model.enabled = True battery_model.echem_model = "ntgk/dcir" battery_model.eload_condition.eload_settings.eload_type = "specified-system-power" -battery_model.eload_condition.eload_settings.power_value = 200 # W (Total pack power) +battery_model.eload_condition.eload_settings.power_value = 200 * W # Total pack power # Conductive zones battery_model.zone_assignment.active_zone = "cell_*" # Active cells @@ -179,67 +191,41 @@ materials = Materials(solver) # Active material (cells): conductivity via UDS-0 and UDS-1 -materials.solid.create("e_material") - -materials.solid["e_material"] = { - "chemical_formula": "e", - "thermal_conductivity": {"value": 20}, # W/(m·K) - "uds_diffusivity": { - "option": "defined-per-uds", - "uds_diffusivities": { - "uds-0": {"value": 1000000}, # S/m (Electronic conductivity) - "uds-1": {"value": 1000000}, # S/m (Ionic conductivity) - }, - }, -} +e_material = SolidMaterial.create(solver, name="e_material", chemical_formula="e") +e_material.thermal_conductivity = 20 * W / (m * K) +e_material.uds_diffusivity.option = "defined-per-uds" +e_material.uds_diffusivity.uds_diffusivities["uds-0"] = ( + 1e6 * S / m +) # Electronic conductivity +e_material.uds_diffusivity.uds_diffusivities["uds-1"] = ( + 1e6 * S / m +) # Ionic conductivity # Passive material (busbars & tabs): high constant conductivity -materials.solid.create("busbar_material") - -materials.solid["busbar_material"] = { - "chemical_formula": "bus", - "uds_diffusivity": { - "option": "value", - "value": 3.541e7, # S/m (Copper-like conductivity) - }, -} +busbar_material = SolidMaterial.create( + solver, name="busbar_material", chemical_formula="bus" +) +busbar_material.uds_diffusivity.option = "value" +busbar_material.uds_diffusivity.value = 3.541e7 * S / m # Copper-like conductivity # %% # Assign materials to cell zones # ------------------------------ -cell_zone_conditions = CellZoneConditions(solver) - -# Assign e_material to cell_1 -cell_zone_conditions.solid["cell_1"] = {"general": {"material": "e_material"}} +# Assign e_material to cell_1 2 and 3 all at once +SolidCellZone.get(solver, name="cell_*").general.material = e_material -# Copy to cell_2 and cell_3 -cell_zone_conditions.copy(from_="cell_1", to="cell_*") - -# Assign busbar_material to bar1 -cell_zone_conditions.solid["bar1"] = {"general": {"material": "busbar_material"}} - -# Copy to all passive zones -cell_zone_conditions.copy(from_="bar1", to="*bar*|*tabzone*") -# '*bar*' matches any zone containing 'bar', -# '|*tabzone*' matches any zone containing 'tabzone' → OR logic +# Assign busbar_material to bar1 and all passive zones +SolidCellZone.get(solver, name="*bar*|*tabzone*").general.material = busbar_material # %% # Boundary conditions # ------------------- -conditions = BoundaryConditions(solver) - -# Convection on wall-cell_1 -conditions.wall["wall-cell_1"] = { - "thermal": { - "thermal_condition": "Convection", - "heat_transfer_coeff": {"value": 5}, # W/(m²·K) - } -} - -# Copy to all other walls (tabs, busbars, cells) -conditions.copy(from_="wall-cell_1", to="wall*") +# Convection on all walls (tabs, busbars, cells) +wall_bc = WallBoundary.get(solver, name="wall*") +wall_bc.thermal.thermal_condition = wall_bc.thermal.thermal_condition.CONVECTION +wall_bc.thermal.heat_transfer_coeff = 5 * W / (m**2 * K) # %% # Define solution controls and monitors @@ -247,10 +233,8 @@ controls = Controls(solver) # Disable flow and turbulence equations -controls.equations = { - "flow": False, - "kw": False, -} +controls.equations["flow"] = False +controls.equations["kw"] = False solution = Solution(solver) @@ -264,34 +248,35 @@ definitions = ReportDefinitions(solver) # Surface report: voltage at positive tab (area-weighted average) -definitions.surface["voltage_surface_areaavg"] = { - "report_type": "surface-areaavg", - "field": "passive-zone-potential", - "surface_names": ["tab_p"], - "create_report_file": True, - "create_report_plot": True, -} +definitions.surface.create( + name="voltage_surface_areaavg", + report_type="surface-areaavg", + field="passive-zone-potential", + surface_names=["tab_p"], + create_report_file=True, + create_report_plot=True, +) # Format plot axes -report_plot = solver.settings.solution.monitor.report_plots[ - "voltage_surface_areaavg-rplot" -] -report_plot.axes.x.number_format.precision = 0 # Integer time steps -report_plot.axes.y.number_format.precision = 2 # 2 decimal places for voltage +voltage_surface_areaavg = ReportPlot.get(solver, name="voltage_surface_areaavg-rplot") +voltage_surface_areaavg.axes.x.number_format.precision = 0 # Integer time steps +voltage_surface_areaavg.axes.y.number_format.precision = ( + 2 # 2 decimal places for voltage +) # Volume report: maximum temperature in all cell zones -definitions.volume["volume_max_temp"] = { - "report_type": "volume-max", - "field": "temperature", - "cell_zones": "*cell|*bar*|*tabzone*", - "create_report_file": True, - "create_report_plot": True, -} +vol_max = definitions.volume.create( + name="volume_max_temp", + report_type="volume-max", + field=VariableCatalog.TEMPERATURE, + cell_zones=["*cell|*bar*|*tabzone*"], + create_report_file=True, + create_report_plot=True, +) -# Format plot axes -report_plot_1 = solver.settings.solution.monitor.report_plots["volume_max_temp-rplot"] -report_plot_1.axes.x.number_format.precision = 0 -report_plot_1.axes.y.number_format.precision = 2 +volume_max_temp = ReportPlot.get(solver, name="volume_max_temp-rplot") +volume_max_temp.axes.x.number_format.precision = 0 +volume_max_temp.axes.y.number_format.precision = 2 # %% # Initialize solution @@ -302,24 +287,28 @@ # %% # Transient controls # ------------------ -Transient_controls = solver.settings.solution.run_calculation.transient_controls +calculation = RunCalculation(solver) -Transient_controls.time_step_count = 50 # Number of time steps -Transient_controls.time_step_size = 30 # s (30 s per step) +transient_controls = calculation.transient_controls +# Use typed quantities for time step settings +transient_controls.time_step_count = 50 # Number of time steps +transient_controls.time_step_size = 30 # 30s per step -calculation = RunCalculation(solver) -calculation.calculate() # Run transient simulation +# Run transient simulation +calculation.calculate() # %% # Post-processing # --------------- # Current density vector plot -vector = Vector(solver, new_instance_name="current-magnitude-vector") - -vector.vector_field = "current-density-j" # A/m² (Current density vector) -vector.field = "current-magnitude" # A/m² (Magnitude for coloring) -vector.surfaces_list = ["tab_n", "tab_p", "wall*"] +vector = Vector.create( + solver, + name="current-magnitude-vector", + vector_field="current-density-j", # A/m² (Current density vector) + field="current-magnitude", # A/m² (Magnitude for coloring) + surfaces_list=["tab_n", "tab_p", "wall*"], +) vector.options.vector_style = "arrow" vector.options.scale = 0.03 # Scale factor for visibility vector.vector_opt.fixed_length = True # Uniform arrow length @@ -334,10 +323,12 @@ # :alt: Current density vector plot # Temperature contour -temp_contour = Contour(solver, new_instance_name="temp_contour") - -temp_contour.field = "temperature" # K -temp_contour.surfaces_list = ["tab_n", "tab_p", "wall*"] +temp_contour = Contour.create( + solver, + name="temp_contour", + field=VariableCatalog.TEMPERATURE, # K + surfaces_list=["tab_n", "tab_p", "wall*"], +) temp_contour.colorings.banded = True temp_contour.display() @@ -350,10 +341,11 @@ # :alt: Temperature contour # Joule heat source contour -joule_contour = Contour(solver, new_instance_name="joule_heating_contour") - -joule_contour.field = "battery-joule-heat-source" # W/m³ -joule_contour.surfaces_list = ["tab_n", "tab_p", "wall*"] +joule_contour = Contour.create( + solver, + field="battery-joule-heat-source", # W/m³ + surfaces_list=["tab_n", "tab_p", "wall*"], +) joule_contour.colorings.banded = True joule_contour.display() @@ -366,10 +358,12 @@ # :alt: Joule heat source contour # Total heat source contour -total_heat_contour = Contour(solver, new_instance_name="total_heating_contour") - -total_heat_contour.field = "total-heat-source" # W/m³ (Joule + reaction heat) -total_heat_contour.surfaces_list = ["tab_n", "tab_p", "wall*"] +total_heat_contour = Contour.create( + solver, + name="total_heating_contour", + field="total-heat-source", # W/m³ (Joule + reaction heat) + surfaces_list=["tab_n", "tab_p", "wall*"], +) total_heat_contour.colorings.banded = True total_heat_contour.display() @@ -403,7 +397,7 @@ # %% # Save case and data # ------------------------ -solver.settings.file.write_case_data(file_name="1P3S_Battery_Pack") +write_case_data(solver, file_name="1P3S_Battery_Pack") # %% # Close Fluent diff --git a/examples/00-fluent/brake.py b/examples/00-fluent/brake.py index 3251c94887c..686774f1777 100644 --- a/examples/00-fluent/brake.py +++ b/examples/00-fluent/brake.py @@ -50,18 +50,34 @@ # ================================================================================== import csv -import os +import itertools +from pathlib import Path +from ansys.units import VariableCatalog import matplotlib.pyplot as plt import ansys.fluent.core as pyfluent from ansys.fluent.core import examples +from ansys.fluent.core.generated.solver.settings_242 import report_type +from ansys.fluent.core.generated.solver.settings_builtin_261 import read_case, write_case_data from ansys.fluent.visualization import Contour, GraphicsWindow +from ansys.fluent.core.generated.solver.settings_builtin import Controls, Graphics +from ansys.fluent.core.solver import ( + Energy, + General, + SolidCellZone, + WallBoundary, + ReportDefinitions, + Monitor, + Initialization, + RunCalculation, +) +from ansys.units.common import K, m, W, radian, s import_filename = examples.download_file( "brake.msh.h5", "pyfluent/examples/Brake-Thermal-PyVista-Matplotlib", - save_path=os.getcwd(), + save_path=Path.cwd(), ) #################################################################################### @@ -72,67 +88,56 @@ # Launch Fluent session with solver mode and print Fluent version # --------------------------------------------------------------- -session = pyfluent.launch_fluent(precision="double", processor_count=2, dimension=3) -print(session.get_fluent_version()) +solver = pyfluent.Solver.from_install(precision="double", processor_count=2, dimension=3) +print(solver.get_fluent_version()) #################################################################################### # Import mesh # ------------ -session.settings.file.read_case(file_name=import_filename) +read_case(solver, file_name=import_filename) ############################ # Define models and material # -------------------------- -session.settings.setup.models.energy = {"enabled": True} -session.settings.setup.general.solver.time = "unsteady-2nd-order-bounded" -session.tui.define.materials.copy("solid", "steel") +energy = Energy(solver) +energy.enabled = True + +general = General(solver) +general.solver.time = "unsteady-2nd-order-bounded" + +Materials(solver).database.copy_by_name(type="solid", name="steel") ######################################### # Solve only energy equation (conduction) # --------------------------------------- -session.tui.solve.set.equations("flow", "no", "kw", "no") +controls = Controls(solver) +controls.equations["kw"] = False # Turbulence +controls.equations["flow"] = False # Flow +controls.equations["temperature"] = True # Energy ########################################################################################## # Define disc rotation # -------------------- -# (15.79 rps corresponds to 100 km/h car speed -# with 0.28 m of axis height from ground) -session.settings.setup.cell_zone_conditions.solid["disc2"] = { - "solid_motion": { - "solid_motion_zone_motion_function": "none", - "solid_motion_axis_direction": [0, 1, 0], - "solid_motion_axis_origin": [-0.035, -0.821, 0.045], - "solid_motion_velocity": [0, 0, 0], - "solid_omega": -15.79, - "solid_relative_to_thread": "absolute", - "enable": True, - } -} -session.settings.setup.cell_zone_conditions.solid["disc1"] = { - "solid_motion": { - "solid_motion_zone_motion_function": "none", - "solid_motion_axis_direction": [0, 1, 0], - "solid_motion_axis_origin": [-0.035, -0.821, 0.045], - "solid_motion_velocity": [0, 0, 0], - "solid_omega": -15.79, - "solid_relative_to_thread": "absolute", - "enable": True, - } -} +discs = SolidCellZone.get(solver, name="disc*") +discs.solid_motion.enable = True +discs.solid_motion.solid_motion_zone_motion_function = "none" +discs.solid_motion.solid_motion_axis_direction = [0, 1, 0] +discs.solid_motion.solid_motion_axis_origin = [-0.035, -0.821, 0.045] * m +discs.solid_motion.solid_motion_velocity = [0, 0, 0] * m / s +discs.solid_motion.solid_omega = ( + -15.79 * radian / s +) # 100 km/h car speed with 0.28 m of axis height from ground +discs.solid_motion.solid_relative_to_thread = "absolute" ########################################################################################## # Apply frictional heating on pad-disc surfaces # ---------------------------------------------- # Wall thickness 0f 2 mm has been assumed and 2e9 w/m3 is the heat generation which # has been calculated from kinetic energy change due to braking. - -session.settings.setup.boundary_conditions.wall["wall-pad-disc2"] = { - "thermal": {"q_dot": {"value": 2000000000}, "wall_thickness": {"value": 0.002}} -} -session.settings.setup.boundary_conditions.wall["wall_pad-disc1"] = { - "thermal": {"q_dot": {"value": 2000000000}, "wall_thickness": {"value": 0.002}} -} +wall_pad_discs = WallBoundary.get(solver, name="wall-pad-disc*") +wall_pad_discs.thermal.q_dot = 2e9 * W / m**3 +wall_pad_discs.thermal.wall_thickness = 0.002 * m ########################################################################################## # Apply convection cooling on outer surfaces due to air flow @@ -140,26 +145,18 @@ # Outer surfaces are applied a constant htc of 100 W/(m2 K) # and 300 K free stream temperature -session.tui.define.boundary_conditions.set.wall( - "wall-disc*", - "wall-geom*", - "()", - "thermal-bc", - "yes", - "convection", - "convective-heat-transfer-coefficient", - "no", - 100, - "q", -) +walls = WallBoundary.get(solver, name="wall-disc*|wall-geom*") +walls.thermal.thermal_condition = walls.thermal.thermal_condition.CONVECTION +walls.thermal.convection.convective_heat_transfer_coefficient = 100 * W / (m**2 * K) +walls.thermal.convection.free_stream_temperature = 300 * K ########################################################################################## # Initialize # ---------- # Initialize with 300 K temperature - -session.settings.solution.initialization.initialization_type = "standard" -session.settings.solution.initialization.standard_initialize() +initialization = Initialization(solver) +initialization.initialization_type = "standard" +initialization.standard_initialize() ############################################################################################### # Post processing setup @@ -169,114 +166,64 @@ # * Set views and camera # * Set animation object -session.settings.solution.report_definitions.volume["max-pad-temperature"] = {} -session.settings.solution.report_definitions.volume[ - "max-pad-temperature" -].report_type = "volume-max" -session.settings.solution.report_definitions.volume["max-pad-temperature"] = { - "field": "temperature", - "cell_zones": ["geom-1-innerpad", "geom-1-outerpad"], -} - -session.settings.solution.report_definitions.volume["max-disc-temperature"] = {} -session.settings.solution.report_definitions.volume[ - "max-disc-temperature" -].report_type = "volume-max" -session.settings.solution.report_definitions.volume["max-disc-temperature"] = { - "field": "temperature", - "cell_zones": ["disc1", "disc2"], -} - -session.settings.solution.monitor.report_plots.create(name="max-temperature") -session.settings.solution.monitor.report_plots["max-temperature"] = { - "report_defs": ["max-pad-temperature", "max-disc-temperature"] -} - -session.settings.solution.monitor.report_files.create(name="max-temperature") -session.settings.solution.monitor.report_files["max-temperature"] = { - "report_defs": ["max-pad-temperature", "max-disc-temperature"], - "file_name": "max-temperature.out", -} -session.settings.solution.monitor.report_files["max-temperature"].report_defs = [ - "max-pad-temperature", - "max-disc-temperature", - "flow-time", -] - -session.settings.results.graphics.contour.create(name="contour-1") -session.settings.results.graphics.contour["contour-1"] = { - "surfaces_list": "wall*", - "boundary_values": True, - "range_option": {"auto_range_on": {"global_range": True}}, - "field": "temperature", - "draw_mesh": False, - "coloring": {"smooth": False}, - "color_map": { - "user_skip": 9, - "log_scale": False, - "visible": True, - "width": 6, - "show_all": True, - "font_name": "Helvetica", - "font_size": 0.032, - "font_automatic": True, - "length": 0.54, - "size": 100, - "format": "%0.2e", - "position": 1, - "color": "field-velocity", - }, - "mesh_object": "", - "node_values": True, - "contour_lines": False, - "display_state_name": "None", - "filled": True, -} - -session.settings.results.graphics.contour["temperature"] = { - "field": "temperature", - "surfaces_list": "wall*", - "color_map": { - "visible": True, - "size": 100, - "color": "field-velocity", - "log_scale": False, - "format": "%0.1f", - "user_skip": 9, - "show_all": True, - "position": 1, - "font_name": "Helvetica", - "font_automatic": True, - "font_size": 0.032, - "length": 0.54, - "width": 6, - "bground_transparent": True, - "bground_color": "#CCD3E2", - "title_elements": "Variable and Object Name", - }, -} - -session.settings.results.graphics.contour["temperature"].range_option.option = ( - "auto-range-off" -) -session.settings.results.graphics.contour["temperature"].range_option.set_state( - { - "auto_range_off": {"maximum": 400.0, "minimum": 300, "clip_to_range": False}, - } -) - -session.settings.results.graphics.views.restore_view(view_name="top") -session.settings.results.graphics.views.camera.zoom(factor=2) -session.settings.results.graphics.views.save_view(view_name="animation-view") - -session.settings.solution.calculation_activity.solution_animations[ - "animate-temperature" -] = { - "animate_on": "temperature", - "frequency_of": "flow-time", - "flow_time_frequency": 0.05, - "view": "animation-view", -} +report_defs = ReportDefinitions(solver) + +max_pad_temp = report_defs.volume.create(name="max-pad-temperature", report_type="volume-max", field=VariableCatalog.TEMPERATURE, cell_zones=["geom-1-innerpad", "geom-1-outerpad"]) + + +max_disc_temp = report_defs.volume.create(name="max-disc-temperature", +report_type = "volume-max", +field = "temperature", +cell_zones = ["disc1", "disc2"],) + +monitor = Monitor(solver) +temp_plot = monitor.report_plots.create(name="max-temperature") +temp_plot.report_defs = [max_pad_temp, max_disc_temp] + +temp_file = monitor.report_files.create(name="max-temperature", +report_defs = [max_pad_temp, max_disc_temp, "flow-time"], +file_name = "max-temperature.out") + + +graphics = Graphics(solver) +temp_contour = graphics.contour.create(name="temperature", +field = VariableCatalog.TEMPERATURE, +surfaces_list = "wall*") + +temp_contour.color_map.visible = True +temp_contour.color_map.size = 100 +temp_contour.color_map.color = "field-velocity" +temp_contour.color_map.log_scale = False +temp_contour.color_map.format = "%0.1f" +temp_contour.color_map.user_skip = 9 +temp_contour.color_map.show_all = True +temp_contour.color_map.position = 1 +temp_contour.color_map.font_name = "Helvetica" +temp_contour.color_map.font_automatic = True +temp_contour.color_map.font_size = 0.032 +temp_contour.color_map.length = 0.54 +temp_contour.color_map.width = 6 +temp_contour.color_map.bground_transparent = True +temp_contour.color_map.bground_color = "#CCD3E2" +temp_contour.color_map.title_elements = "Variable and Object Name" + +# range configuration +temp_contour.range.option = "auto-range-off" +temp_contour.range.auto_range_off.minimum = 300.0 +temp_contour.range.auto_range_off.maximum = 400.0 +temp_contour.range.auto_range_off.clip_to_range = False + +# views / camera +graphics.restore_view(view_name="top") +graphics.views.camera.zoom(factor=2) +graphics.views.save_view(view_name="animation-view") + +solver.solution.calculation_activity.solution_animations.create( + name="animate-temperature", +animate_on = "temperature", +frequency_of = "flow-time", +flow_time_frequency = 0.05, +view = "animation-view",) ################################################################################################## # Run simulation @@ -284,17 +231,15 @@ # * Run simulation for 2 seconds flow time # * Set time step size # * Set number of time steps and maximum number of iterations per time step - -session.settings.solution.run_calculation.transient_controls.time_step_size = 0.01 -session.settings.solution.run_calculation.dual_time_iterate( - time_step_count=200, max_iter_per_step=5 -) +run_calc = RunCalculation(solver) +run_calc.transient_controls.time_step_size = 0.01 +run_calc.dual_time_iterate(time_step_count=200, max_iter_per_step=5) ################################################################################################## # Save simulation data # -------------------- # Write case and data files -session.settings.file.write(file_type="case-data", file_name="brake-final.cas.h5") +write_case_data(solver, file_name="brake-final.cas.h5") ############################################### # Post processing with PyVista (3D visualization) @@ -313,7 +258,7 @@ "wall-geom-1-innerpad", "wall-geom-1-outerpad", ] -contour1 = Contour(solver=session, field="temperature", surfaces=contour1_surfaces) +contour1 = Contour(solver=solver, field="temperature", surfaces=contour1_surfaces) ############################################### # Set contour properties @@ -350,15 +295,15 @@ X = [] Y = [] Z = [] -i = -1 -with open(os.path.join(os.getcwd(), "max-temperature.out"), "r") as datafile: - plotting = csv.reader(datafile, delimiter=" ") - for rows in plotting: - i = i + 1 - if i > 2: - X.append(float(rows[3])) - Y.append(float(rows[2])) - Z.append(float(rows[1])) + +with (Path.cwd() / "max-temperature.out").open() as datafile: + for rows in csv.reader( + itertools.islice(datafile, 3, -1), # skip header lines + delimiter=" ", + ): + X.append(float(rows[3])) + Y.append(float(rows[2])) + Z.append(float(rows[1])) ############################################### # Plot graph @@ -390,6 +335,6 @@ # Close the session # ================================================================================== -session.exit() +solver.exit() # sphinx_gallery_thumbnail_path = '_static/brake_surface_temperature-thumbnail.png' diff --git a/examples/00-fluent/catalytic_converter_workflow.py b/examples/00-fluent/catalytic_converter_workflow.py index f7c3b5a54db..6d4cc92a045 100644 --- a/examples/00-fluent/catalytic_converter_workflow.py +++ b/examples/00-fluent/catalytic_converter_workflow.py @@ -88,26 +88,29 @@ # sphinx_gallery_capture_repr = ('_repr_html_', '__repr__') # sphinx_gallery_thumbnail_path = '_static/catalytic_converter/catalytic_converter_cad_geo.png' -import os +from pathlib import Path import platform +from ansys.units import VariableCatalog + import ansys.fluent.core as pyfluent from ansys.fluent.core import ( Dimension, - FluentMode, - FluentVersion, Precision, UIMode, examples, ) +from ansys.fluent.core.generated.solver.settings_builtin import IsoSurface +from ansys.fluent.core.generated.solver.settings_builtin_261 import write_case_data from ansys.fluent.core.solver import ( # noqa: E402 - CellZoneCondition, + CellZoneConditions, + Energy, General, Graphics, Initialization, + IsoSurfaces, Materials, Mesh, - Models, Monitor, PressureOutlet, ReportDefinitions, @@ -115,12 +118,14 @@ RunCalculation, Scene, VelocityInlet, + WallBoundaries, ) +from ansys.units.common import K, Pa, m, s +# %% # Launch meshing session -meshing = pyfluent.launch_fluent( - product_version=FluentVersion.v252, - mode=FluentMode.MESHING, +# ---------------------------- +meshing = pyfluent.Meshing.from_install( ui_mode=UIMode.GUI, processor_count=4, precision=Precision.DOUBLE, @@ -152,11 +157,11 @@ geometry_filename = examples.download_file( filenames.get(platform.system(), filenames["Other"]), "/pyfluent/catalytic_converter/", - save_path=os.getcwd(), + save_path=Path.cwd(), ) workflow.InitializeWorkflow(WorkflowType="Watertight Geometry") -workflow.TaskObject["Import Geometry"].Arguments = dict(FileName=geometry_filename) +workflow.TaskObject["Import Geometry"].Arguments = {"FileName": geometry_filename} workflow.TaskObject["Import Geometry"].Execute() # %% @@ -166,23 +171,21 @@ # Add local sizing for sensor components -workflow.TaskObject["Add Local Sizing"].Arguments = dict( - { - "AddChild": "yes", - "BOIControlName": "sensor", - "BOIExecution": "Curvature", - "BOIFaceLabelList": [ - "sensing_element-65-solid", - "sensor_innertube-67-solid", - "sensor_protectiontube-66-solid1", - ], - "BOIMaxSize": 1.2, - "BOIMinSize": 0.1, - } -) +workflow.TaskObject["Add Local Sizing"].Arguments = { + "AddChild": "yes", + "BOIControlName": "sensor", + "BOIExecution": "Curvature", + "BOIFaceLabelList": [ + "sensing_element-65-solid", + "sensor_innertube-67-solid", + "sensor_protectiontube-66-solid1", + ], + "BOIMaxSize": 1.2, + "BOIMinSize": 0.1, +} workflow.TaskObject["Add Local Sizing"].AddChildToTask() workflow.TaskObject["Add Local Sizing"].InsertCompoundChildTask() -workflow.TaskObject["Add Local Sizing"].Arguments = dict({"AddChild": "yes"}) +workflow.TaskObject["Add Local Sizing"].Arguments = {"AddChild": "yes"} workflow.TaskObject["sensor"].Execute() # %% @@ -192,16 +195,14 @@ # Configure surface mesh settings -workflow.TaskObject["Generate the Surface Mesh"].Arguments = dict( - { - "CFDSurfaceMeshControls": {"MinSize": 1.5}, - "SurfaceMeshPreferences": { - "SMQualityImprove": "yes", - "SMQualityImproveLimit": 0.95, - "ShowSurfaceMeshPreferences": True, - }, - } -) +workflow.TaskObject["Generate the Surface Mesh"].Arguments = { + "CFDSurfaceMeshControls": {"MinSize": 1.5}, + "SurfaceMeshPreferences": { + "SMQualityImprove": "yes", + "SMQualityImproveLimit": 0.95, + "ShowSurfaceMeshPreferences": True, + }, +} workflow.TaskObject["Generate the Surface Mesh"].Execute() # %% @@ -212,27 +213,23 @@ # Describe geometry type workflow.TaskObject["Describe Geometry"].UpdateChildTasks(SetupTypeChanged=False) -workflow.TaskObject["Describe Geometry"].Arguments = dict( - {"SetupType": "The geometry consists of both fluid and solid regions and/or voids"} -) +workflow.TaskObject["Describe Geometry"].Arguments = { + "SetupType": "The geometry consists of both fluid and solid regions and/or voids" +} workflow.TaskObject["Describe Geometry"].UpdateChildTasks(SetupTypeChanged=True) # Enable capping and wall-to-internal conversion -workflow.TaskObject["Describe Geometry"].Arguments = dict( - { - "CappingRequired": "Yes", - "SetupType": "The geometry consists of both fluid and solid regions and/or voids", - } -) +workflow.TaskObject["Describe Geometry"].Arguments = { + "CappingRequired": "Yes", + "SetupType": "The geometry consists of both fluid and solid regions and/or voids", +} workflow.TaskObject["Describe Geometry"].UpdateChildTasks(SetupTypeChanged=False) -workflow.TaskObject["Describe Geometry"].Arguments = dict( - { - "CappingRequired": "Yes", - "SetupType": "The geometry consists of both fluid and solid regions and/or voids", - "WallToInternal": "Yes", - } -) +workflow.TaskObject["Describe Geometry"].Arguments = { + "CappingRequired": "Yes", + "SetupType": "The geometry consists of both fluid and solid regions and/or voids", + "WallToInternal": "Yes", +} workflow.TaskObject["Describe Geometry"].Execute() # %% @@ -242,24 +239,20 @@ # Create inlet boundary -workflow.TaskObject["Enclose Fluid Regions (Capping)"].Arguments = dict( - { - "LabelSelectionList": ["in1"], - "PatchName": "inlet", - } -) +workflow.TaskObject["Enclose Fluid Regions (Capping)"].Arguments = { + "LabelSelectionList": ["in1"], + "PatchName": "inlet", +} workflow.TaskObject["Enclose Fluid Regions (Capping)"].AddChildToTask() workflow.TaskObject["Enclose Fluid Regions (Capping)"].InsertCompoundChildTask() workflow.TaskObject["inlet"].Execute() # Create outlet boundary as pressure outlet -workflow.TaskObject["Enclose Fluid Regions (Capping)"].Arguments = dict( - { - "LabelSelectionList": ["out1"], - "PatchName": "outlet", - } -) +workflow.TaskObject["Enclose Fluid Regions (Capping)"].Arguments = { + "LabelSelectionList": ["out1"], + "PatchName": "outlet", +} workflow.TaskObject["Enclose Fluid Regions (Capping)"].AddChildToTask() workflow.TaskObject["Enclose Fluid Regions (Capping)"].InsertCompoundChildTask() workflow.TaskObject["outlet"].Execute() @@ -267,14 +260,12 @@ # Configure outlet as pressure-outlet workflow.TaskObject["outlet"].Revert() -workflow.TaskObject["outlet"].Arguments = dict( - { - "CompleteLabelSelectionList": ["out1"], - "LabelSelectionList": ["out1"], - "PatchName": "outlet", - "ZoneType": "pressure-outlet", - } -) +workflow.TaskObject["outlet"].Arguments = { + "CompleteLabelSelectionList": ["out1"], + "LabelSelectionList": ["out1"], + "PatchName": "outlet", + "ZoneType": "pressure-outlet", +} workflow.TaskObject["outlet"].Execute() # Update boundaries @@ -288,19 +279,17 @@ # Create multiple flow volumes -workflow.TaskObject["Create Regions"].Arguments = dict({"NumberOfFlowVolumes": 3}) +workflow.TaskObject["Create Regions"].Arguments = {"NumberOfFlowVolumes": 3} workflow.TaskObject["Create Regions"].Execute() # Convert solid substrate regions to fluid regions -workflow.TaskObject["Update Regions"].Arguments = dict( - { - "OldRegionNameList": ["honeycomb-solid1", "honeycomb_af0-solid1"], - "OldRegionTypeList": ["solid", "solid"], - "RegionNameList": ["fluid:substrate:1", "fluid:substrate:2"], - "RegionTypeList": ["fluid", "fluid"], - } -) +workflow.TaskObject["Update Regions"].Arguments = { + "OldRegionNameList": ["honeycomb-solid1", "honeycomb_af0-solid1"], + "OldRegionTypeList": ["solid", "solid"], + "RegionNameList": ["fluid:substrate:1", "fluid:substrate:2"], + "RegionTypeList": ["fluid", "fluid"], +} workflow.TaskObject["Update Regions"].Execute() # %% @@ -312,9 +301,9 @@ workflow.TaskObject["Add Boundary Layers"].AddChildToTask() workflow.TaskObject["Add Boundary Layers"].InsertCompoundChildTask() -workflow.TaskObject["smooth-transition_1"].Arguments = dict( - {"BLControlName": "smooth-transition_1"} -) +workflow.TaskObject["smooth-transition_1"].Arguments = { + "BLControlName": "smooth-transition_1" +} workflow.TaskObject["smooth-transition_1"].Execute() @@ -325,9 +314,9 @@ # Generate volume mesh -workflow.TaskObject["Generate the Volume Mesh"].Arguments = dict( - {"VolumeMeshPreferences": {"MergeBodyLabels": "yes"}} -) +workflow.TaskObject["Generate the Volume Mesh"].Arguments = { + "VolumeMeshPreferences": {"MergeBodyLabels": "yes"} +} workflow.TaskObject["Generate the Volume Mesh"].Execute() # %% @@ -349,7 +338,11 @@ # Switch to solver mode -solver_session = meshing.switch_to_solver() +solver = meshing.switch_to_solver() + + +# Create output directory for results +out = Path("out").mkdir(exist_ok=True) # %% Visualize Mesh # ~~~~~~~~~~~~~~~~~ @@ -357,7 +350,7 @@ # Visualize mesh in the graphics window and save a screenshot # Create Graphics object to save the graphics with following settings -graphics = Graphics(solver_session) +graphics = Graphics(solver) graphics.views.auto_scale() if graphics.picture.use_window_resolution.is_active(): graphics.picture.use_window_resolution = False @@ -370,12 +363,14 @@ # Define and display the mesh # First, get all wall boundary names and create a mesh object for visualization context -all_walls = solver_session.settings.setup.boundary_conditions.wall.get_object_names() -mesh = Mesh(solver_session, new_instance_name="mesh-1") -mesh.surfaces_list = all_walls +all_walls = WallBoundaries(solver).get_object_names() +mesh = Mesh( + solver, + new_instance_name="mesh-1", + surfaces_list=all_walls, +) mesh.options.edges = True mesh.display() -os.makedirs("out", exist_ok=True) graphics.picture.save_picture(file_name="out/catalytic_converter_mesh.png") mesh.options.edges = False # Turn off edges after saving the picture @@ -393,16 +388,14 @@ # Set length units to millimeters -general_settings = General(solver_session) +general_settings = General(solver) general_settings.units_settings.new_unit( offset=0.0, units_name="mm", scale_factor=1.0, quantity="length" ) # Enable energy equation -energy_model_settings = Models(solver_session) -energy_model_settings.energy = { - "enabled": True, - "inlet_diffusion": False, -} +energy = Energy(solver) +energy.enabled = True +energy.inlet_diffusion = False # %% # Materials @@ -411,23 +404,14 @@ # Copy nitrogen from database -solver_session.settings.setup.materials.database.copy_by_name( - type="fluid", name="nitrogen" -) - -# Assign material to main fluid zone - -materials = Materials(solver_session) +materials = Materials(solver) materials.database.copy_by_name(type="fluid", name="nitrogen") -material_assignments = CellZoneCondition(solver_session, name="fluid:1") -material_assignments.general = {"material": "nitrogen"} +# Assign material to main fluid zone -# Copy boundary conditions to other fluid zones +material_assignments = CellZoneConditions.get(solver, name="fluid:*") +material_assignments.general.material = "nitrogen" -solver_session.tui.define.boundary_conditions.copy_bc( - "fluid:1", "fluid:2", "fluid:3", "()" -) # %% # Cell Zone Conditions @@ -436,30 +420,32 @@ # Configure first substrate zone as porous media -porous_media_settings = CellZoneCondition(solver_session, name="fluid:substrate:1") -porous_media_settings.general = {"laminar": True, "material": "nitrogen"} -porous_media_settings.porous_zone = { - "solid_material": "aluminum", - "equib_thermal": True, - "relative_viscosity": {"value": 1, "option": "constant"}, - "porosity": 1, - "power_law_model": [0, 0], - "inertial_resistance": [1000.0, 1000.0, 1000.0], - "alt_inertial_form": False, - "viscous_resistance": [1000000.0, 1000000.0, 1000.0], - "rel_vel_resistance": True, - "direction_2_vector": [0, 1, 0], - "direction_1_vector": [1, 0, 0], - "dir_spec_cond": "Cartesian", - "porous": True, -} - +porous_media_settings = CellZoneConditions.get(solver, name="fluid:substrate:*") +porous_media_settings.general.laminar = True +porous_media_settings.general.material = "nitrogen" +porous_media_settings.porous_zone.solid_material = "aluminum" +porous_media_settings.porous_zone.equib_thermal = True +porous_media_settings.porous_zone.relative_viscosity.option = "constant" +porous_media_settings.porous_zone.relative_viscosity.value = 1 +porous_media_settings.porous_zone.porosity = 1 +porous_media_settings.porous_zone.power_law_model = [0, 0] +porous_media_settings.porous_zone.inertial_resistance = [ + 1000.0, + 1000.0, + 1000.0, +] / m +porous_media_settings.porous_zone.alt_inertial_form = False +porous_media_settings.porous_zone.viscous_resistance = [ + 1000000.0, + 1000000.0, + 1000.0, +] / m**2 +porous_media_settings.porous_zone.rel_vel_resistance = True +porous_media_settings.porous_zone.direction_2_vector = (0, 1, 0) +porous_media_settings.porous_zone.direction_1_vector = (1, 0, 0) +porous_media_settings.porous_zone.dir_spec_cond = "Cartesian" +porous_media_settings.porous_zone.porous = True -# Copy porous media settings to second substrate zone - -solver_session.tui.define.boundary_conditions.copy_bc( - "fluid:substrate:1", "fluid:substrate:2", "()" -) # %% # Boundary Conditions @@ -468,25 +454,19 @@ # Configure velocity inlet -velocity_inlet = VelocityInlet(solver_session, name="inlet") -velocity_inlet.momentum = {"velocity_magnitude": {"value": 125.0}} - -velocity_inlet.turbulence = { - "hydraulic_diameter": 0.5, # in meters - "turbulence_specification": "Intensity and Hydraulic Diameter", -} -velocity_inlet.thermal = {"temperature": {"value": 800.0}} # in Kelvin +velocity_inlet = VelocityInlet.get(solver, name="inlet") +velocity_inlet.momentum.velocity_magnitude = 125.0 * m / s +velocity_inlet.turbulence.hydraulic_diameter = 0.5 * m +velocity_inlet.turbulence.turbulence_specification = "Intensity and Hydraulic Diameter" +velocity_inlet.thermal.temperature = 800.0 * K # Configure pressure outlet -pressure_outlet = PressureOutlet(solver_session, name="outlet") -pressure_outlet.momentum = {"gauge_pressure": {"value": 0.0}} -pressure_outlet.turbulence = { - "backflow_hydraulic_diameter": 0.5, # in meters - "turbulence_specification": "Intensity and Hydraulic Diameter", -} -pressure_outlet.thermal = {"backflow_total_temperature": {"value": 800.0}} # in Kelvin - +pressure_outlet = PressureOutlet.get(solver, name="outlet") +pressure_outlet.momentum.gauge_pressure = 0.0 * Pa +pressure_outlet.turbulence.backflow_hydraulic_diameter = 0.5 * m +pressure_outlet.turbulence.turbulence_specification = "Intensity and Hydraulic Diameter" +pressure_outlet.thermal.backflow_total_temperature = 800.0 * K # %% # Solution Monitoring @@ -495,25 +475,27 @@ # Create surface report definition -report_definitions = ReportDefinitions(solver_session) -surface_report = report_definitions.surface.create(name="surf-mon-1") -surface_report.report_type = "surface-massflowrate" -surface_report.surface_names = ["outlet"] +report_definitions = ReportDefinitions(solver) +surface_report = report_definitions.surface.create( + name="surf-mon-1", + report_type="surface-massflowrate", + surface_names=["outlet"], +) # Create report file monitor -monitor = Monitor(solver_session) -surface_monitor = monitor.report_files.create(name="surf-mon-1") -surface_monitor.print = True -surface_monitor.report_defs = ["surf-mon-1"] -os.makedirs("out", exist_ok=True) -surface_monitor.file_name = "out/surf-mon-1.out" - +monitor = Monitor(solver) +monitor.report_files.create( + name=surface_report, + print=True, + report_defs=[surface_report.name], + file_name="out/surf-mon-1.out", +) # Create report plot monitor -surface_plot_monitor = monitor.report_plots.create(name="surf-mon-1") -surface_plot_monitor.print = True -surface_plot_monitor.report_defs = ["surf-mon-1"] +monitor.report_plots.create( + name=surface_report, print=True, report_defs=[surface_report] +) # %% @@ -523,7 +505,7 @@ # Compute initial conditions from inlet -solution_initialization = Initialization(solver_session) +solution_initialization = Initialization(solver) solution_initialization.compute_defaults( from_zone_type="velocity-inlet", from_zone_name="inlet", phase="mixture" @@ -541,7 +523,7 @@ # Set iteration count and run calculation -run_calculation = RunCalculation(solver_session) +run_calculation = RunCalculation(solver) run_calculation.iter_count = ( 150 # Iteration count, keep it at 150 for demo purposes only ) @@ -557,9 +539,7 @@ # ~~~~~~~~~~~~~~~~~~ # Calculate mass flow rate at outlet. -# Ensure the 'out/' directory exists before writing files to it -os.makedirs("out", exist_ok=True) -results = Results(solver_session) +results = Results(solver) results.report.fluxes.mass_flow( zones=["outlet"], write_to_file=True, file_name="out/mass_flow_rate.flp" ) @@ -572,18 +552,18 @@ # Create cross-sectional surfaces surfaces_data = [ - ("y=-425", "y-coordinate", [-0.425]), - ("z=185", "z-coordinate", [0.185]), - ("z=230", "z-coordinate", [0.23]), - ("z=280", "z-coordinate", [0.28]), - ("z=330", "z-coordinate", [0.33]), - ("z=375", "z-coordinate", [0.375]), + ("y=-425", "y-coordinate", [-0.425] * m), + ("z=185", "z-coordinate", [0.185] * m), + ("z=230", "z-coordinate", [0.23] * m), + ("z=280", "z-coordinate", [0.28] * m), + ("z=330", "z-coordinate", [0.33] * m), + ("z=375", "z-coordinate", [0.375] * m), ] for surf_name, field_name, iso_values in surfaces_data: - results.surfaces.iso_surface.create(name=surf_name) - results.surfaces.iso_surface[surf_name].field = field_name - results.surfaces.iso_surface[surf_name].iso_values = iso_values + surface = IsoSurface.create( + solver, name=surf_name, field=field_name, iso_values=iso_values + ) # %% # Velocity Analysis @@ -617,39 +597,36 @@ # Velocity vectors show both flow direction and magnitude using arrow symbols # The scale factor controls arrow size for optimal visualization -results.graphics.vector.create(name="vector-vel") -results.graphics.vector["vector-vel"] = { - "scale": { - "auto_scale": True, # Automatically scale arrows for best visibility - "scale_f": 0.006, # Fine-tune scale factor (smaller = shorter arrows) - }, - "surfaces_list": ["y=-425"], # Display vectors on the y=-425 cross-section -} +vec = results.graphics.vector.create( + name="vector-vel", surfaces_list=["y=-425"] +) # Display vectors on the y=-425 cross-section +vec.scale.auto_scale = True # Automatically scale arrows for best visibility +vec.scale.scale_f = 0.006 # Fine-tune scale factor (smaller = shorter arrows) # Create static pressure contour plot # Pressure contours use color mapping to show pressure distribution # This helps identify high/low pressure regions and pressure gradients -results.graphics.contour.create(name="contour-ps") -results.graphics.contour["contour-ps"] = { - "field": "pressure", # Specify pressure as the contour variable - "surfaces_list": ["y=-425"], # Display on the same cross-section as vectors -} +pressure_contour = results.graphics.contour.create( + name="contour-ps", + field=VariableCatalog.PRESSURE, # Specify pressure as the contour variable + surfaces_list=["y=-425"], # Display on the same cross-section as vectors +) # Create velocity magnitude contour plot # Velocity magnitude shows speed distribution without directional information # Using multiple z-surfaces provides a comprehensive view through the domain -results.graphics.contour.create(name="contour-velmag") -results.graphics.contour["contour-velmag"] = { - "field": "velocity-magnitude", # Specify velocity magnitude as the variable - "surfaces_list": z_surfaces, # Display on all z-coordinate surfaces -} +cont_velmag = results.graphics.contour.create( + name="contour-velmag", + field=VariableCatalog.VELOCITY_MAGNITUDE, # Specify velocity magnitude as the variable + surfaces_list=z_surfaces, # Display on all z-coordinate surfaces +) # Scene 1: Display velocity vectors with mesh context # Scenes combine multiple graphics objects for comprehensive visualization -velocity_vectors_scene = Scene(solver_session, new_instance_name="scene-1") +velocity_vectors_scene = Scene(solver, new_instance_name="scene-1") velocity_vectors_scene.graphics_objects.add(name="vector-vel") # adding mesh for context which is created earlier steps just after switching to solver @@ -657,15 +634,13 @@ velocity_vectors_scene.graphics_objects.add(name="mesh-1") # Configure scene appearance and display settings -solver_session.settings.results.scene["scene-1"] = { - "graphics_objects": { - "vector-vel": {"name": "vectors"}, # Label for the vector plot - "mesh-1": {"transparency": 75}, # Semi-transparent mesh (75% transparent) - } +scene_1= Scene.create(solver, name="scene-1") +scene_1.graphics_objects = { + "vector-vel": {"name": "vectors"}, # Label for the vector plot + "mesh-1": {"transparency": 75}, # Semi-transparent mesh (75% transparent) } velocity_vectors_scene.display() graphics.views.auto_scale() -os.makedirs("out", exist_ok=True) graphics.picture.save_picture(file_name="out/velocity_vectors.png") # %% @@ -678,22 +653,16 @@ # Scene 2: Display static pressure contours with mesh context # This scene focuses on pressure distribution across the catalytic converter -static_pressure_scene = Scene(solver_session, new_instance_name="scene-2") -static_pressure_scene.graphics_objects.add(name="contour-ps") -static_pressure_scene.graphics_objects.add(name="mesh-1") +static_pressure_scene = Scene.create(solver, name="scene-2") +pressure_contour_scene = static_pressure_scene.graphics_objects.add(name="contour-ps") +mesh_1_scene = static_pressure_scene.graphics_objects.add(name="mesh-1") # Configure pressure contour scene settings +pressure_contour_scene.name =pressure_contour # Label for the pressure contour +mesh_1_scene.transparency = 75 # Consistent mesh transparency -solver_session.settings.results.scene["scene-2"] = { - "graphics_objects": { - "contour-ps": {"name": "contour-ps"}, # Label for the pressure contour - "mesh-1": {"transparency": 75}, # Consistent mesh transparency - } -} static_pressure_scene.display() graphics.views.auto_scale() -# Ensure "out/" directory exists before saving files -os.makedirs("out", exist_ok=True) graphics.picture.save_picture(file_name="out/static_pressure.png") # %% @@ -707,23 +676,16 @@ # Scene 3: Display velocity magnitude contours with mesh context # This scene shows speed distribution across multiple axial locations -velocity_magnitude_scene = Scene(solver_session, new_instance_name="scene-3") -velocity_magnitude_scene.graphics_objects.add(name="contour-velmag") -velocity_magnitude_scene.graphics_objects.add(name="mesh-1") +velocity_magnitude_scene = Scene.create(solver, name="scene-3") +velocity_mag_contour_scene = velocity_magnitude_scene.graphics_objects.add(name="contour-velmag") +mesh_1_scene = velocity_magnitude_scene.graphics_objects.add(name="mesh-1") # Configure velocity magnitude contour scene settings -solver_session.settings.results.scene["scene-3"] = { - "graphics_objects": { - "contour-velmag": { - "name": "contour-velmag" - }, # Label for velocity magnitude contour - "mesh-1": {"transparency": 75}, # Consistent mesh transparency - } -} +velocity_mag_contour_scene.name = velocity_mag_contour # Label for velocity magnitude contour +mesh_1_scene.transparency = 75 # Consistent mesh transparency + velocity_magnitude_scene.display() graphics.views.auto_scale() -# Ensure the 'out/' directory exists before saving files -os.makedirs("out", exist_ok=True) graphics.picture.save_picture(file_name="out/velocity_magnitude.png") # %% @@ -741,8 +703,9 @@ # Write final case and data -solver_session.settings.file.write( - file_type="case-data", file_name="out/catalytic_converter_final.cas.h5" +write_case_data( + solver, + file_name="out/catalytic_converter_final.cas.h5" ) # %% @@ -752,7 +715,7 @@ # Close solver session -solver_session.exit() +solver.exit() # %% # References diff --git a/examples/00-fluent/conjugate_heat_transfer.py b/examples/00-fluent/conjugate_heat_transfer.py index 65e87aaa8af..03bf067a0f3 100644 --- a/examples/00-fluent/conjugate_heat_transfer.py +++ b/examples/00-fluent/conjugate_heat_transfer.py @@ -57,15 +57,37 @@ # ================================= import csv -import os from pathlib import Path import platform +from ansys.units import VariableCatalog import matplotlib.pyplot as plt import pyvista as pv import ansys.fluent.core as pyfluent from ansys.fluent.core import examples +from ansys.fluent.core.solver import ( + CellZoneCondition, + FluidMaterial, + Initialization, + Materials, + Monitor, + PressureOutlet, + ReportDefinitions, + RunCalculation, + SolidMaterial, + VelocityInlet, + Viscous, + WallBoundary, + BoundaryCondition, + Energy, + Fluxes, + General, + IsoSurface, + write_case_data, + write_case, + MeshInterfaces, +) from ansys.fluent.visualization import ( Contour, GraphicsWindow, @@ -73,6 +95,7 @@ Vector, XYPlot, ) +from ansys.units.common import J, K, Pa, W, kg, m, s filenames = { "Windows": "cht_fin_htc_new.scdoc", @@ -82,7 +105,7 @@ geom_filename = examples.download_file( filenames.get(platform.system(), filenames["Other"]), "pyfluent/examples/CHT", - save_path=os.getcwd(), + save_path=Path.cwd(), ) ####################### @@ -93,42 +116,35 @@ # Launch Fluent session with meshing mode and print Fluent version # ================================================================ -meshing_session = pyfluent.launch_fluent( - mode="meshing", - precision="double", +meshing = pyfluent.Meshing.from_install( + precision=pyfluent.Precision.DOUBLE, processor_count=4, ) -print(meshing_session.get_fluent_version()) +print(meshing.get_fluent_version()) ############################################################################# # Start Watertight Geometry Meshing Workflow # ========================================== -meshing_session.workflow.InitializeWorkflow(WorkflowType=r"Watertight Geometry") +meshing.workflow.InitializeWorkflow(WorkflowType=r"Watertight Geometry") -meshing_session.workflow.TaskObject["Import Geometry"].Arguments = dict( - FileName=geom_filename -) +meshing.workflow.TaskObject["Import Geometry"].Arguments = {"FileName": geom_filename} -meshing_session.workflow.TaskObject["Import Geometry"].Execute() +meshing.workflow.TaskObject["Import Geometry"].Execute() -meshing_session.workflow.TaskObject["Add Local Sizing"].Execute() +meshing.workflow.TaskObject["Add Local Sizing"].Execute() -meshing_session.workflow.TaskObject["Generate the Surface Mesh"].Arguments = dict( - { - "CFDSurfaceMeshControls": { - "MinSize": 0.3, - "MaxSize": 1, - "ScopeProximityTo": "faces", - }, - } -) -meshing_session.workflow.TaskObject["Generate the Surface Mesh"].Execute() +meshing.workflow.TaskObject["Generate the Surface Mesh"].Arguments = { + "CFDSurfaceMeshControls": { + "MinSize": 0.3, + "MaxSize": 1, + "ScopeProximityTo": "faces", + }, +} +meshing.workflow.TaskObject["Generate the Surface Mesh"].Execute() -meshing_session.workflow.TaskObject["Describe Geometry"].UpdateChildTasks( - SetupTypeChanged=True -) -meshing_session.workflow.TaskObject["Describe Geometry"].Arguments.setState( +meshing.workflow.TaskObject["Describe Geometry"].UpdateChildTasks(SetupTypeChanged=True) +meshing.workflow.TaskObject["Describe Geometry"].Arguments.setState( { r"CappingRequired": r"No", r"InvokeShareTopology": r"No", @@ -137,13 +153,13 @@ } ) -meshing_session.workflow.TaskObject["Describe Geometry"].Execute() +meshing.workflow.TaskObject["Describe Geometry"].Execute() ############################################################################# # Update Interface Boundaries; Create Region # ========================================== -meshing_session.workflow.TaskObject["Update Boundaries"].Arguments.setState( +meshing.workflow.TaskObject["Update Boundaries"].Arguments.setState( { r"BoundaryLabelList": [ r"interface-out-solid-a", @@ -350,44 +366,38 @@ } ) -meshing_session.workflow.TaskObject["Update Boundaries"].Execute() +meshing.workflow.TaskObject["Update Boundaries"].Execute() -meshing_session.workflow.TaskObject["Create Regions"].Execute() +meshing.workflow.TaskObject["Create Regions"].Execute() ############################################################################# # Custom Journal for Creating Periodicity due to Non-Conformal Objects # ==================================================================== -meshing_session.workflow.TaskObject["Describe Geometry"].InsertNextTask( +meshing.workflow.TaskObject["Describe Geometry"].InsertNextTask( CommandName=r"RunCustomJournal" ) -meshing_session.workflow.TaskObject["Run Custom Journal"].Rename( - NewName=r"set-periodicity" -) -meshing_session.workflow.TaskObject["set-periodicity"].Arguments = dict( - { - r"JournalString": r"""/bo rps translational semi-auto periodic-1-high periodic-2-high periodic-3-high periodic-4-high , 0 0 -2.3 +meshing.workflow.TaskObject["Run Custom Journal"].Rename(NewName=r"set-periodicity") +meshing.workflow.TaskObject["set-periodicity"].Arguments = { + r"JournalString": r"""/bo rps translational semi-auto periodic-1-high periodic-2-high periodic-3-high periodic-4-high , 0 0 -2.3 /bo rps translational semi-auto periodic-5* , 0 0 -2.3 /bo rps translational semi-auto periodic-6-high , 0 0 -2.3 /bo rps translational semi-auto periodic-7-high , 0 0 -2.3 """, - } -) +} -meshing_session.workflow.TaskObject["set-periodicity"].Execute() +meshing.workflow.TaskObject["set-periodicity"].Execute() ############################################################################# # Update Boundary Layer Task # ========================== -meshing_session.workflow.TaskObject["Update Regions"].Execute() -meshing_session.workflow.TaskObject["Add Boundary Layers"].AddChildToTask() -meshing_session.workflow.TaskObject["Add Boundary Layers"].InsertCompoundChildTask() -meshing_session.workflow.TaskObject["smooth-transition_1"].Rename( - NewName=r"aspect-ratio_1" -) +meshing.workflow.TaskObject["Update Regions"].Execute() +meshing.workflow.TaskObject["Add Boundary Layers"].AddChildToTask() +meshing.workflow.TaskObject["Add Boundary Layers"].InsertCompoundChildTask() +meshing.workflow.TaskObject["smooth-transition_1"].Rename(NewName=r"aspect-ratio_1") -meshing_session.workflow.TaskObject["aspect-ratio_1"].Arguments.setState( +meshing.workflow.TaskObject["aspect-ratio_1"].Arguments.setState( { "BLControlName": r"aspect-ratio_1", "BLRegionList": [ @@ -432,23 +442,23 @@ } ) -meshing_session.workflow.TaskObject["aspect-ratio_1"].Execute() +meshing.workflow.TaskObject["aspect-ratio_1"].Execute() ############################################################################# # Generate Mesh # ============= -meshing_session.workflow.TaskObject["Generate the Volume Mesh"].Execute() +meshing.workflow.TaskObject["Generate the Volume Mesh"].Execute() ############################################################################# # Improve Volume Mesh # =================== -meshing_session.workflow.TaskObject["Generate the Volume Mesh"].InsertNextTask( +meshing.workflow.TaskObject["Generate the Volume Mesh"].InsertNextTask( CommandName=r"ImproveVolumeMesh" ) -meshing_session.workflow.TaskObject["Improve Volume Mesh"].Arguments.setState( +meshing.workflow.TaskObject["Improve Volume Mesh"].Arguments.setState( { r"CellQualityLimit": 0.05, r"VMImprovePreferences": { @@ -460,7 +470,7 @@ } ) -meshing_session.workflow.TaskObject["Improve Volume Mesh"].Execute() +meshing.workflow.TaskObject["Improve Volume Mesh"].Execute() ############################################################################# # Save Mesh File @@ -473,25 +483,25 @@ # Switch to Solution Mode # ======================= -solver_session = meshing_session.switch_to_solver() +solver = meshing.switch_to_solver() ############################################################################# # Auto-create Mesh Interfaces # =========================== -solver_session.tui.define.mesh_interfaces.create("int", "yes", "no") +MeshInterfaces(solver).create(si_name="int", all_bnd=True) ############################################################################# # Mesh Check; Review Fluent transcript for errors # =============================================== -solver_session.settings.mesh.check() +solver.settings.mesh.check() ############################################################################# # Create boundary lists for display and post-processing # ===================================================== -mesh1 = Mesh(solver=solver_session, surfaces=[]) +mesh1 = Mesh(solver=solver, surfaces=[]) wall_list = [ boundary_name @@ -523,243 +533,140 @@ # * Enable Energy Equation # * Enable Laminar Viscous Model -solver_session.settings.setup.general.units.set_units( +General(solver).units.set_units( quantity="temperature", units_name="C", scale_factor=1.0, offset=273.15 ) -solver_session.settings.setup.models.energy.enabled = True -solver_session.settings.setup.models.viscous.model.set_state("laminar") +Energy(solver).enabled = True +viscous = Viscous(solver) +viscous.model = viscous.model.LAMINAR ############################################################################# # Change a few material properties of default Air # =============================================== -air_dict = solver_session.settings.setup.materials.fluid["air"].get_state() -air_dict["density"]["value"] = 1.2 -air_dict["viscosity"]["value"] = 1.5e-5 -air_dict["thermal_conductivity"]["value"] = 0.026 -air_dict["specific_heat"]["value"] = 1006.0 -solver_session.settings.setup.materials.fluid["air"].set_state(air_dict) +# Air +air = FluidMaterial.get(solver, name="air") +air.density = 1.2 * kg / m**3 +air.viscosity = 1.5e-5 * Pa * s +air.thermal_conductivity = 0.026 * W / (m * K) +air.specific_heat = 1006.0 * J / (kg * K) + +# Aluminum +al = SolidMaterial.create(solver, name="aluminum") +al.density = 2719.0 * kg / m**3 +al.thermal_conductivity = 200.0 * W / (m * K) +al.specific_heat = 871.0 * J / (kg * K) + +# Copy Copper and set properties +materials = Materials(solver) +materials.database.copy_by_name(type="solid", name="copper") +cu = SolidMaterial.create(solver, name="copper") +cu.density = 8978.0 * kg / m**3 +cu.thermal_conductivity = 340.0 * W / (m * K) +cu.specific_heat = 381.0 * J / (kg * K) -############################################################################# -# Change a few material properties of default Aluminum -# ==================================================== +# Set Tube Cell Zone Material as Copper +cell_zones = CellZoneCondition(solver, name="solid-tube-*") +cell_zones.general.material = "copper" -al_dict = solver_session.settings.setup.materials.solid["aluminum"].get_state() -al_dict["density"]["value"] = 2719.0 -al_dict["thermal_conductivity"]["value"] = 200.0 -al_dict["specific_heat"]["value"] = 871.0 -solver_session.settings.setup.materials.solid["aluminum"].set_state(al_dict) +# Boundary conditions +inlet = VelocityInlet.get(solver, name="inlet") +inlet.momentum.velocity = 4.0 * m / s +inlet.thermal.temperature = 293.15 * K -############################################################################# -# Copy Copper and change a few material properties of default Copper -# ================================================================== +outlet = PressureOutlet.get(solver, name="outlet") +outlet.thermal.backflow_total_temperature = 293.15 * K -solver_session.settings.setup.materials.database.copy_by_name( - type="solid", name="copper" -) -cu_dict = solver_session.settings.setup.materials.solid["copper"].get_state() -cu_dict["density"]["value"] = 8978.0 -cu_dict["thermal_conductivity"]["value"] = 340.0 -cu_dict["specific_heat"]["value"] = 381.0 -solver_session.settings.setup.materials.solid["copper"].set_state(cu_dict) +# Wall thermal BC +walls_inner = WallBoundary.get(solver, name="wall-inner-tube-*") +walls_inner.thermal.thermal_condition = walls_inner.thermal.thermal_condition.CONVECTION +walls_inner.thermal.heat_transfer_coeff = 1050.0 * W / (m**2 * K) +walls_inner.thermal.free_stream_temp = 353.15 * K -############################################################################# -# Set Tube Cell Zone Material as Copper -# ===================================== - -tube_dict = solver_session.settings.setup.cell_zone_conditions.solid[ - "solid-tube-1" -].get_state() -tube_dict["material"] = "copper" -solver_session.settings.setup.cell_zone_conditions.solid["solid-tube-1"].set_state( - tube_dict +# Enable HOTR +solver.settings.solution.methods.high_order_term_relaxation.enable = True + +# Define Report Definitions using typed API +rdefs = ReportDefinitions(solver) +out_ent = rdefs.surface.create( + name="outlet-enthalpy-flow", + report_type="surface-flowrate", + field=VariableCatalog.ENTHALPY, + surface_names=["outlet"], ) -tube_dict = solver_session.settings.setup.cell_zone_conditions.solid[ - "solid-tube-2" -].get_state() -tube_dict["material"] = "copper" -solver_session.settings.setup.cell_zone_conditions.solid["solid-tube-2"].set_state( - tube_dict +avg_pressure = rdefs.surface.create( + name="avg-pressure-inlet", + report_type="surface-areaavg", + field=VariableCatalog.PRESSURE, + surface_names=["inlet"], ) -############################################################################# -# Set Boundary Condition for Inlet and Outlet -# =========================================== - -solver_session.settings.setup.boundary_conditions.velocity_inlet[ - "inlet" -].momentum.velocity = 4.0 -solver_session.settings.setup.boundary_conditions.velocity_inlet[ - "inlet" -].thermal.temperature = 293.15 # Need to specify in Kelvin - -solver_session.settings.setup.boundary_conditions.pressure_outlet[ - "outlet" -].thermal.backflow_total_temperature = 293.15 - -############################################################################# -# Set Thermal Boundary Condition for Wall Inner Tube -# ================================================== - -solver_session.settings.setup.boundary_conditions.wall[ - "wall-inner-tube-1" -].thermal.thermal_condition = "Convection" -solver_session.settings.setup.boundary_conditions.wall[ - "wall-inner-tube-1" -].thermal.heat_transfer_coeff = 1050.0 -solver_session.settings.setup.boundary_conditions.wall[ - "wall-inner-tube-1" -].thermal.free_stream_temp = 353.15 - -solver_session.settings.setup.boundary_conditions.copy( - from_="wall-inner-tube-1", to="wall-inner-tube-2" +vol_max = rdefs.volume.create( + name="max-vel-louvers4", + report_type="volume-max", + field=VariableCatalog.VELOCITY_MAGNITUDE, + cell_zones=["fluid-sweep-fin4"], ) -############################################################################# -# Enable HOTR -# =========== - -solver_session.settings.solution.methods.high_order_term_relaxation.enable = True -############################################################################# -# Define Report Definitions -# ========================= - -solver_session.settings.solution.report_definitions.surface["outlet-enthalpy-flow"] = {} -solver_session.settings.solution.report_definitions.surface[ - "outlet-enthalpy-flow" -].report_type = "surface-flowrate" -solver_session.settings.solution.report_definitions.surface[ - "outlet-enthalpy-flow" -].field = "enthalpy" -solver_session.settings.solution.report_definitions.surface[ - "outlet-enthalpy-flow" -].surface_names = ["outlet"] - -solver_session.settings.solution.report_definitions.surface["avg-pressure-inlet"] = {} -solver_session.settings.solution.report_definitions.surface[ - "avg-pressure-inlet" -].report_type = "surface-areaavg" -solver_session.settings.solution.report_definitions.surface[ - "avg-pressure-inlet" -].field = "pressure" -solver_session.settings.solution.report_definitions.surface[ - "avg-pressure-inlet" -].surface_names = ["inlet"] - -solver_session.settings.solution.report_definitions.volume["max-vel-louvers4"] = {} -solver_session.settings.solution.report_definitions.volume[ - "max-vel-louvers4" -].report_type = "volume-max" -solver_session.settings.solution.report_definitions.volume["max-vel-louvers4"].field = ( - "velocity-magnitude" -) -solver_session.settings.solution.report_definitions.volume[ - "max-vel-louvers4" -].cell_zones = ["fluid-tet-4"] - -solver_session.settings.solution.report_definitions.surface["wall-shear-int"] = {} -solver_session.settings.solution.report_definitions.surface[ - "wall-shear-int" -].report_type = "surface-integral" -solver_session.settings.solution.report_definitions.surface["wall-shear-int"].field = ( - "wall-shear" +wall_shear = rdefs.surface.create( + name="wall-shear-int", + report_type="surface-integral", + field=VariableCatalog.WALL_SHEAR, + surface_names=[ + "wall-fluid-sweep-fin-solid-sweep-fin-shadow", + "wall-fluid-tet-1-solid-tet-1", + "wall-fluid-tet-2-solid-tet-2", + "wall-fluid-tet-3-solid-tet-3", + "wall-fluid-tet-4-solid-tet-4", + ], ) -solver_session.settings.solution.report_definitions.surface[ - "wall-shear-int" -].surface_names = [ - "wall-fluid-sweep-fin-solid-sweep-fin-shadow", - "wall-fluid-tet-1-solid-tet-1", - "wall-fluid-tet-2-solid-tet-2", - "wall-fluid-tet-3-solid-tet-3", - "wall-fluid-tet-4-solid-tet-4", -] -solver_session.settings.solution.monitor.report_plots.create( - name="outlet-enthalpy-flow-plot" +monitor = Monitor(solver) +monitor.report_plots.create(report_defs=[out_ent]) +monitor.report_files.create(report_defs=[out_ent], file_name="outlet-enthalpy-flow.out") +monitor.report_plots.create(report_defs=[avg_pressure]) +monitor.report_files.create( + report_defs=[avg_pressure], file_name="avg-pressure-inlet.out" ) -solver_session.settings.solution.monitor.report_plots[ - "outlet-enthalpy-flow-plot" -].report_defs = "outlet-enthalpy-flow" - -solver_session.settings.solution.monitor.report_files["outlet-enthalpy-flow-file"] = {} -solver_session.settings.solution.monitor.report_files["outlet-enthalpy-flow-file"] = { - "report_defs": ["outlet-enthalpy-flow"], - "file_name": r"outlet-enthalpy-flow.out", -} - -solver_session.settings.solution.monitor.report_plots["avg-pressure-inlet-plot"] = {} -solver_session.settings.solution.monitor.report_plots["avg-pressure-inlet-plot"] = { - "report_defs": ["avg-pressure-inlet"] -} - -solver_session.settings.solution.monitor.report_files["avg-pressure-inlet-file"] = {} -solver_session.settings.solution.monitor.report_files["avg-pressure-inlet-file"] = { - "report_defs": ["avg-pressure-inlet"], - "file_name": r"avg-pressure-inlet.out", -} - -solver_session.settings.solution.monitor.report_plots["max-vel-louvers4-plot"] = {} -solver_session.settings.solution.monitor.report_plots["max-vel-louvers4-plot"] = { - "report_defs": ["max-vel-louvers4"] -} - -solver_session.settings.solution.monitor.report_files["max-vel-louvers4-file"] = {} -solver_session.settings.solution.monitor.report_files["max-vel-louvers4-file"] = { - "report_defs": ["max-vel-louvers4"], - "file_name": r"max-vel-louvers4.out", -} - -solver_session.settings.solution.monitor.report_plots["wall-shear-int-plot"] = {} -solver_session.settings.solution.monitor.report_plots["wall-shear-int-plot"] = { - "report_defs": ["wall-shear-int"] -} - -solver_session.settings.solution.monitor.report_files["wall-shear-int-file"] = {} -solver_session.settings.solution.monitor.report_files["wall-shear-int-file"] = { - "report_defs": ["wall-shear-int"], - "file_name": r"wall-shear-int.out", -} +monitor.report_plots.create(report_defs=[vol_max]) +monitor.report_files.create(report_defs=[vol_max], file_name="max-vel-louvers4.out") +monitor.report_plots.create(report_defs=[wall_shear]) +monitor.report_files.create(report_defs=[wall_shear], file_name="wall-shear-int.out") ############################################################################# # Hybrid Initialization; Slit Interior between Solid Zones; Save Case # =================================================================== -solver_session.settings.solution.initialization.initialization_type = "hybrid" -solver_session.settings.solution.initialization.hybrid_initialize() +initialization = Initialization(solver) +initialization.initialization_type = "hybrid" +initialization.hybrid_initialize() -solver_session.settings.setup.boundary_conditions.slit_interior_between_diff_solids() -solver_session.settings.file.write(file_type="case", file_name="hx-fin-2mm.cas.h5") +BoundaryCondition(solver).slit_interior_between_diff_solids() +write_case(solver, file_name="hx-fin-2mm.cas.h5") ############################################################################# # Set Aggressive Length Scale Method; Run Calculation & Save Data # =============================================================== -solver_session.settings.solution.run_calculation.pseudo_time_settings.time_step_method.time_step_method = ( - "automatic" -) -solver_session.settings.solution.run_calculation.pseudo_time_settings.time_step_method.length_scale_methods = ( - "aggressive" -) +run_calc = RunCalculation(solver) +run_calc.pseudo_time_settings.time_step_method.time_step_method = "automatic" +run_calc.pseudo_time_settings.time_step_method.length_scale_methods = "aggressive" -solver_session.settings.solution.run_calculation.iterate(iter_count=250) +run_calc.iterate(iter_count=250) -solver_session.settings.file.write(file_type="case-data", file_name="hx-fin-2mm.dat.h5") +write_case_data(solver, file_name="hx-fin-2mm.dat.h5") ############################################################################# # Post-Processing Mass Balance Report # =================================== -inlet_mfr = solver_session.scheme.exec( - ('(ti-menu-load-string "/report/fluxes/mass-flow no inlet () no")',) -).split(" ")[-1] -outlet_mfr = solver_session.scheme.exec( - ('(ti-menu-load-string "/report/fluxes/mass-flow no outlet () no")',) -).split(" ")[-1] -net_mfr = solver_session.scheme.exec( - ('(ti-menu-load-string "/report/fluxes/mass-flow no inlet outlet () no")',) -).split(" ")[-1] +fluxes = Fluxes(solver) +inlet_mfr = fluxes.get_mass_flow(zones=["inlet"]) +outlet_mfr = fluxes.get_mass_flow(zones=["outlet"]) +net_mfr = inlet_mfr - outlet_mfr + print("Mass Balance Report\n") print("Inlet (kg/s): ", inlet_mfr) print("Outlet (kg/s): ", outlet_mfr) @@ -769,9 +676,8 @@ # Heat Balance Report # =================== -htr = solver_session.scheme.exec( - ('(ti-menu-load-string "/report/fluxes/heat-transfer yes no")',) -).split(" ")[-1] +htr = fluxes.get_heat_transfer() + print("Heat Balance Report\n") print("Net Imbalance (Watt): ", htr) @@ -782,22 +688,14 @@ fig, axs = plt.subplots(2, 2, figsize=(10, 8)) fig.suptitle("Monitor Plots") -outFilesList = [] -fileList = os.listdir(os.getcwd()) -for tempFile in fileList: - fName, ext = os.path.splitext(tempFile) - if ext == ".out": - outFilesList.append(tempFile) -outFilesList.sort() - +out_files = sorted(Path.cwd().glob("*.out")) index = 0 -for ax in axs.flat: +for ax, file in zip(axs.flat, out_files): X = [] Y = [] i = -1 - with open(outFilesList[index], "r") as datafile: - plotting = csv.reader(datafile, delimiter=" ") - for rows in plotting: + with file.open() as fp: + for rows in csv.reader(fp, delimiter=" "): i += 1 if i == 1: var = rows[1] @@ -829,7 +727,7 @@ # Contour Plot # ============ -contour1 = Contour(solver=solver_session, field="temperature", surfaces=wall_list) +contour1 = Contour(solver=solver, field="temperature", surfaces=wall_list) window2 = GraphicsWindow() window2.add_graphics(contour1) window2.show() @@ -861,23 +759,22 @@ # Create Iso-Surface of X=0.012826 m # ================================== -solver_session.settings.results.surfaces.iso_surface["x=0.012826"] = {} -solver_session.settings.results.surfaces.iso_surface["x=0.012826"].field = ( - "x-coordinate" +IsoSurface.create( + solver, + name="x=0.012826", + field="x-coordinate", + iso_values=[0.012826 * m], ) -solver_session.settings.results.surfaces.iso_surface["x=0.012826"] = { - "iso_values": [0.012826] -} ############################################################################# # Vector Plot # =========== vector1 = Vector( - solver=solver_session, + solver=solver, field="velocity", color_by="x-velocity", - surfaces=["x=0.012826"], + surfaces=[iso_x.name], scale=2.0, skip=5, ) @@ -911,8 +808,8 @@ # =================== p1 = XYPlot( - solver=solver_session, - surfaces=["x=0.012826"], + solver=solver, + surfaces=[iso_x.name], y_axis_function="pressure", x_axis_function="direction-vector", direction_vector=[0, 1, 0], @@ -937,4 +834,4 @@ ############################################################################# # Exit Fluent Session # =================== -solver_session.exit() +solver.exit() diff --git a/examples/00-fluent/exhaust_system_settings_api.py b/examples/00-fluent/exhaust_system_settings_api.py index af5ff3a8eda..d5f233d4d55 100644 --- a/examples/00-fluent/exhaust_system_settings_api.py +++ b/examples/00-fluent/exhaust_system_settings_api.py @@ -73,9 +73,14 @@ # the geometry file. # sphinx_gallery_thumbnail_path = '_static/exhaust_system_settings.png' +from ansys.units import VariableCatalog import ansys.fluent.core as pyfluent from ansys.fluent.core import examples - +from pathlib import Path +from ansys.fluent.core.generated.solver.settings_builtin import IsoSurface +from ansys.fluent.core.generated.solver.settings_builtin_261 import iterate, write_case_data +from ansys.fluent.core.solver import Viscous, VelocityInlet, PressureOutlet, Initialization, RunCalculation, Graphics, Pathline, Scene, Surfaces +from ansys.units.common import m, s import_file_name = examples.download_file( "exhaust_system.fmd", "pyfluent/exhaust_system" ) @@ -86,22 +91,22 @@ # Launch Fluent as a service in meshing mode with double precision running on # two processors and print Fluent version. -meshing_session = pyfluent.launch_fluent( +meshing = pyfluent.Meshing.from_install( precision="double", processor_count=2, - mode="meshing", ) -print(meshing_session.get_fluent_version()) +meshing.upload(import_file_name) +print(meshing.get_fluent_version()) ############################################################################### # Initialize workflow # ~~~~~~~~~~~~~~~~~~~ # Initialize the fault-tolerant meshing workflow. -meshing_session.workflow.InitializeWorkflow(WorkflowType="Fault-tolerant Meshing") +meshing.workflow.InitializeWorkflow(WorkflowType="Fault-tolerant Meshing") ############################################################################### -# Fault-folerant meshing workflow +# Fault-tolerant meshing workflow # ------------------------------- # The fault-tolerant meshing workflow guides you through the many tasks that # follow. @@ -111,11 +116,11 @@ # Import the CAD geometry file (``exhaust_system.fmd``) and selectively manage some # parts. -meshing_session.PartManagement.InputFileChanged( +meshing.PartManagement.InputFileChanged( FilePath=import_file_name, IgnoreSolidNames=False, PartPerBody=False ) -meshing_session.PMFileManagement.FileManager.LoadFiles() -meshing_session.PartManagement.Node["Meshing Model"].Copy( +meshing.PMFileManagement.FileManager.LoadFiles() +meshing.PartManagement.Node["Meshing Model"].Copy( Paths=[ "/dirty_manifold-for-wrapper," + "1/dirty_manifold-for-wrapper,1/main,1", "/dirty_manifold-for-wrapper," + "1/dirty_manifold-for-wrapper,1/flow-pipe,1", @@ -124,10 +129,10 @@ "/dirty_manifold-for-wrapper," + "1/dirty_manifold-for-wrapper,1/object1,1", ] ) -meshing_session.PartManagement.ObjectSetting[ +meshing.PartManagement.ObjectSetting[ "DefaultObjectSetting" ].OneZonePer.set_state("part") -cad_import = meshing_session.workflow.TaskObject["Import CAD and Part Management"] +cad_import = meshing.workflow.TaskObject["Import CAD and Part Management"] cad_import.Arguments.set_state( { "Context": 0, @@ -149,7 +154,7 @@ # ~~~~~~~~~~~~~~~~~~~~~~~~~~ # Describe the geometry and the flow characteristics. -describe_geom = meshing_session.workflow.TaskObject["Describe Geometry and Flow"] +describe_geom = meshing.workflow.TaskObject["Describe Geometry and Flow"] describe_geom.Arguments.set_state( { "AddEnclosure": "No", @@ -186,7 +191,7 @@ # .. image:: /_static/exhaust_system_012.png # :width: 400pt # :align: center -capping = meshing_session.workflow.TaskObject["Enclose Fluid Regions (Capping)"] +capping = meshing.workflow.TaskObject["Enclose Fluid Regions (Capping)"] capping.Arguments.set_state( { "CreatePatchPreferences": { @@ -221,7 +226,7 @@ capping.InsertCompoundChildTask() capping.Arguments.set_state({}) -meshing_session.workflow.TaskObject["inlet-1"].Execute() +meshing.workflow.TaskObject["inlet-1"].Execute() capping.Arguments.set_state( { "PatchName": "inlet-2", @@ -250,7 +255,7 @@ capping.InsertCompoundChildTask() capping.Arguments.set_state({}) -meshing_session.workflow.TaskObject["inlet-2"].Execute() +meshing.workflow.TaskObject["inlet-2"].Execute() capping.Arguments.set_state( { "PatchName": "inlet-3", @@ -279,7 +284,7 @@ capping.InsertCompoundChildTask() capping.Arguments.set_state({}) -meshing_session.workflow.TaskObject["inlet-3"].Execute() +meshing.workflow.TaskObject["inlet-3"].Execute() capping.Arguments.set_state( { "PatchName": "outlet-1", @@ -310,13 +315,13 @@ capping.InsertCompoundChildTask() capping.Arguments.set_state({}) -meshing_session.workflow.TaskObject["outlet-1"].Execute() +meshing.workflow.TaskObject["outlet-1"].Execute() ############################################################################### # Extract edge features # ~~~~~~~~~~~~~~~~~~~~~ # Extract edge features. -edge_features = meshing_session.workflow.TaskObject["Extract Edge Features"] +edge_features = meshing.workflow.TaskObject["Extract Edge Features"] edge_features.Arguments.set_state( { "ExtractMethodType": "Intersection Loops", @@ -326,7 +331,7 @@ edge_features.AddChildToTask() edge_features.InsertCompoundChildTask() -edge_group = meshing_session.workflow.TaskObject["edge-group-1"] +edge_group = meshing.workflow.TaskObject["edge-group-1"] edge_group.Arguments.set_state( { "ExtractEdgesName": "edge-group-1", @@ -342,7 +347,7 @@ # Identify regions # ~~~~~~~~~~~~~~~~ # Identify regions. -identify_regions = meshing_session.workflow.TaskObject["Identify Regions"] +identify_regions = meshing.workflow.TaskObject["Identify Regions"] identify_regions.Arguments.set_state( { "SelectionType": "zone", @@ -374,7 +379,7 @@ identify_regions.AddChildToTask() identify_regions.InsertCompoundChildTask() -fluid_region_1 = meshing_session.workflow.TaskObject["fluid-region-1"] +fluid_region_1 = meshing.workflow.TaskObject["fluid-region-1"] fluid_region_1.Arguments.set_state( { "MaterialPointsName": "fluid-region-1", @@ -414,13 +419,13 @@ identify_regions.Arguments.set_state({}) -meshing_session.workflow.TaskObject["void-region-1"].Execute() +meshing.workflow.TaskObject["void-region-1"].Execute() ############################################################################### # Define thresholds for leakages # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ # Define thresholds for potential leakages. -leakage_threshold = meshing_session.workflow.TaskObject["Define Leakage Threshold"] +leakage_threshold = meshing.workflow.TaskObject["Define Leakage Threshold"] leakage_threshold.Arguments.set_state( { "AddChild": "yes", @@ -432,7 +437,7 @@ leakage_threshold.AddChildToTask() leakage_threshold.InsertCompoundChildTask() -leakage_1 = meshing_session.workflow.TaskObject["leakage-1"] +leakage_1 = meshing.workflow.TaskObject["leakage-1"] leakage_1.Arguments.set_state( { "AddChild": "yes", @@ -453,7 +458,7 @@ # Review region settings # ~~~~~~~~~~~~~~~~~~~~~~ # Review the region settings. -update_region = meshing_session.workflow.TaskObject["Update Region Settings"] +update_region = meshing.workflow.TaskObject["Update Region Settings"] update_region.Arguments.set_state( { "AllRegionFilterCategories": ["2"] * 5 + ["1"] * 2, @@ -496,7 +501,7 @@ # ~~~~~~~~~~~~~~~~~~~~~~~~ # Set mesh control options. -meshing_session.workflow.TaskObject["Choose Mesh Control Options"].Execute() +meshing.workflow.TaskObject["Choose Mesh Control Options"].Execute() ############################################################################### # Generate surface mesh @@ -508,32 +513,32 @@ # :width: 500pt # :align: center -meshing_session.workflow.TaskObject["Generate the Surface Mesh"].Execute() +meshing.workflow.TaskObject["Generate the Surface Mesh"].Execute() ############################################################################### # Confirm and update boundaries # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ # Confirm and update the boundaries. -meshing_session.workflow.TaskObject["Update Boundaries"].Execute() +meshing.workflow.TaskObject["Update Boundaries"].Execute() ############################################################################### # Add boundary layers # ~~~~~~~~~~~~~~~~~~~ # Add boundary layers. -meshing_session.workflow.TaskObject["Add Boundary Layers"].AddChildToTask() +meshing.workflow.TaskObject["Add Boundary Layers"].AddChildToTask() -meshing_session.workflow.TaskObject["Add Boundary Layers"].InsertCompoundChildTask() +meshing.workflow.TaskObject["Add Boundary Layers"].InsertCompoundChildTask() -meshing_session.workflow.TaskObject["aspect-ratio_1"].Arguments.set_state( +meshing.workflow.TaskObject["aspect-ratio_1"].Arguments.set_state( { "BLControlName": "aspect-ratio_1", } ) -meshing_session.workflow.TaskObject["Add Boundary Layers"].Arguments.set_state({}) +meshing.workflow.TaskObject["Add Boundary Layers"].Arguments.set_state({}) -meshing_session.workflow.TaskObject["aspect-ratio_1"].Execute() +meshing.workflow.TaskObject["aspect-ratio_1"].Execute() ############################################################################### # Generate volume mesh @@ -544,7 +549,7 @@ # .. image:: /_static/exhaust_system_014.png # :width: 500pt # :align: center -volume_mesh_gen = meshing_session.workflow.TaskObject["Generate the Volume Mesh"] +volume_mesh_gen = meshing.workflow.TaskObject["Generate the Volume Mesh"] volume_mesh_gen.Arguments.set_state( { "AllRegionNameList": [ @@ -568,7 +573,7 @@ # ~~~~~~~~~~ # Check the mesh. -meshing_session.tui.mesh.check_mesh() +meshing.tui.mesh.check_mesh() ############################################################################### # Solve and postprocess @@ -580,64 +585,44 @@ # ~~~~~~~~~~~~~~~~~~~~~~~ # Switch to the solution mode. -solver_session = meshing_session.switch_to_solver() +solver = meshing.switch_to_solver() -solver_session.settings.mesh.check() +solver.settings.mesh.check() ############################################################################### # Select turbulence model # ~~~~~~~~~~~~~~~~~~~~~~~ # Select the kw sst turbulence model. -viscous = solver_session.settings.setup.models.viscous - -viscous.model = "k-omega" -viscous.k_omega_model = "sst" +viscous = Viscous(solver) +viscous.model = viscous.model.K_OMEGA +viscous.k_omega_model = viscous.k_omega_model.SST ############################################################################### # Set velocity and turbulence boundary conditions for first inlet # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -# Set the velocity and turbulence boundary conditions for the first inlet -# (``inlet-1``). - -boundary_conditions = solver_session.settings.setup.boundary_conditions +# Set the velocity and turbulence boundary conditions for the inlets -boundary_conditions.velocity_inlet["inlet-1"] = { - "momentum": { - "velocity_specification_method": "Magnitude, Normal to Boundary", - "velocity": { - "value": 1, - }, - }, -} - -############################################################################### -# Set same boundary conditions for other velocity inlets -# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -# Set the same boundary conditions for the other velocity inlets (``inlet_2`` -# and ``inlet_3``). +inlets = VelocityInlet.get(solver, name="inlet-*") -boundary_conditions.copy( - from_="inlet-1", - to=["inlet-2", "inlet-3"], -) +inlets.momentum.velocity_specification_method = "Magnitude, Normal to Boundary" +inlets.momentum.velocity_magnitude = 1 * m / s ############################################################################### # Set boundary conditions at outlet # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ # Set the boundary conditions at the outlet (``outlet-1``). - -boundary_conditions.pressure_outlet["outlet-1"].turbulence.turbulent_intensity = 0.05 -boundary_conditions.pressure_outlet[ - "outlet-1" -].turbulence.backflow_turbulent_intensity = 0.05 +outlet = PressureOutlet.get(solver, name="outlet-1") +outlet.turbulence.turbulent_intensity = 0.05 +outlet.turbulence.backflow_turbulent_intensity = 0.05 ############################################################################### # Initialize flow field # ~~~~~~~~~~~~~~~~~~~~~ # Initialize the flow field using hybrid initialization. -solver_session.settings.solution.initialization.hybrid_initialize() +initialize = Initialization(solver) +initialize.hybrid_initialize() ############################################################################### # Start calculation @@ -649,14 +634,13 @@ # :width: 500pt # :align: center -solver_session.settings.solution.run_calculation.iterate(iter_count=100) +iterate(solver, iter_count=100) ############################################################################### # Write the case and data files # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -solver_session.settings.file.write( - file_type="case-data", +write_case_data(solver, file_name="exhaust_system.cas.h5", ) @@ -667,7 +651,6 @@ # picture files. Edit the picture settings to use a custom resolution so that # the images are large enough. -graphics = solver_session.settings.results.graphics # use_window_resolution option not active inside containers or Ansys Lab environment if graphics.picture.use_window_resolution.is_active(): graphics.picture.use_window_resolution = False @@ -686,15 +669,13 @@ # :width: 500pt # :align: center -graphics.pathline["pathlines-1"] = { - "field": "time", - "accuracy_control": { - "tolerance": 0.001, - }, - "skip": 5, - "release_from_surfaces": ["inlet-1", "inlet-2", "inlet-3"], -} -graphics.pathline["pathlines-1"].display() +pathlines = Pathline.create(solver, name="pathlines-1", +field = "time", +skip = 5, +release_from_surfaces = list(inlets), +) +pathlines.accuracy_control.tolerance = 0.001 +pathlines.display() graphics.views.restore_view(view_name="isometric") graphics.views.auto_scale() @@ -705,11 +686,7 @@ # ~~~~~~~~~~~~~~~~~~ # Create an iso-surface through the manifold geometry. -solver_session.settings.results.surfaces.iso_surface["surf-x-coordinate"] = { - "field": "x-coordinate", - "zones": ["fluid-region-1"], - "iso_values": [0.38], -} +IsoSurface.create(solver, name="surf-x-coordinate", field="x-coordinate", zones=["fluid-region-1"], iso_values=[0.38] * m) ############################################################################### # Create contours of velocity magnitude @@ -722,22 +699,15 @@ # :width: 500pt # :align: center -graphics.contour["contour-velocity"] = { - "field": "velocity-magnitude", - "surfaces_list": ["surf-x-coordinate"], - "node_values": False, - "range_option": { - "option": "auto-range-on", - "auto_range_on": { - "global_range": False, - }, - }, -} -graphics.mesh["mesh-1"] = { - "surfaces_list": "*", -} -graphics.contour["contour-velocity"].display() +graphics = Graphics(solver) +vel_contour = Contour.create(solver, name="contour-velocity", field = "velocity-magnitude", surfaces_list = ["surf-x-coordinate"], node_values = False) +vel_contour.range_option.option = "auto-range-on" +vel_contour.range_option.auto_range_on.global_range = False + +mesh_1 = graphics.mesh.create("mesh-1") +mesh_1.surfaces_list = "*" +vel_contour.display() graphics.views.restore_view(view_name="right") graphics.views.auto_scale() graphics.picture.save_picture(file_name="contour-velocity.png") @@ -753,13 +723,11 @@ # :width: 500pt # :align: center -solver_session.settings.results.scene["scene-1"] = {} -scene1 = solver_session.settings.results.scene["scene-1"] -scene1.graphics_objects.add(name="mesh-1") -scene1.graphics_objects["mesh-1"].transparency = 90 -scene1.graphics_objects.add(name="contour-velocity") -scene1.display() - +scene_1 = Scene.create(solver, name="scene-1") +added_mesh = scene_1.graphics_objects.add(name=mesh_1) +added_mesh.transparency = 90 +scene_1.graphics_objects.add(name=vel_contour.name) +scene_1.display() graphics.views.camera.position = [1.70, 1.14, 0.29] graphics.views.camera.up_vector = [-0.66, 0.72, -0.20] graphics.picture.save_picture(file_name="scene-1.png") @@ -769,4 +737,4 @@ # ~~~~~~~~~~~~ # Close Fluent. -solver_session.exit() +solver.exit() diff --git a/examples/00-fluent/external_compressible_flow.py b/examples/00-fluent/external_compressible_flow.py index 4cb142e3b88..6a27febb107 100644 --- a/examples/00-fluent/external_compressible_flow.py +++ b/examples/00-fluent/external_compressible_flow.py @@ -78,6 +78,16 @@ import ansys.fluent.core as pyfluent from ansys.fluent.core import examples +from ansys.fluent.core.generated.solver.settings_builtin import RunCalculation +from ansys.fluent.core.generated.solver.settings_builtin_261 import write_case +from ansys.fluent.core.solver import ( + FluidMaterial, + General, + Initialization, + PressureFarFieldBoundary, + Viscous, +) +from ansys.units.common import K, Pa, kg, m, s wing_spaceclaim_file, wing_intermediary_file = [ examples.download_file(CAD_file, "pyfluent/external_compressible") @@ -90,22 +100,21 @@ # Launch Fluent as a service in meshing mode with double precision running on # four processors and print Fluent version. -meshing_session = pyfluent.launch_fluent( - precision="double", +meshing = pyfluent.Meshing.from_install( + precision=pyfluent.Precision.DOUBLE, processor_count=4, - mode="meshing", ) -print(meshing_session.get_fluent_version()) +print(meshing.get_fluent_version()) tmpdir = tempfile.mkdtemp() -meshing_session.preferences.MeshingWorkflow.TempFolder = tmpdir +meshing.preferences.MeshingWorkflow.TempFolder = tmpdir ############################################################################### # Initialize workflow # ~~~~~~~~~~~~~~~~~~~ # Initialize the watertight geometry meshing workflow. -meshing_session.workflow.InitializeWorkflow(WorkflowType="Watertight Geometry") +meshing.workflow.InitializeWorkflow(WorkflowType="Watertight Geometry") ############################################################################### # Watertight geometry meshing workflow @@ -116,7 +125,7 @@ # Import CAD and set length units # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ # Import the CAD geometry and set the length units to inches. -geo_import = meshing_session.workflow.TaskObject["Import Geometry"] +geo_import = meshing.workflow.TaskObject["Import Geometry"] geo_import.Arguments.set_state( { "FileName": wing_intermediary_file, @@ -129,7 +138,7 @@ # Add local sizing # ~~~~~~~~~~~~~~~~ # Add local sizing controls to the faceted geometry. -local_sizing = meshing_session.workflow.TaskObject["Add Local Sizing"] +local_sizing = meshing.workflow.TaskObject["Add Local Sizing"] local_sizing.Arguments.set_state( { "AddChild": "yes", @@ -168,7 +177,7 @@ # Generate surface mesh # ~~~~~~~~~~~~~~~~~~~~~ # Generate the surface mash. -surface_mesh_gen = meshing_session.workflow.TaskObject["Generate the Surface Mesh"] +surface_mesh_gen = meshing.workflow.TaskObject["Generate the Surface Mesh"] surface_mesh_gen.Arguments.set_state( {"CFDSurfaceMeshControls": {"MaxSize": 1000, "MinSize": 2}} ) @@ -179,7 +188,7 @@ # Describe geometry # ~~~~~~~~~~~~~~~~~ # Describe geometry and define the fluid region. -describe_geo = meshing_session.workflow.TaskObject["Describe Geometry"] +describe_geo = meshing.workflow.TaskObject["Describe Geometry"] describe_geo.UpdateChildTasks(SetupTypeChanged=False) describe_geo.Arguments.set_state( @@ -195,21 +204,21 @@ # ~~~~~~~~~~~~~~~~~ # Update the boundaries. -meshing_session.workflow.TaskObject["Update Boundaries"].Execute() +meshing.workflow.TaskObject["Update Boundaries"].Execute() ############################################################################### # Update regions # ~~~~~~~~~~~~~~ # Update the regions. -meshing_session.workflow.TaskObject["Update Regions"].Execute() +meshing.workflow.TaskObject["Update Regions"].Execute() ############################################################################### # Add boundary layers # ~~~~~~~~~~~~~~~~~~~ # Add boundary layers, which consist of setting properties for the # boundary layer mesh. -add_boundary_layer = meshing_session.workflow.TaskObject["Add Boundary Layers"] +add_boundary_layer = meshing.workflow.TaskObject["Add Boundary Layers"] add_boundary_layer.Arguments.set_state({"NumberOfLayers": 12}) add_boundary_layer.AddChildAndUpdate() @@ -219,7 +228,7 @@ # ~~~~~~~~~~~~~~~~~~~~ # Generate the volume mesh, which consists of setting properties for the # volume mesh. -volume_mesh_gen = meshing_session.workflow.TaskObject["Generate the Volume Mesh"] +volume_mesh_gen = meshing.workflow.TaskObject["Generate the Volume Mesh"] volume_mesh_gen.Arguments.set_state( { "VolumeFill": "poly-hexcore", @@ -238,14 +247,14 @@ # ~~~~~~~~~~~~~~~~~~~~~~~~~~ # Check the mesh in meshing mode. -meshing_session.tui.mesh.check_mesh() +meshing.tui.mesh.check_mesh() ############################################################################### # Save mesh file # ~~~~~~~~~~~~~~ # Save the mesh file (``wing.msh.h5``). -meshing_session.meshing.File.WriteMesh(FileName="wing.msh.h5") +meshing.meshing.File.WriteMesh(FileName="wing.msh.h5") ############################################################################### # Solve and postprocess @@ -259,7 +268,7 @@ # using Fluent in meshing mode, you can switch to solver mode to complete the # setup of the simulation. -solver_session = meshing_session.switch_to_solver() +solver = meshing.switch_to_solver() ############################################################################### # Check mesh in solver mode @@ -269,7 +278,7 @@ # reports a number of other mesh features that are checked. Any errors in the # mesh are reported. -solver_session.settings.mesh.check() +solver.settings.mesh.check() ############################################################################### # Define model @@ -279,24 +288,17 @@ # model : k-omega # k-omega model : sst -viscous = solver_session.settings.setup.models.viscous +viscous = Viscous(solver) -viscous.model = "k-omega" -viscous.k_omega_model = "sst" +viscous.model = viscous.model.K_OMEGA +viscous.k_omega_model = viscous.k_omega_model.SST ############################################################################### # Define materials # ~~~~~~~~~~~~~~~~ # Modify the default material ``air`` to account for compressibility and variations of the thermophysical properties with temperature. -# density : ideal-gas -# viscosity : sutherland -# viscosity method : three-coefficient-method -# reference viscosity : 1.716e-05 [kg/(m s)] -# reference temperature : 273.11 [K] -# effective temperature : 110.56 [K] - -air = solver_session.settings.setup.materials.fluid["air"] +air = FluidMaterial.get(solver, name="air") air.density.option = "ideal-gas" @@ -304,68 +306,57 @@ air.viscosity.sutherland.option = "three-coefficient-method" -air.viscosity.sutherland.reference_viscosity = 1.716e-05 +air.viscosity.sutherland.reference_viscosity = 1.716e-05 * kg / (m * s) -air.viscosity.sutherland.reference_temperature = 273.11 +air.viscosity.sutherland.reference_temperature = 273.11 * K -air.viscosity.sutherland.effective_temperature = 110.56 +air.viscosity.sutherland.effective_temperature = 110.56 * K ############################################################################### # Boundary Conditions # ~~~~~~~~~~~~~~~~~~~ # Set the boundary conditions for ``pressure_farfield``. -# gauge pressure : 0 [Pa] -# mach number : 0.8395 -# temperature : 255.56 [K] -# x-component of flow direction : 0.998574 -# z-component of flow direction : 0.053382 -# turbulent intensity : 5 [%] -# turbulent viscosity ratio : 10 - -pressure_farfield = ( - solver_session.settings.setup.boundary_conditions.pressure_far_field[ - "pressure_farfield" - ] -) +pressure_far_field = PressureFarFieldBoundary.get(solver, name="pressure_farfield") -pressure_farfield.momentum.gauge_pressure = 0 +pressure_far_field.momentum.gauge_pressure = 0 * Pa -pressure_farfield.momentum.mach_number = 0.8395 +pressure_far_field.momentum.mach_number = 0.8395 -pressure_farfield.thermal.temperature = 255.56 +pressure_far_field.thermal.temperature = 255.56 * K -pressure_farfield.momentum.flow_direction[0] = 0.998574 +pressure_far_field.momentum.flow_direction[0] = 0.998574 # x-component -pressure_farfield.momentum.flow_direction[2] = 0.053382 +pressure_far_field.momentum.flow_direction[2] = 0.053382 # z-component -pressure_farfield.turbulence.turbulent_intensity = 0.05 +pressure_far_field.turbulence.turbulent_intensity = 0.05 -pressure_farfield.turbulence.turbulent_viscosity_ratio = 10 +pressure_far_field.turbulence.turbulent_viscosity_ratio = 10 ############################################################################### # Operating Conditions # ~~~~~~~~~~~~~~~~~~~~ # Set the operating conditions. -# operating pressure : 80600 [Pa] - -solver_session.settings.setup.general.operating_conditions.operating_pressure = 80600 +general = General(solver) +general.operating_conditions.operating_pressure = 80_600 * Pa ############################################################################### # Initialize flow field # ~~~~~~~~~~~~~~~~~~~~~ # Initialize the flow field using hybrid initialization. -solver_session.settings.solution.initialization.hybrid_initialize() +initialize = Initialization(solver) +initialize.hybrid_initialize() ############################################################################### # Save case file # ~~~~~~~~~~~~~~ # Save the case file ``external_compressible1.cas.h5``. -solver_session.settings.file.write( - file_name="external_compressible.cas.h5", file_type="case" +write_case( + solver, + file_name="external_compressible.cas.h5" ) ############################################################################### @@ -373,15 +364,16 @@ # ~~~~~~~~~~~~~~~~~~~~~~~~ # Solve for 25 iterations (100 iterations is recommended, however for this example 25 is sufficient). -solver_session.settings.solution.run_calculation.iterate(iter_count=25) +RunCalculation(solver).iterate(iter_count=25) ############################################################################### # Write final case file and data # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ # Write the final case file and the data. -solver_session.settings.file.write( - file_name="external_compressible1.cas.h5", file_type="case" +write_case( + solver, + file_name="external_compressible1.cas.h5" ) ############################################################################### @@ -389,7 +381,7 @@ # ~~~~~~~~~~~~ # Close Fluent. -solver_session.exit() +solver.exit() shutil.rmtree(tmpdir, ignore_errors=True) shutil.rmtree("wing_workflow_files", ignore_errors=True) diff --git a/examples/00-fluent/frozen_rotor_workflow.py b/examples/00-fluent/frozen_rotor_workflow.py index a789437dc28..17996774486 100644 --- a/examples/00-fluent/frozen_rotor_workflow.py +++ b/examples/00-fluent/frozen_rotor_workflow.py @@ -80,10 +80,42 @@ # Import required libraries/modules # ============================================================================================================== import math -import os +from mimetypes import init +from nt import write +from pathlib import Path + +from ansys.units import VariableCatalog import ansys.fluent.core as pyfluent from ansys.fluent.core import examples +from ansys.fluent.core.generated.solver.settings_builtin import ( + BoundaryCondition, + BoundaryConditions, + Initialization, + Materials, + MeshInterfaces, + Methods, + Monitor, + NamedExpression, + PlaneSurface, + PressureInlet, + ReportDefinitions, + ReportPlot, + Setup, + Surfaces, +) +from ansys.fluent.core.generated.solver.settings_builtin_261 import write_case, write_case_data +from ansys.fluent.core.solver import ( + FluidCellZone, + General, + MassFlowOutletBoundary, + PressureInletBoundary, + Viscous, + WallBoundary, +) +from ansys.fluent.core.solver import RunCalculation +from ansys.fluent.visualization import Contour, Graphics +from ansys.units.common import Pa, kg, m, s ################################################################################################################ # Download the mesh file @@ -94,37 +126,40 @@ impeller_mesh = examples.download_file( "impeller.msh.h5", "pyfluent/examples/pump-volute", - save_path=os.getcwd(), + save_path=Path.cwd(), ) volute_mesh = examples.download_file( "volute.msh.h5", "pyfluent/examples/pump-volute", - save_path=os.getcwd(), + save_path=Path.cwd(), ) + ################################################################################################################ # Define Constants # ============================================================================================================== -density_water = 998.2 # kg/m^3 -viscosity_water = 0.001002 # kg/(m.s) -g = 9.81 # m/s^2 -# Impeller speed +density_water = 998.2 * kg / m**3 +viscosity_water = 0.001002 * Pa * s +g = 9.81 * m / s**2 impeller_speed = 1450 # rpm -# Convert to rad/s -impeller_speed_rad = impeller_speed * 2 * math.pi / 60 # rad/s +# Convert to rad/s (numeric) +impeller_speed_rad = impeller_speed * 2 * math.pi / 60 ################################################################################################################ # Launch Fluent with solver mode and print Fluent version # ============================================================================================================== -solver_session = pyfluent.launch_fluent( - mode="solver", +solver = pyfluent.Solver.from_install( processor_count=4, cleanup_on_exit=True, ) -print(solver_session.get_fluent_version()) +print(solver.get_fluent_version()) + +# upload mesh files to the solver +solver.upload(impeller_mesh) +solver.upload(volute_mesh) ################################################################################################################ @@ -132,19 +167,19 @@ # ============================================================================================================== # Read Impeller mesh file -solver_session.settings.file.read_mesh(file_name=impeller_mesh) +solver.settings.file.read_mesh(file_name=impeller_mesh) # Append Volute mesh file -solver_session.settings.mesh.modify_zones.append_mesh(file_name=volute_mesh) +solver.settings.mesh.modify_zones.append_mesh(file_name=volute_mesh) ################################################################################################################ # Display the mesh # ============================================================================================================== # Access the graphics object -graphics = solver_session.settings.results.graphics +graphics = Graphics(solver) # Create a mesh object and configure its settings -mesh_object = solver_session.settings.results.graphics.mesh.create(name="mesh-1") +mesh_object = graphics.mesh.create(name="mesh-1") mesh_object.surfaces_list = [ "inlet", "mass-flow-inlet-11", @@ -183,108 +218,88 @@ # Set the unit for angular velocity, rad/s to rev/min # ============================================================================================================== -solver_session.settings.setup.general.units.set_units( - quantity="angular-velocity", units_name="rev/min" -) +general = General(solver) +general.units.set_units(quantity="angular-velocity", units_name="rev/min") ################################################################################################################ # Define the Viscous Model # ============================================================================================================== # Models setting -viscous = solver_session.settings.setup.models.viscous -viscous = solver_session.settings.setup.models.viscous -viscous.model = "k-omega" -viscous.k_omega_model = "sst" +viscous = Viscous(solver) +viscous.model = viscous.model.K_OMEGA +viscous.k_omega_model = viscous.k_omega_model.SST ################################################################################################################ # Define Materials # ============================================================================================================== -solver_session.settings.setup.materials.database.copy_by_name( - type="fluid", name="water-liquid" -) +Materials(solver).database.copy_by_name(type="fluid", name="water-liquid") ################################################################################################################ # Define Cell Zone Conditions # ============================================================================================================== -impeller_cell_zone = solver_session.settings.setup.cell_zone_conditions.fluid[ - "impeller" -] +impeller_cell_zone = FluidCellZone.get(solver, name="impeller") impeller_cell_zone.general.material = "water-liquid" -impeller_cell_zone.reference_frame.reference_frame_axis_origin = [0, 0, 0] -impeller_cell_zone.reference_frame.reference_frame_axis_direction = [0, 0, 1] +impeller_cell_zone.reference_frame.reference_frame_axis_origin = (0, 0, 0) +impeller_cell_zone.reference_frame.reference_frame_axis_direction = (0, 0, 1) impeller_cell_zone.reference_frame.frame_motion = True -# impeller rotation -impeller_cell_zone.reference_frame.mrf_omega.value = impeller_speed_rad +impeller_cell_zone.reference_frame.mrf_omega = impeller_speed_rad -# Volute Cell Zone Conditions -volute_cell_zone = solver_session.settings.setup.cell_zone_conditions.fluid["volute"] +volute_cell_zone = FluidCellZone.get(solver, name="volute") volute_cell_zone.general.material = "water-liquid" # Boundary Conditions -# impeller hub -impeller_hub = solver_session.settings.setup.boundary_conditions.wall[ - "impeller-hub" -].momentum -impeller_hub.wall_motion = "Moving Wall" -impeller_hub.relative = True -impeller_hub.velocity_spec = "Rotational" - -# inblock-shroud - -inblock_shroud = solver_session.settings.setup.boundary_conditions.wall[ - "inblock-shroud" -].momentum -inblock_shroud.wall_motion = "Moving Wall" -inblock_shroud.relative = False -inblock_shroud.velocity_spec = "Rotational" +impeller_hub = WallBoundary.get(solver, name="impeller-hub") +impeller_hub.momentum.wall_motion = impeller_hub.momentum.wall_motion.MOVING_WALL +impeller_hub.momentum.relative = True +impeller_hub.momentum.velocity_spec = impeller_hub.momentum.velocity_spec.ROTATIONAL + +inblock_shroud = WallBoundary.get(solver, name="inblock-shroud") +inblock_shroud.momentum.wall_motion = inblock_shroud.momentum.wall_motion.MOVING_WALL +inblock_shroud.momentum.relative = False +inblock_shroud.momentum.velocity_spec = "Rotational" ################################################################################################################ # Define Boundary Conditions # ============================================================================================================== # Inlet Boundary Condition -pressure_inlet = solver_session.settings.setup.boundary_conditions.pressure_inlet[ - "inlet" -] -pressure_inlet.momentum.supersonic_or_initial_gauge_pressure.value = -100 +pressure_inlet = PressureInlet.get(solver, name="inlet") +pressure_inlet.momentum.supersonic_or_initial_gauge_pressure = -100 * Pa # It seems, need to change the boundary condition to mass flow outlet -solver_session.settings.setup.boundary_conditions.set_zone_type( +BoundaryConditions(solver).set_zone_type( zone_list=["mass-flow-inlet-11"], new_type="mass-flow-outlet" ) # Outlet Boundary Condition -mass_flow_outlet = solver_session.settings.setup.boundary_conditions.mass_flow_outlet[ - "mass-flow-inlet-11" -] -mass_flow_outlet.momentum.mass_flow_rate.value = 90 # kg/s +mass_flow_outlet = MassFlowOutletBoundary.get(solver, name="mass-flow-inlet-11") +mass_flow_outlet.momentum.mass_flow_rate.value = 90 * kg / s # Create a turbo interfaces # enable the turbo models -solver_session.settings.setup.turbo_models.enabled = True - -impeller_volute_interface = ( - solver_session.settings.setup.mesh_interfaces.turbo_create.create( - adjacent_cell_zone_1="impeller", - adjacent_cell_zone_2="volute", - mesh_interface_name="imp-volute-interface", - turbo_choice="No-Pitch-Scale", - zone1="interface-impeller-outlet", - zone2="interface-volute-inlet", - ) +turbo_models = Setup(solver).turbo_models +turbo_models.enabled = True + +impeller_volute_interface = MeshInterfaces(solver).turbo_create.create( + adjacent_cell_zone_1="impeller", + adjacent_cell_zone_2="volute", + mesh_interface_name="imp-volute-interface", + turbo_choice="No-Pitch-Scale", + zone1="interface-impeller-outlet", + zone2="interface-volute-inlet", ) ################################################################################################################ # Define Solver Settings # ============================================================================================================== -methods = solver_session.settings.solution.methods +methods = Methods(solver) methods.spatial_discretization.gradient_scheme = "green-gauss-node-based" methods.high_order_term_relaxation.enable = True @@ -292,95 +307,68 @@ # Define Named Expressions # ============================================================================================================== -pump_head = solver_session.settings.setup.named_expressions.create("head") -pump_head.definition = "(({p-out} - {p-in}) / (998.2 [kg/m^3] * 9.81[m/s^2]))" -pump_head.output_parameter = True +pump_head = NamedExpression.create( + solver, + name="head", + definition="(({p-out} - {p-in}) / (998.2 [kg/m^3] * 9.81[m/s^2]))", + output_parameter=True, +) ################################################################################################################ # Define Report Definitions # ============================================================================================================== +monitor = Monitor(solver) +report_definitions = ReportDefinitions(solver) + # Create a report definition # p-out -outlet_pressure_report_def = ( - solver_session.settings.solution.report_definitions.surface.create("p-out") +outlet_pressure_report_def = report_definitions.surface.create( + "p-out", + report_type="surface-massavg", + surface_names=["mass-flow-inlet-11"], + field="total-pressure", + per_surface=False, ) -outlet_pressure_report_def.report_type = "surface-massavg" -outlet_pressure_report_def.surface_names = ["mass-flow-inlet-11"] -outlet_pressure_report_def.field = "total-pressure" -outlet_pressure_report_def.per_surface = False -outlet_pressure_report_plot = ( - solver_session.settings.solution.monitor.report_plots.create("p-out-rplot") -) -outlet_pressure_report_plot.report_defs = "p-out" +outlet_pressure_report_plot = ReportPlot(solver, name="p-out-rplot",report_defs = "p-out") -outlet_pressure_report_file = ( - solver_session.settings.solution.monitor.report_files.create("p-out-rfile") -) -outlet_pressure_report_file.report_defs = "p-out" +outlet_pressure_report_file = ReportPlot(solver, name="p-out-rfile",report_defs = "p-out") # p-in -inlet_pressure_report_def = ( - solver_session.settings.solution.report_definitions.surface.create("p-in") -) -inlet_pressure_report_def.report_type = "surface-massavg" -inlet_pressure_report_def.surface_names = ["inlet"] -inlet_pressure_report_def.field = "total-pressure" -inlet_pressure_report_def.per_surface = False +inlet_pressure_report_def = report_definitions.surface.create("p-in", report_type = "surface-massavg", surface_names = ["inlet"], field = "total-pressure", per_surface = False) # Pump Head -pump_head_report_def = ( - solver_session.settings.solution.report_definitions.single_valued_expression.create( - "pump-head" - ) -) +pump_head_report_def = report_definitions.single_valued_expression.create("pump-head") pump_head_report_def.definition = "head" # report plot -pump_head_report_plot = solver_session.settings.solution.monitor.report_plots.create( - "pump-head-rplot" -) -pump_head_report_plot.report_defs = "pump-head" +pump_head_report_plot = monitor.report_plots.create("pump-head-rplot", report_defs=pump_head_report_def) # report file -pump_head_report_file = solver_session.settings.solution.monitor.report_files.create( - "pump-head-rfile" -) -pump_head_report_file.report_defs = "pump-head" +pump_head_report_file = monitor.report_files.create("pump-head-rfile", report_defs=pump_head_report_def) # p-blade -blade_pressure_report_def = ( - solver_session.settings.solution.report_definitions.surface.create("p-blade") -) -blade_pressure_report_def.report_type = "surface-massavg" -blade_pressure_report_def.surface_names = ["blade"] -blade_pressure_report_def.field = "pressure" -blade_pressure_report_def.per_surface = False - +blade_pressure_report_def = report_definitions.surface.create("p-blade", report_type = "surface-massavg", surface_names = ["blade"], field = "pressure", per_surface = False) ################################################################################################################ # Initialization and run solver # ============================================================================================================== -initialization = solver_session.settings.solution.initialization +initialization = Initialization(solver) initialization.reference_frame = "absolute" -initialization.hybrid_init_options.general_settings.initialization_options.initial_pressure = ( - True -) +initialization.hybrid_init_options.general_settings.initialization_options.initial_pressure = True initialization.hybrid_initialize() # Run calculation settings -run_calculation = solver_session.settings.solution.run_calculation +run_calculation = RunCalculation(solver) run_calculation.pseudo_time_settings.time_step_method.time_step_size_scale_factor = 10 run_calculation.iter_count = 200 # Write the case file -solver_session.settings.file.write( - file_type="case", file_name="pump_voulte_setup.cas.h5" -) +write_case(solver, file_name="pump_volute_setup.cas.h5") # Run the calculation run_calculation.calculate() @@ -389,24 +377,14 @@ # ============================================================================================================== # Create a mid-plane surface at z = -0.015 m -z_mid_plane = solver_session.settings.results.surfaces.plane_surface.create( - name="z_mid_plane" -) -z_mid_plane.method = "xy-plane" -z_mid_plane.z = -0.015 +z_mid_plane = PlaneSurface.create(solver, name="z_mid_plane", method = "xy-plane", z = -0.015) z_mid_plane.display() -# Define the contour for static pressure -pressure_contour = solver_session.settings.results.graphics.contour.create( - name="static-pressure-contour" -) -pressure_contour.field = "pressure" -pressure_contour.surfaces_list = ["z_mid_plane"] - -# Display the contour and save the image - -graphics.views.restore_view(view_name="front") +# Define and display the contour for static pressure using typed API +graphics = Graphics(solver) +pressure_contour = Contour.create(solver=solver, field=VariableCatalog.PRESSURE, surfaces=["z_mid_plane"]) pressure_contour.display() +graphics.views.restore_view(view_name="front") graphics.views.auto_scale() graphics.picture.save_picture(file_name="static-pressure-contour.png") @@ -419,14 +397,14 @@ ################################################################################################################ # Save the case file # ============================================================================================================== -solver_session.settings.file.write( - file_type="case-data", file_name="pump_volute_setup_solved.cas.h5" +write_case_data(solver, + file_name="pump_volute_setup_solved.cas.h5" ) ################################################################################################################ # Close the session # ============================================================================================================== -solver_session.exit() +solver.exit() ################################################################################################################ # References diff --git a/examples/00-fluent/fsi_1way_workflow.py b/examples/00-fluent/fsi_1way_workflow.py index 8bba0da9184..2ce7ba21497 100644 --- a/examples/00-fluent/fsi_1way_workflow.py +++ b/examples/00-fluent/fsi_1way_workflow.py @@ -67,10 +67,13 @@ # Importing the following classes offer streamlined access to key solver settings, # eliminating the need to manually browse through the full settings structure. -import os +from pathlib import Path import ansys.fluent.core as pyfluent -from ansys.fluent.core import FluentMode, Precision, examples +from ansys.fluent.core import Precision, examples +from ansys.fluent.core.generated.solver.settings_242 import read_case +from ansys.fluent.core.generated.solver.settings_builtin import Controls +from ansys.fluent.core.generated.solver.settings_builtin_261 import BoundaryCondition, Materials, iterate, write_case, write_case_data from ansys.fluent.core.solver import ( BoundaryConditions, Contour, @@ -78,18 +81,20 @@ Initialization, RunCalculation, Setup, + SolidCellZone, Solution, + Structure, VelocityInlet, + WallBoundary, ) +from ansys.units import VariableCatalog +from ansys.units.common import m, s # %% # Launch Fluent session in solver mode # ------------------------------------ -solver = pyfluent.launch_fluent( - precision=Precision.DOUBLE, - mode=FluentMode.SOLVER, -) +solver = pyfluent.Solver.from_install(precision=Precision.DOUBLE) # %% # Download and read the mesh file @@ -98,16 +103,16 @@ mesh_file = examples.download_file( "fsi_1way.msh.h5", "pyfluent/fsi_1way", - save_path=os.getcwd(), + save_path=Path.cwd(), ) -solver.settings.file.read_case(file_name=mesh_file) +read_case(solver, file_name=mesh_file) # %% # Configure solver settings for fluid flow # ---------------------------------------- -velocity_inlet = VelocityInlet(solver, name="velocity_inlet") -velocity_inlet.momentum.velocity_magnitude = 100.0 # High-speed inlet flow (m/s) +velocity_inlet = VelocityInlet.get(solver, name="velocity_inlet") +velocity_inlet.momentum.velocity_magnitude = 100.0 * m / s velocity_inlet.turbulence.turbulent_viscosity_ratio = ( 5 # Dimensionless, typically 1-10 for moderate turbulence ) @@ -119,8 +124,7 @@ initialize = Initialization(solver) initialize.hybrid_initialize() -calculation = RunCalculation(solver) -calculation.iterate(iter_count=100) +iterate(solver, iter_count=100) # %% # Post-processing @@ -130,13 +134,14 @@ graphics.picture.x_resolution = 650 # Horizontal resolution for clear visualization graphics.picture.y_resolution = 450 # Vertical resolution matching typical aspect ratio -graphics.contour["contour-vel"] = { - "field": "velocity-magnitude", - "surfaces_list": ["fluid-symmetry"], - "coloring": {"option": "banded"}, -} - -graphics.contour["contour-vel"].display() +contour_vel = Contour.create( + solver, + name="contour-vel", + field=VariableCatalog.VELOCITY_MAGNITUDE, + surfaces_list=["fluid-symmetry"], +) +contour_vel.colorings.banded = True +contour_vel.display() graphics.views.restore_view(view_name="front") graphics.picture.save_picture(file_name="fsi_1way_2.png") @@ -154,12 +159,13 @@ # Linear Elasticity Structural model is chosen setup = Setup(solver) -setup.models.structure.model = "linear-elasticity" +structure = Structure(solver) +structure.model = "linear-elasticity" # Copy materials from the database and assign to solid zone - -setup.materials.database.copy_by_name(type="solid", name="steel") -setup.cell_zone_conditions.solid["solid"] = {"general": {"material": "steel"}} +steel = Materials(solver).database.copy_by_name(type="solid", name="steel") +solid_zone = SolidCellZone.get(solver, name="solid") +solid_zone.general.material = steel # %% # Structural boundary conditions @@ -167,39 +173,28 @@ # configure Fluent to define the steel probe's support and movement using # structural boundary conditions -wall_boundary = BoundaryConditions(solver) - # Configure solid-symmetry boundary -wall_boundary.wall["solid-symmetry"] = { - "structure": { - "z_disp_boundary_value": 0, - "z_disp_boundary_condition": "Node Z-Displacement", - } -} +solid_sym = WallBoundary.get(solver, name="solid-symmetry") +solid_sym.structure.z_disp_boundary_value = 0 +solid_sym.structure.z_disp_boundary_condition = "Node Z-Displacement" # Set solid-top boundary (fully fixed) -wall_boundary.wall["solid-top"] = { - "structure": { - "z_disp_boundary_value": 0, - "z_disp_boundary_condition": "Node Z-Displacement", - "y_disp_boundary_value": 0, - "y_disp_boundary_condition": "Node Y-Displacement", - "x_disp_boundary_value": 0, - "x_disp_boundary_condition": "Node X-Displacement", - } -} - -# Copy boundary conditions from solid-symmetry to solid-symmetry:011 -wall_boundary.copy(from_="solid-symmetry", to=["solid-symmetry:011"]) +solid_top = WallBoundary.get(solver, name="solid-top") +solid_top.structure.z_disp_boundary_value = 0 +solid_top.structure.z_disp_boundary_condition = "Node Z-Displacement" +solid_top.structure.y_disp_boundary_value = 0 +solid_top.structure.y_disp_boundary_condition = "Node Y-Displacement" +solid_top.structure.x_disp_boundary_value = 0 +solid_top.structure.x_disp_boundary_condition = "Node X-Displacement" + +# Copy boundary conditions +BoundaryCondition(solver).copy(from_="solid-symmetry", to=["solid-symmetry:011"]) # Configure FSI surface -wall_boundary.wall["fsisurface-solid"] = { - "structure": { - "x_disp_boundary_condition": "Intrinsic FSI", - "y_disp_boundary_condition": "Intrinsic FSI", - "z_disp_boundary_condition": "Intrinsic FSI", - } -} +fsisurface = WallBoundary.get(solver, name="fsisurface-solid") +fsisurface.structure.x_disp_boundary_condition = "Intrinsic FSI" +fsisurface.structure.y_disp_boundary_condition = "Intrinsic FSI" +fsisurface.structure.z_disp_boundary_condition = "Intrinsic FSI" # %% # Inclusion of Operating Pressure in Fluid-Structure Interaction Forces @@ -207,40 +202,42 @@ # Fluent uses gauge pressure for fluid-structure interaction force calculations. # By setting ``include_pop_in_fsi_force`` to ``True``, Fluent uses absolute pressure. -setup.models.structure.expert.include_pop_in_fsi_force = True +structure.expert.include_pop_in_fsi_force = True # %% # Configure flow settings # ----------------------- # Disable flow equations for structural simulation -solution = Solution(solver) -solution.controls.equations["flow"] = False -solution.controls.equations["kw"] = False +controls = Controls(solver) +controls.equations["flow"] = False +controls.equations["kw"] = False # %% # Run FSI simulation # ------------------ -solver.settings.file.write_case(file_name="probe_fsi_1way.cas.h5") +write_case(solver, file_name="probe_fsi_1way.cas.h5") -calculation.iterate(iter_count=2) +iterate(solver, iter_count=2) # %% # Structural Postprocessing # ------------------------- -displacement_contour = Contour(solver, new_instance_name="displacement_contour") - -displacement_contour.field = "total-displacement" -displacement_contour.surfaces_list = ["fsisurface-solid"] +displacement_contour = Contour.create( + solver, + name="displacement_contour", + field=VariableCatalog.TOTAL_DISPLACEMENT, + surfaces_list=["fsisurface-solid"], +) displacement_contour.display() graphics.views.restore_view(view_name="isometric") graphics.picture.save_picture(file_name="fsi_1way_3.png") # save the case and data file -solver.settings.file.write_case_data(file_name="probe_fsi_1way") +write_case_data(solver, file_name="probe_fsi_1way") # %% # .. image:: ../../_static/fsi_1way_3.png diff --git a/examples/00-fluent/lunar_lander_thermal.py b/examples/00-fluent/lunar_lander_thermal.py index ee93a571f90..982d322da84 100644 --- a/examples/00-fluent/lunar_lander_thermal.py +++ b/examples/00-fluent/lunar_lander_thermal.py @@ -95,18 +95,43 @@ # flake8: noqa: E402 from itertools import chain -import os +from pathlib import Path import numpy as np import ansys.fluent.core as pyfluent from ansys.fluent.core import examples +from ansys.fluent.core.solver import write_case +from ansys.fluent.core.generated.solver.settings_builtin import ( + BoundaryCondition, + CellZoneConditions, + Monitor, + RunCalculation, +) +from ansys.fluent.core.generated.solver.settings_builtin_261 import ( + CellZoneCondition, + calculate, +) +from ansys.fluent.core.session_solver import Solver +from ansys.fluent.core.solver import ( + Energy, + General, + Initialization, + Radiation, + ReportDefinitions, + SolidCellZone, + SolidMaterial, + Viscous, + WallBoundary, +) +from ansys.units import Quantity, VariableCatalog +from ansys.units.common import J, K, W, kg, m, s lander_spaceclaim_file, lander_mesh_file, apollo17_temp_data = [ examples.download_file( f, "pyfluent/lunar_lander_thermal", - save_path=os.getcwd(), + save_path=Path.cwd(), ) for f in [ "lander_geom.scdoc", @@ -133,15 +158,15 @@ # Lunar axial obliquity relative to ecliptic moon_obliquity = np.deg2rad(1.54) -# Louver setpoint temperature [K] -louver_setpoint_temp = 273 +# Louver setpoint temperature +louver_setpoint_temp = 273 * K # Lander coordinates (Apollo 17 landing site) land_lat = np.deg2rad(20.1908) land_lon = np.deg2rad(30.7717) # Timestep size of 1 Earth day -step_size = 86400 +step_size = 86400 * s # Run simulation for 60 Earth days n_steps = 60 @@ -235,7 +260,7 @@ def sun_vec_to_beam_dir( def get_surf_mean_temp( surf_names: list[str], - solver: pyfluent.session_solver.Solver, + solver: Solver, ) -> float: """Calculate mean surface temperature.""" # Get surface IDs @@ -263,18 +288,17 @@ def get_surf_mean_temp( # Launch Fluent and print Fluent version # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -solver_session = pyfluent.launch_fluent( - precision="double", +solver = pyfluent.Solver.from_install( + precision=pyfluent.Precision.DOUBLE, processor_count=12, - mode="solver", ) -print(solver_session.get_fluent_version()) +print(solver.get_fluent_version()) ############################################################################### # Load the mesh # ~~~~~~~~~~~~~ -solver_session.settings.file.read_mesh(file_name=lander_mesh_file) +solver.settings.file.read_mesh(file_name=lander_mesh_file) ############################################################################### # Case Setup @@ -288,11 +312,10 @@ def get_surf_mean_temp( # Since we are only running 1 timestep at a time, the time step count is set to # 1. -# Set solution to transient -solver_session.settings.setup.general.solver.time = "unsteady-2nd-order" +general = General(solver) +general.solver.time = "unsteady-2nd-order" -# Set transient settings -trans_controls = solver_session.settings.solution.run_calculation.transient_controls +trans_controls = RunCalculation(solver).transient_controls trans_controls.type = "Fixed" trans_controls.max_iter_per_time_step = 20 trans_controls.time_step_count = 1 @@ -304,9 +327,11 @@ def get_surf_mean_temp( # Enable the energy model. Since fluid flow is not simulated, we will set the # viscosity model to laminar. -models = solver_session.settings.setup.models -models.energy.enabled = True -models.viscous.model = "laminar" +energy = Energy(solver) +energy.enabled = True + +viscous = Viscous(solver) +viscous.model = "laminar" ############################################################################### # Set up radiation model @@ -322,23 +347,15 @@ def get_surf_mean_temp( # space industry best practices [4_]. -# Set up radiation model -radiation = models.radiation +radiation = Radiation(solver) radiation.model = "monte-carlo" radiation.monte_carlo.number_of_histories = 1e7 -# Define range of solar wavelengths -radiation.multiband["solar"] = { - "start": 0, - "end": 2.8, -} -# Define range of thermal IR wavelengths -radiation.multiband["thermal-ir"] = { - "start": 2.8, - "end": 100, -} - -# Solve radiation once per timestep +radiation.multiband["solar"].start = 0 +radiation.multiband["solar"].end = 2.8 +radiation.multiband["thermal-ir"].start = 2.8 +radiation.multiband["thermal-ir"].end = 100 + radiation_freq = radiation.solve_frequency radiation_freq.method = "time-step" radiation_freq.time_step_interval = 1 @@ -351,38 +368,25 @@ def get_surf_mean_temp( # (soil). The thermal conductivity of the regolith and the surface 'fluff' is # strongly temperature-dependent and so must be modelled using an expression. -# --- Properties of vacuum --- -# Thermal conductivity: 0 - -vacuum = solver_session.settings.setup.materials.solid.create("vacuum") -vacuum.chemical_formula = "" -vacuum.thermal_conductivity.value = 0 -vacuum.absorption_coefficient.value = 0 -vacuum.refractive_index.value = 1 - -# --- Properties of fluff (see ref. [2]) --- -# Density: 1000 [kg m^-3] -# Specific heat capacity: 1050 [J kg^-1 K^-1] -# Thermal conductivity: 9.22e-4*(1 + 1.48*(temperature/350 K)^3) [W m^-1 K^-1] +vacuum = SolidMaterial.create( + solver, + name="vacuum", + thermal_conductivity=0 * W / (m * K), + absorption_coefficient=0, + refractive_index=1, +) -fluff = solver_session.settings.setup.materials.solid.create("fluff") -fluff.chemical_formula = "" -fluff.density.value = 1000 -fluff.specific_heat.value = 1050 +fluff = SolidMaterial.create( + solver, name="fluff", density=1000 * kg / m**3, specific_heat=1050 * J / (kg * K) +) fluff.thermal_conductivity.option = "expression" fluff.thermal_conductivity.expression = ( "9.22e-4[W m^-1 K^-1]*(1 + 1.48*(StaticTemperature/350[K])^3)" ) -# --- Properties of regolith (see ref. [2]) --- -# Density: 2000 [kg m^-3] -# Specific heat capacity: 1050 [J kg^-1 K^-1] -# Thermal conductivity: 9.30e-4*(1 + 0.73*(temperature/350 K)^3) [W m^-1 K^-1] - -regolith = solver_session.settings.setup.materials.solid.create("regolith") -regolith.chemical_formula = "" -regolith.density.value = 2000 -regolith.specific_heat.value = 1050 +regolith = SolidMaterial.create( + solver, name="regolith", density=2000 * kg / m**3, specific_heat=1050 * J / (kg * K) +) regolith.thermal_conductivity.option = "expression" regolith.thermal_conductivity.expression = ( "9.30e-4[W m^-1 K^-1]*(1 + 0.73*(StaticTemperature/350[K])^3)" @@ -396,12 +400,13 @@ def get_surf_mean_temp( # lander. This cell zone must be set to be a solid so that the fluid equations # are not solved there, then it must be assigned to the vacuum material. -cellzones = solver_session.settings.setup.cell_zone_conditions -cellzones.set_zone_type( +CellZoneCondition(solver).set_zone_type( zone_list=["geom-2_domain"], new_type="solid", ) -cellzones.solid["geom-2_domain"].material = "vacuum" + +vacuum_zone = SolidCellZone.get(solver, name="geom-2_domain") +vacuum_zone.general.material = vacuum ############################################################################### # Regolith boundary condition @@ -411,15 +416,9 @@ def get_surf_mean_temp( # used to represent the geothermal heat from the Moon's interior that heats # the regolith from the bottom. -# --- Regolith BC --- -# Thickness of layers: 0.02, 0.04, 0.08, 0.16, 0.32 [m] -# Heating at base: 0.031 [W m^-2] -# Surface absorptivity: 0.87 -# Surface emissivity: 0.97 +regolith_bc = WallBoundary.get(solver, name="regolith") -regolith_bc = solver_session.settings.setup.boundary_conditions.wall["regolith"] - -regolith_bc.thermal.q.value = 0.031 +regolith_bc.thermal.q = 0.031 * W / m**2 regolith_bc.thermal.planar_conduction = True regolith_bc.thermal.shell_conduction = [ { @@ -451,24 +450,23 @@ def get_surf_mean_temp( # The space boundary condition represents deep space and also acts as the # source of the Sun's illumination in the simulation. -# --- Set up space boundary condition --- -# Temperature: 3 [K] -# Emissivity: 1 -# Absorptivity: 1 -# Solar flux: 1414 [W m^-2] - -space_bc = solver_session.settings.setup.boundary_conditions.wall["space"] +space_bc = WallBoundary.get(solver, name="space") space_bc.thermal.thermal_bc = "Temperature" -space_bc.thermal.t.value = 3 -space_bc.thermal.material = "vacuum" +space_bc.thermal.t.value = 3 * K +space_bc.thermal.material = vacuum space_bc.radiation.mc_bsource_p = True -space_bc.radiation.direct_irradiation_settings.direct_irradiation["solar"] = 1414 -space_bc.radiation.diffuse_irradiation_settings.diffuse_fraction_band = { - "solar": 0, - "thermal-ir": 0, -} -space_bc.radiation.internal_emissivity_band = {"solar": 1, "thermal-ir": 1} +space_bc.radiation.direct_irradiation_settings.direct_irradiation.create( + "solar", value=1414 * W / m**2 +) +space_bc.radiation.diffuse_irradiation_settings.diffuse_fraction_band.create( + "solar", value=0 +) +space_bc.radiation.diffuse_irradiation_settings.diffuse_fraction_band.create( + "thermal-ir", value=0 +) +space_bc.radiation.internal_emissivity_band.create("solar", value=1) +space_bc.radiation.internal_emissivity_band.create("thermal-ir", value=1) ############################################################################### # Spacecraft walls boundary condition @@ -476,13 +474,7 @@ def get_surf_mean_temp( # The spacecraft is covered in reflective MLI (multilayer insulation) and heat # transfer through the aluminum shell can be simulated using shell conduction. -# --- Set up spacecraft shell boundary condition --- -# Thickness: 0.03 [m] -# Material: aluminum -# Absorptivity: 0.05 -# Emissivity: 0.05 - -sc_mli_bc = solver_session.settings.setup.boundary_conditions.wall["sc-mli"] +sc_mli_bc = WallBoundary.get(solver, name="sc-mli") sc_mli_bc.thermal.planar_conduction = True sc_mli_bc.thermal.shell_conduction = [ @@ -491,7 +483,8 @@ def get_surf_mean_temp( "material": "aluminum", }, ] -sc_mli_bc.radiation.internal_emissivity_band = {"solar": 0.05, "thermal-ir": 0.05} +sc_mli_bc.radiation.internal_emissivity_band.create("solar", value=0.05) +sc_mli_bc.radiation.internal_emissivity_band.create("thermal-ir", value=0.05) ############################################################################### # Spacecraft radiator boundary condition @@ -500,13 +493,7 @@ def get_surf_mean_temp( # walls, but the emissivity is left unset as it will be changed dynamically by # our PyFluent script depending on its temperature during the simulation. -# --- Set up spacecraft radiator boundary condition --- -# Thickness: 0.03 [m] -# Material: aluminum -# Absorptivity: 0.17 -# Emissivity: 0.09 below 273 K, 0.70 otherwise - -sc_rad_bc = solver_session.settings.setup.boundary_conditions.wall["sc-radiator"] +sc_rad_bc = WallBoundary.get(solver, name="sc-radiator") sc_rad_bc.thermal.planar_conduction = True sc_rad_bc.thermal.shell_conduction = [ @@ -515,7 +502,7 @@ def get_surf_mean_temp( "material": "aluminum", }, ] -sc_rad_bc.radiation.internal_emissivity_band = {"solar": 0.17} +sc_rad_bc.radiation.internal_emissivity_band.create("solar", value=0.17) ############################################################################### # Initialize simulation @@ -525,8 +512,8 @@ def get_surf_mean_temp( # definitions on them in the next step. The entire domain will be initialized # to a temperature of 230 K, or -43 °C. -sim_init = solver_session.settings.solution.initialization -sim_init.defaults["temperature"] = 230 +sim_init = Initialization(solver) +sim_init.defaults.temperature = 230 * K sim_init.initialize() ############################################################################### @@ -534,73 +521,79 @@ def get_surf_mean_temp( # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ # Create reports for the spacecraft's minimum, mean, and maximum temperatures. -surf_report_defs = solver_session.settings.solution.report_definitions.surface +report_defs = ReportDefinitions(solver) sc_surfs = ["sc-radiator", "sc-mli"] -surf_report_defs["sc-min-temp"] = { - "surface_names": sc_surfs, - "report_type": "surface-facetmin", - "field": "temperature", -} -surf_report_defs["sc-avg-temp"] = { - "surface_names": sc_surfs, - "report_type": "surface-facetavg", - "field": "temperature", -} -surf_report_defs["sc-max-temp"] = { - "surface_names": sc_surfs, - "report_type": "surface-facetmax", - "field": "temperature", -} - +sc_min_temp = report_defs.surface.create( + name="sc-min-temp", + surface_names=sc_surfs, + report_type="surface-facetmin", + field=VariableCatalog.TEMPERATURE, +) +sc_avg_temp = report_defs.surface.create( + name="sc-avg-temp", + surface_names=sc_surfs, + report_type="surface-facetavg", + field=VariableCatalog.TEMPERATURE, +) +sc_max_temp = report_defs.surface.create( + name="sc-max-temp", + surface_names=sc_surfs, + report_type="surface-facetmax", + field=VariableCatalog.TEMPERATURE, +) ############################################################################### # Regolith temperature reports # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~ # Create reports for the mean temperatures of each regolith layer. We will # store the report names for use later. -surf_report_defs = solver_session.settings.solution.report_definitions.surface - -# Loop over all regolith reports to set common properties -regolith_report_names = [] -for i in range(1, 5 + 1): - report_name = f"regolith-layer-{i}-temp" - surf_report_defs[report_name] = { - "report_type": "surface-facetavg", - "field": "temperature", - } - regolith_report_names.extend([report_name]) +regolith_reports = [ + report_defs.surface.create( + name=f"regolith-layer-{i}-temp", + report_type="surface-facetavg", + field=VariableCatalog.TEMPERATURE, + surface_names = [f"regolith{f'-{i-1}:{i}' if i > 1 else ''}"], + ) + for i in range(1, 5 + 1) +] -surf_report_defs["regolith-layer-1-temp"].surface_names = ["regolith"] -surf_report_defs["regolith-layer-2-temp"].surface_names = ["regolith-1:2"] -surf_report_defs["regolith-layer-3-temp"].surface_names = ["regolith-2:3"] -surf_report_defs["regolith-layer-4-temp"].surface_names = ["regolith-3:4"] -surf_report_defs["regolith-layer-5-temp"].surface_names = ["regolith-4:5"] ############################################################################### # Temperature report files # ~~~~~~~~~~~~~~~~~~~~~~~~ # Create temperature report files for post-processing. -surf_report_files = solver_session.settings.solution.monitor.report_files +monitor = Monitor(solver) +surf_report_files = monitor.report_files # Spacecraft temperatures -surf_report_files["sc-temps-rfile"] = { - "report_defs": ["flow-time", "sc-min-temp", "sc-avg-temp", "sc-max-temp"], -} +surf_report_files.create( + "sc-temps-rfile", + report_defs=[ + "flow-time", + "sc-min-temp", + "sc-avg-temp", + "sc-max-temp", + ], +) # Regolith temperatures -surf_report_files["regolith-temps-rfile"] = { - "report_defs": [*regolith_report_names, "flow-time"], -} +surf_report_files.create( + "regolith-temps-rfile", + report_defs=[ + *regolith_reports, + "flow-time", + ], +) ############################################################################### # Autosave # ~~~~~~~~ # Set the case to save only the data file at each timestep for post-processing. -autosave = solver_session.settings.file.auto_save +autosave = solver.settings.file.auto_save autosave.case_frequency = "if-mesh-is-modified" autosave.data_frequency = 1 @@ -613,7 +606,7 @@ def get_surf_mean_temp( # Turn off the convergence criteria pertaining to fluid flow as there is no # fluid flow in this simulation. Keep only the energy convergence criterion. -residuals = solver_session.settings.solution.monitor.residual.equations +residuals = monitor.residual.equations for criterion in ["continuity", "x-velocity", "y-velocity", "z-velocity"]: residuals[criterion].check_convergence = False @@ -622,10 +615,10 @@ def get_surf_mean_temp( ############################################################################### # Write case file # ~~~~~~~~~~~~~~~ -# Write the case file. Enable overwrite. +# Write the case file. -solver_session.settings.file.batch_options.confirm_overwrite = True -solver_session.settings.file.write( +write_case( + solver, file_name="lunar_lander_thermal.cas.h5", file_type="case", ) @@ -643,7 +636,7 @@ def get_surf_mean_temp( for i in range(n_steps): # Get current simulation time - t = solver_session.rp_vars("flow-time") + t = solver.rp_vars("flow-time") # Calculate sun vector sun_alt, sun_azm = calc_sun_vecs_for_moon( @@ -659,9 +652,8 @@ def get_surf_mean_temp( ) # Set beam direction - solver_session.settings.setup.boundary_conditions.wall[ - "space" - ].radiation.direct_irradiation_settings.beam_direction = [ + bcs = BoundaryCondition(solver) + bcs.wall["space"].radiation.direct_irradiation_settings.beam_direction = [ beam_x, beam_y, beam_z, @@ -670,27 +662,27 @@ def get_surf_mean_temp( # Calculate radiator mean temperature rad_mean_temp = get_surf_mean_temp( ["sc-radiator"], - solver_session, + solver, ) # Simulate closing louvers below 273 K by changing emissivity - radiation_emission = solver_session.settings.setup.boundary_conditions.wall[ - "sc-radiator" - ].radiation.internal_emissivity_band["thermal-ir"] + radiation_emission = bcs.wall["sc-radiator"].radiation.internal_emissivity_band[ + "thermal-ir" + ] if rad_mean_temp < 273: radiation_emission.value = 0.09 else: radiation_emission.value = 0.70 # Run simulation for 1 timestep - solver_session.settings.solution.run_calculation.calculate() + calculate(solver) ############################################################################### # Close Fluent # ~~~~~~~~~~~~ # Shut down the solver. -solver_session.exit() +solver.exit() ############################################################################### # Post-process @@ -729,7 +721,7 @@ def clean_col_names(df): # alphabetical character, implemented as negative lookarounds in a regular # expression. -root = Path(os.getcwd()) +root = Path.cwd() sep = r"(?`_. # sphinx_gallery_thumbnail_path = '_static/Single_Battery_Cell_4.png' +# +# .. _Reference: +# [3] Simulating a Single Battery Cell Using the MSMD Battery Model, `Ansys Fluent documentation​ `_. + +# sphinx_gallery_thumbnail_path = '_static/Single_Battery_Cell_4.png' diff --git a/examples/00-fluent/species_transport.py b/examples/00-fluent/species_transport.py index 15633ecf523..3349d846555 100644 --- a/examples/00-fluent/species_transport.py +++ b/examples/00-fluent/species_transport.py @@ -87,12 +87,17 @@ # sphinx_gallery_capture_repr = ('_repr_html_', '__repr__') # sphinx_gallery_thumbnail_path = '_static/species_transport/setup.png' -import os +from pathlib import Path + +from ansys.units import VariableCatalog import ansys.fluent.core as pyfluent +from ansys.units.common import K, m, Pa, W, s + +from ansys.fluent.core.generated.solver.settings_builtin_261 import Fluxes, General, Iterate, SurfaceIntegrals, WriteCase, WriteCaseData, write_case -solver_session = pyfluent.launch_fluent(dimension=2) -print(solver_session.get_fluent_version()) +solver = pyfluent.Solver.from_install(dimension=2) +print(solver.get_fluent_version()) # %% # Import some direct settings classes which will be used in the following sections. @@ -104,14 +109,20 @@ from ansys.fluent.core.solver import ( # noqa: E402 Contour, Energy, + Initialize, Mesh, MixtureMaterial, PressureOutlet, + RunCalculation, Species, Vector, VelocityInlet, Viscous, WallBoundary, + BoundaryCondition, + Methods, + Monitor, + Graphics, ) # %% @@ -121,9 +132,9 @@ # Download the mesh file and read it into the Fluent session. mesh_file = download_file( - "gascomb.msh.gz", "pyfluent/tutorials/species_transport", save_path=os.getcwd() + "gascomb.msh.gz", "pyfluent/tutorials/species_transport", save_path=Path.cwd() ) -solver_session.settings.file.read_mesh(file_name=mesh_file) +solver.settings.file.read_mesh(file_name=mesh_file) # %% # General Settings @@ -133,7 +144,7 @@ # Fluent will perform various checks on the mesh and will report the progress in the console. # Ensure that the reported minimum volume reported is a positive number. -solver_session.settings.mesh.check() +solver.settings.mesh.check() # %% # Scale the mesh and check it again. @@ -144,17 +155,17 @@ # # We should check the mesh after we manipulate it (scale, convert to polyhedra, merge, separate, fuse, add zones, or smooth and swap). # This will ensure that the quality of the mesh has not been compromised. - -solver_session.settings.mesh.scale(x_scale=0.001, y_scale=0.001) -solver_session.settings.mesh.check() +mesh = Mesh(solver) +mesh.scale(x_scale=0.001, y_scale=0.001) +mesh.check() # %% # Display the mesh in Fluent and save the image to a file to examine locally. -mesh = Mesh(solver_session, new_instance_name="mesh") +mesh = Mesh.create(solver, name="mesh") mesh.surfaces_list = mesh.surfaces_list.allowed_values() mesh.display() -graphics = solver_session.settings.results.graphics +graphics = Graphics(solver) graphics.views.auto_scale() if graphics.picture.use_window_resolution.is_active(): graphics.picture.use_window_resolution = False @@ -173,34 +184,61 @@ # %% # Inspect the available options for the two-dimensional space setting and set it to axisymmetric. -solver_session.settings.setup.general.solver.two_dim_space.allowed_values() +solver_ = General(solver).solver + +solver_.two_dim_space.allowed_values() # %% -solver_session.settings.setup.general.solver.two_dim_space = "axisymmetric" +solver_.two_dim_space = "axisymmetric" # %% # Models # ^^^^^^ # Enable heat transfer by enabling the energy model. -Energy(solver_session).enabled = True +Energy(solver).enabled = True # %% # Inspect the default settings for the k-ω SST viscous model. -Viscous(solver_session).print_state() +Viscous(solver).print_state() + + +# %% +# Materials +# ^^^^^^^^^ +# In this step, we will examine the default settings for the mixture material. +# This tutorial uses mixture properties copied from the Ansys Fluent database. +# In general, we can modify these or create our own mixture properties for our specific problem as necessary. + +# %% +# Print some specific properties of the mixture material (methane-air). +# We avoid printing the entire state of the mixture material to keep the output concise. + +mixture_material = MixtureMaterial(solver, name="methane-air") +print(f"Species list: {mixture_material.species.volumetric_species.get_object_names()}") +print(f"Reactions option: {mixture_material.reactions.option()}") +print(f"Density option: {mixture_material.density.option()}") +print(f"Cp (specific heat) option: {mixture_material.specific_heat.option()}") +print(f"Thermal conductivity value: {mixture_material.thermal_conductivity.value()}") +print(f"Viscosity value: {mixture_material.viscosity.value()}") +if solver.get_fluent_version() < FluentVersion.v252: + print(f"Mass diffusivity value: {mixture_material.mass_diffusivity.value()}") +else: + print( + f"Mass diffusivity value: {mixture_material.mass_diffusivity.constant_mass_diffusivity()}" + ) # %% # Inspect the available options for the species model and set it to species transport. -species = Species(solver_session) +species = Species(solver) species.model.option.allowed_values() # %% -species.model.option = "species-transport" - +species.model.option = species.model.option.SPECIES_TRANSPORT # %% # Inspect the species model settings. @@ -221,7 +259,7 @@ # The chemical species in the system and their physical and thermodynamic properties are defined by our selection of the mixture material. # We can alter the mixture material selection or modify the mixture material properties using the material settings (see `Materials`_). -species.model.material = "methane-air" +species.model.material = mixture_material # %% # Set the turbulence-chemistry interaction model to eddy-dissipation. @@ -235,31 +273,6 @@ species.print_state() -# %% -# Materials -# ^^^^^^^^^ -# In this step, we will examine the default settings for the mixture material. -# This tutorial uses mixture properties copied from the Ansys Fluent database. -# In general, we can modify these or create our own mixture properties for our specific problem as necessary. - -# %% -# Print some specific properties of the mixture material (methane-air). -# We avoid printing the entire state of the mixture material to keep the output concise. - -mixture_material = MixtureMaterial(solver_session, name="methane-air") -print(f"Species list: {mixture_material.species.volumetric_species.get_object_names()}") -print(f"Reactions option: {mixture_material.reactions.option()}") -print(f"Density option: {mixture_material.density.option()}") -print(f"Cp (specific heat) option: {mixture_material.specific_heat.option()}") -print(f"Thermal conductivity value: {mixture_material.thermal_conductivity.value()}") -print(f"Viscosity value: {mixture_material.viscosity.value()}") -if solver_session.get_fluent_version() < FluentVersion.v252: - print(f"Mass diffusivity value: {mixture_material.mass_diffusivity.value()}") -else: - print( - f"Mass diffusivity value: {mixture_material.mass_diffusivity.constant_mass_diffusivity()}" - ) - # %% # Boundary Conditions # ^^^^^^^^^^^^^^^^^^^ @@ -267,9 +280,7 @@ # # *The symmetry zone must be converted to an axis to prevent numerical difficulties where the radius reduces to zero.* -solver_session.settings.setup.boundary_conditions.set_zone_type( - zone_list=["symmetry-5"], new_type="axis" -) +BoundaryCondition(solver).set_zone_type(zone_list=["symmetry-5"], new_type="axis") # %% # Set the boundary conditions for the air inlet (velocity-inlet-8). @@ -278,9 +289,7 @@ # # *This name is more descriptive for the zone than velocity-inlet-8.* -solver_session.settings.setup.boundary_conditions.velocity_inlet[ - "velocity-inlet-8" -].rename("air-inlet") +VelocityInlet.get(solver, name="velocity-inlet-8").rename("air-inlet") # %% # Set the following boundary conditions for the air-inlet: @@ -295,12 +304,12 @@ # # * Species mass fraction for o2: 0.23 -air_inlet = VelocityInlet(solver_session, name="air-inlet") -air_inlet.momentum.velocity_magnitude = 0.5 +air_inlet = VelocityInlet.get(solver, name="air-inlet") +air_inlet.momentum.velocity_magnitude = 0.5 * m / s air_inlet.turbulence.turbulence_specification = "Intensity and Hydraulic Diameter" air_inlet.turbulence.turbulent_intensity = 0.1 -air_inlet.turbulence.hydraulic_diameter = 0.44 -air_inlet.thermal.temperature = 300 +air_inlet.turbulence.hydraulic_diameter = 0.44 * m +air_inlet.thermal.temperature = 300 * K air_inlet.species.species_mass_fraction["o2"] = 0.23 # %% @@ -315,9 +324,7 @@ # # *This name is more descriptive for the zone than velocity-inlet-6.* -solver_session.settings.setup.boundary_conditions.velocity_inlet[ - "velocity-inlet-6" -].rename("fuel-inlet") +VelocityInlet.get(solver, name="velocity-inlet-6").rename("fuel-inlet") # %% # Set the following boundary conditions for the fuel-inlet: @@ -332,12 +339,12 @@ # # * Species mass fraction for ch4: 1 -fuel_inlet = VelocityInlet(solver_session, name="fuel-inlet") -fuel_inlet.momentum.velocity_magnitude = 80 +fuel_inlet = VelocityInlet(solver, name="fuel-inlet") +fuel_inlet.momentum.velocity_magnitude = 80 * m / s fuel_inlet.turbulence.turbulence_specification = "Intensity and Hydraulic Diameter" fuel_inlet.turbulence.turbulent_intensity = 0.1 -fuel_inlet.turbulence.hydraulic_diameter = 0.01 -fuel_inlet.thermal.temperature = 300 +fuel_inlet.turbulence.hydraulic_diameter = 0.01 * m +fuel_inlet.thermal.temperature = 300 * K fuel_inlet.species.species_mass_fraction["ch4"] = 1 # %% @@ -346,27 +353,17 @@ fuel_inlet.print_state() # %% -# Set the following boundary conditions for the exit boundary (pressure-outlet-9): -# -# * Gauge pressure: 0 Pa -# -# * Backflow turbulence intensity: 10% -# -# * Backflow Hydraulic diameter: 0.45 m -# -# * Backflow total temperature: 300 K -# -# * Backflow species mass fraction for o2: 0.23 +# Set the boundary conditions for the exit boundary (pressure-outlet-9): # # *The Backflow values in the pressure outlet boundary condition are utilized only when backflow occurs at the pressure outlet. # Always assign reasonable values because backflow may occur during intermediate iterations and could affect the solution stability.* -pressure_outlet = PressureOutlet(solver_session, name="pressure-outlet-9") -pressure_outlet.momentum.gauge_pressure = 0 +pressure_outlet = PressureOutlet.get(solver, name="pressure-outlet-9") +pressure_outlet.momentum.gauge_pressure = 0 * Pa pressure_outlet.turbulence.turbulence_specification = "Intensity and Hydraulic Diameter" pressure_outlet.turbulence.backflow_turbulent_intensity = 0.1 -pressure_outlet.turbulence.backflow_hydraulic_diameter = 0.45 -pressure_outlet.thermal.backflow_total_temperature = 300 +pressure_outlet.turbulence.backflow_hydraulic_diameter = 0.45 * m +pressure_outlet.thermal.backflow_total_temperature = 300 * K pressure_outlet.species.backflow_species_mass_fraction["o2"] = 0.23 # %% @@ -381,16 +378,14 @@ # # *This name is more descriptive for the zone than wall-7.* -solver_session.settings.setup.boundary_conditions.wall["wall-7"].rename("outer-wall") +WallBoundary.get(solver, name="wall-7").rename("outer-wall") # %% # Set the following boundary conditions for the outer-wall: -# -# * Temperature: 300 K -outer_wall = WallBoundary(solver_session, name="outer-wall") +outer_wall = WallBoundary.get(solver, name="outer-wall") outer_wall.thermal.thermal_condition = "Temperature" -outer_wall.thermal.temperature = 300 +outer_wall.thermal.temperature = 300 * K # %% # Verify the state of thermal properties of the outer-wall boundary condition after the changes. @@ -404,16 +399,16 @@ # # *This name is more descriptive for the zone than wall-2.* -solver_session.settings.setup.boundary_conditions.wall["wall-2"].rename("nozzle") +WallBoundary.get(solver, name="wall-2").rename("nozzle") # %% # Set the following boundary conditions for the nozzle for adiabatic wall conditions: # # * Heat flux: 0 :math:`W/m^2` -nozzle = WallBoundary(solver_session, name="nozzle") -nozzle.thermal.thermal_condition = "Heat Flux" -nozzle.thermal.heat_flux = 0 +nozzle = WallBoundary.get(solver, name="nozzle") +nozzle.thermal.thermal_condition = nozzle.thermal.thermal_condition.HEAT_FLUX +nozzle.thermal.heat_flux = 0 * W * m ** -2 # %% # Verify the state of thermal properties of the nozzle boundary condition after the changes. @@ -427,27 +422,27 @@ # # Inspect the solution methods settings. -solver_session.settings.solution.methods.print_state() +Methods(solver).print_state() # %% # Ensure that plot is enabled in residual monitor options. -solver_session.settings.solution.monitor.residual.options.plot() +Monitor(solver).residual.options.plot() # %% # Initialize the field variables. -solver_session.settings.solution.initialization.hybrid_initialize() +Initialize(solver).hybrid_initialize() # %% # Save the case file (gascomb1.cas.h5). -solver_session.settings.file.write_case(file_name="gascomb1.cas.h5") +WriteCase(file_name="gascomb1.cas.h5") # %% # Run the calculation for 200 iterations. -solver_session.settings.solution.run_calculation.iterate(iter_count=200) +Iterate(solver, iter_count=200) # %% # Set time scale factor to 5. @@ -455,19 +450,16 @@ # *The Time Scale Factor allows us to further manipulate the computed time step size calculated by Fluent. # Larger time steps can lead to faster convergence. However, if the time step is too large it can lead to solution instability.* -solver_session.settings.solution.run_calculation.pseudo_time_settings.time_step_method.time_step_size_scale_factor = ( - 5 -) +RunCalculation(solver).pseudo_time_settings.time_step_method.time_step_size_scale_factor = 5 # %% # Run the calculation for 200 iterations. -solver_session.settings.solution.run_calculation.iterate(iter_count=200) +Iterate(solver, iter_count=200) # %% # Save the case and data files (gascomb1.cas.h5 and gascomb1.dat.h5). - -solver_session.settings.file.write_case_data(file_name="gascomb1.cas.h5") +WriteCaseData(solver, file_name="gascomb1.cas.h5") # %% # Postprocessing @@ -477,13 +469,12 @@ # Report the total sensible heat flux. # We shall use wildcards to specify all zones. -solver_session.settings.results.report.fluxes.get_heat_transfer_sensible(zones="*") +Fluxes.get_heat_transfer_sensible(zones="*") # %% # Display filled contours of temperature and save the image to a file. -contour1 = Contour(solver_session, new_instance_name="contour-temp") -contour1.field = "temperature" +contour1 = Contour.create(solver, name="contour-temp", field = VariableCatalog.TEMPERATURE) contour1.surfaces_list = contour1.surfaces_list.allowed_values() contour1.colorings.banded = True contour1.display() @@ -502,8 +493,7 @@ # %% # Display velocity vectors and save the image to a file. -vector1 = Vector(solver_session, new_instance_name="vector-vel") -vector1.surfaces_list = ["interior-4"] +vector1 = Vector.create(solver, name="vector-vel", surfaces_list = ["interior-4"]) vector1.options.scale = 0.01 vector1.vector_opt.fixed_length = True @@ -529,8 +519,7 @@ # %% # Display filled contours of mass fraction of :math:`CH_4` and save the image to a file. -contour2 = Contour(solver_session, new_instance_name="contour-ch4-mass-fraction") -contour2.field = "ch4" +contour2 = Contour.create(solver, name="contour-ch4-mass-fraction", field = "ch4") contour2.surfaces_list = contour2.surfaces_list.allowed_values() contour2.display() graphics.views.auto_scale() @@ -547,8 +536,7 @@ # %% # Display filled contours of mass fraction of :math:`O_2` and save the image to a file. -contour3 = Contour(solver_session, new_instance_name="contour-o2-mass-fraction") -contour3.field = "o2" +contour3 = Contour.create(solver, name="contour-o2-mass-fraction", field = "o2") contour3.surfaces_list = contour3.surfaces_list.allowed_values() contour3.display() graphics.views.auto_scale() @@ -564,8 +552,7 @@ # %% # Display filled contours of mass fraction of :math:`CO_2` and save the image to a file. -contour4 = Contour(solver_session, new_instance_name="contour-co2-mass-fraction") -contour4.field = "co2" +contour4 = Contour.create(solver, name="contour-co2-mass-fraction", field = "co2") contour4.surfaces_list = contour4.surfaces_list.allowed_values() contour4.display() graphics.views.auto_scale() @@ -581,8 +568,7 @@ # %% # Display filled contours of mass fraction of :math:`H_2O` and save the image to a file. -contour5 = Contour(solver_session, new_instance_name="contour-h2o-mass-fraction") -contour5.field = "h2o" +contour5 = Contour.create(solver, name="contour-h2o-mass-fraction", field = "h2o") contour5.surfaces_list = contour5.surfaces_list.allowed_values() contour5.display() graphics.views.auto_scale() @@ -604,7 +590,7 @@ # # *The mass-averaged temperature at the exit is approximately 1840 K.* -solver_session.settings.results.report.surface_integrals.get_mass_weighted_avg( +SurfaceIntegrals(solver).get_mass_weighted_avg( report_of="temperature", surface_names=["pressure-outlet-9"] ) @@ -617,20 +603,20 @@ # # *The Area-Weighted Average field will show that the exit velocity is approximately 3.37 m/s.* -solver_session.settings.results.report.surface_integrals.get_area_weighted_avg( +SolverIntegrals(solver).get_area_weighted_avg( report_of="velocity-magnitude", surface_names=["pressure-outlet-9"] ) # %% # Save the case file (gascomb1.cas.h5). -solver_session.settings.file.write_case(file_name="gascomb1.cas.h5") +write_case(solver, file_name="gascomb1.cas.h5") # %% # Close Fluent # ^^^^^^^^^^^^ -solver_session.exit() +solver.exit() # %% # Summary diff --git a/examples/00-fluent/steady_vortex.py b/examples/00-fluent/steady_vortex.py index 2f88d31ebaa..83006075481 100644 --- a/examples/00-fluent/steady_vortex.py +++ b/examples/00-fluent/steady_vortex.py @@ -79,12 +79,12 @@ # sphinx_gallery_capture_repr = ('_repr_html_', '__repr__') # sphinx_gallery_thumbnail_path = '_static/steady_vortex/steady_vortex_setup.png' -import os +from pathlib import Path import imageio.v2 as imageio import ansys.fluent.core as pyfluent -from ansys.fluent.core import Dimension, FluentMode, Precision +from ansys.fluent.core import Dimension, Precision from ansys.fluent.core.examples import download_file from ansys.fluent.core.solver import ( # noqa: E402 LIC, @@ -93,6 +93,7 @@ Contour, General, Graphics, + FluidMaterial, Initialization, IsoClip, IsoSurface, @@ -100,12 +101,18 @@ Mesh, Methods, Models, + Multiphase, NamedExpression, PlaneSurface, - RunCalculation, Scene, + Viscous, WallBoundary, + read_case, + CalculationActivity, + iterate, + write_case_data, ) +from ansys.units.common import m, s # %% # Launch Fluent @@ -113,14 +120,13 @@ # # Launch Fluent in 3D double precision solver mode. -solver_session = pyfluent.launch_fluent( - mode=FluentMode.SOLVER, +solver = pyfluent.Solver.from_install( dimension=Dimension.THREE, precision=Precision.DOUBLE, cleanup_on_exit=True, - cwd=os.getcwd(), + cwd=Path.cwd(), ) -print(solver_session.get_fluent_version()) # Print the Fluent version +print(solver.get_fluent_version()) # Print the Fluent version pyfluent.set_console_logging_level("INFO") # Set the console logging level # %% @@ -132,7 +138,7 @@ vortex_mesh = download_file( "vortex-mixingtank.msh.h5", "pyfluent/examples/Steady-Vortex-VOF", - save_path=os.getcwd(), + save_path=Path.cwd(), ) # %% @@ -141,7 +147,7 @@ # # Define constants. -g = 9.81 # m/s^2 +g = 9.81 * m / s**2 # %% # @@ -150,25 +156,22 @@ # # Import the mesh file into the Fluent session. -solver_session.settings.file.read_case(file_name=vortex_mesh) +read_case(solver, file_name=vortex_mesh) # %% # Display the mesh in Fluent and save the image to a file to examine locally. # Create a middle plane to display the mesh -y_mid_plane = PlaneSurface(solver_session, new_instance_name="y_mid_plane") -y_mid_plane.method = "zx-plane" -y_mid_plane.y = 0 +y_mid_plane = PlaneSurface.create(solver, name="y_mid_plane", method="zx-plane", y=0) y_mid_plane.display() # Define and display the mesh -mesh = Mesh(solver_session, new_instance_name="mesh") -mesh.surfaces_list = y_mid_plane.name() +mesh = Mesh.create(solver, name="mesh", surfaces_list=y_mid_plane.name()) mesh.options.edges = True mesh.display() # Create Graphics object to save the mesh image -graphics = Graphics(solver_session) +graphics = Graphics(solver) graphics.views.auto_scale() if graphics.picture.use_window_resolution.is_active(): graphics.picture.use_window_resolution = False @@ -193,28 +196,27 @@ # # Set gravity -general_settings = General(solver_session) -general_settings.operating_conditions.gravity.enable = True -general_settings.operating_conditions.gravity.components = [0.0, 0.0, -g] +general = General(solver) +general.operating_conditions.gravity.enable = True +general.operating_conditions.gravity.components = [0.0, 0.0, -g] # %% # Copy Materials from Fluent Database # ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ # -# Copy water liquid materials from the Fluent database. +# Copy liquid water material from the Fluent database and get a reference to air material (it's predefined in Fluent). -materials = Materials(solver_session) -materials.database.copy_by_name(type="fluid", name="water-liquid") +water = Materials(solver).database.copy_by_name(type="fluid", name="water-liquid") +air = FluidMaterial.get(solver, name="air") # %% # Define Named Expression for Agitation Speed # ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ # # Create a named expression for the agitation speed and specify as an input parameter. -stirring_speed = NamedExpression(solver_session, new_instance_name="stirring_speed") - -stirring_speed.definition = "240 [rev min^-1]" -stirring_speed.input_parameter = True +stirring_speed = NamedExpression.create( + solver, name="stirring_speed", definition="240 [rev min^-1]", input_parameter=True +) # %% # MRF zone parameters @@ -222,11 +224,11 @@ # # Define MRF zone parameters for the mrf cell zone. -fluid_cell_zone = CellZoneCondition(solver_session, name="mrf") -fluid_cell_zone.reference_frame.frame_motion = True -fluid_cell_zone.reference_frame.reference_frame_axis_origin = [0, 0, 0] -fluid_cell_zone.reference_frame.reference_frame_axis_direction = [0, 0, 1] -fluid_cell_zone.reference_frame.mrf_omega.value = "stirring_speed" +reference_frame = CellZoneCondition(solver, name="mrf").reference_frame +reference_frame.frame_motion = True +reference_frame.reference_frame_axis_origin = (0, 0, 0) +reference_frame.reference_frame_axis_direction = (0, 0, 1) +reference_frame.mrf_omega.value = "stirring_speed" # %% # Rotating Wall BC parameters @@ -234,11 +236,11 @@ # # Define the rotating wall boundary condition for the shaft. -wall_boundary = WallBoundary(solver_session, name="shaft_tank") +wall_boundary = WallBoundary(solver, name="shaft_tank") wall_boundary.momentum.wall_motion = "Moving Wall" wall_boundary.momentum.relative = False wall_boundary.momentum.rotating = True -wall_boundary.momentum.rotation_axis_direction = [0, 0, 1] +wall_boundary.momentum.rotation_axis_direction = (0, 0, 1) wall_boundary.momentum.rotation_speed = "stirring_speed" # %% @@ -246,27 +248,31 @@ # ^^^^^^^^^^^^^^^^^^^^^^^ # # Enable the VOF multiphase model and update the curvature correction setting for the viscous model. -model_setup = Models(solver_session) -model_setup.multiphase.model = "vof" -model_setup.multiphase.vof_parameters.vof_formulation = "implicit" -model_setup.multiphase.vof_parameters.vof_cutoff = 1e-06 -model_setup.multiphase.advanced_formulation.implicit_body_force = True - -model_setup.viscous.options.curvature_correction = True - -solution_methods = Methods(solver_session) -solution_methods.multiphase_numerics.solution_stabilization.execute_settings_optimization = ( - True -) -solution_methods.multiphase_numerics.solution_stabilization.execute_advanced_stabilization = ( - True -) +model_setup = Models(solver) +multiphase = Multiphase(solver) +multiphase.model = "vof" +multiphase.vof_parameters.vof_formulation = "implicit" +multiphase.vof_parameters.vof_cutoff = 1e-06 +multiphase.advanced_formulation.implicit_body_force = True +model_setup.multiphase = multiphase + +viscous = Viscous(solver) +viscous.options.curvature_correction = True +model_setup.viscous = viscous + +solution_methods = Methods(solver) +solution_methods.multiphase_numerics.solution_stabilization.execute_settings_optimization = True +solution_methods.multiphase_numerics.solution_stabilization.execute_advanced_stabilization = True # Change phase names -solver_session.tui.define.phases.set_domain_properties.change_phases_names( - "water", "air" -) -general_settings.solver.time = "steady" # steady solver +# TODO check +primary_phase = multiphase.phases["phase-1"] +primary_phase.name = "water" +primary_phase.material = water +secondary_phase = multiphase.phases["phase-2"] +secondary_phase.name = "air" +secondary_phase.material = air +general.solver.time = "steady" # steady solver # %% # Define Initial Conditions @@ -282,29 +288,24 @@ # the tank's minimum height coordinate and Z-max to 0.19 m. Utilize the minimum and maximum X & Y # values to ensure cells across the entire tank diameter are included. -solution_initialization = Initialization(solver_session) -solution_initialization.reference_frame = "absolute" -solution_initialization.defaults["k"] = 0.001 -solution_initialization.localized_turb_init.enabled = False +initialization = Initialization(solver) +initialization.reference_frame = "absolute" +initialization.defaults["k"] = 0.001 +initialization.localized_turb_init.enabled = False -solver_session.settings.solution.cell_registers.create(name="liquid_patch") -cell_register = CellRegister(solver_session, name="liquid_patch") -cell_register.type = { - "option": "hexahedron", - "hexahedron": { - "inside": True, - "max_point": [100.0, 100.0, 0.19], - "min_point": [-100.0, -100.0, -100.0], - }, -} +cell_register = CellRegister(solver, new_instance_name="liquid_patch") +cell_register.type.option = "hexahedron" +cell_register.type.hexahedron.inside = True +cell_register.type.hexahedron.max_point = (100.0, 100.0, 0.19) +cell_register.type.hexahedron.min_point = (-100.0, -100.0, -100.0) -solution_initialization.initialize() +initialization.initialize() # Patch the water volume fraction in the defined cell register to set the initial # liquid region in the tank. # "mp" refers to the volume fraction of the primary phase (here water). # Setting value=1 fills the patch region entirely with water. -solution_initialization.patch.calculate_patch( +initialization.patch.calculate_patch( domain="water", cell_zones=[], registers=["liquid_patch"], @@ -322,117 +323,100 @@ # e.g., to visualize the free surface and wetted walls and dry walls. # Free surface iso-surface -solver_session.settings.results.surfaces.iso_surface.create(name="freesurface") -freesurface = IsoSurface(solver_session, name="freesurface") -freesurface.field = "water-vof" -freesurface.iso_values = [0.5] +free_surface = IsoSurface.create( + solver, name="freesurface", field="water-vof", iso_values=[0.5] * m +) # Wetted wall and dry wall iso-clips -solver_session.settings.results.surfaces.iso_clip.create(name="wet_wall") -wet_wall = IsoClip(solver_session, name="wet_wall") -wet_wall.field = "water-vof" -wet_wall.range = { - "minimum": 0.5, - "maximum": 1.0, -} -wet_wall.surfaces = ["wall_tank"] - - -solver_session.settings.results.surfaces.iso_clip.create(name="dry_wall") -dry_wall = IsoClip(solver_session, name="dry_wall") -dry_wall.field = "water-vof" -dry_wall.range = { - "minimum": 0.0, - "maximum": 0.499, -} -dry_wall.surfaces = ["wall_tank"] +wet_wall = IsoClip.create( + solver, name="wet_wall", field="water-vof", surfaces=["wall_tank"] +) +wet_wall.range.minimum = 0.5 +wet_wall.range.maximum = 1.0 + + +dry_wall = IsoClip.create( + solver, name="dry_wall", field="water-vof", surfaces=["wall_tank"] +) +dry_wall.range.minimum = 0.0 +dry_wall.range.maximum = 0.499 # Meshes -internal_comp_mesh = Mesh(solver_session, new_instance_name="internals") -internal_comp_mesh.surfaces_list = [ - "wall_impeller", - "shaft_mrf", - "shaft_tank", -] +internal_comp_mesh = Mesh.create( + solver, + name="internals", + surfaces_list=[ + "wall_impeller", + "shaft_mrf", + "shaft_tank", + ], +) internal_comp_mesh.surfaces_list() # dry wall -dry_wall_comp_mesh = Mesh(solver_session, new_instance_name="drywall") -dry_wall_comp_mesh.surfaces_list = ["dry_wall"] +dry_wall_comp_mesh = Mesh.create(solver, name="drywall", surfaces_list=[dry_wall]) dry_wall_comp_mesh.surfaces_list() # wet wall -wet_wall_comp_mesh = Mesh(solver_session, new_instance_name="wetwall") -wet_wall_comp_mesh.surfaces_list = ["wet_wall"] +wet_wall_comp_mesh = Mesh.create(solver, name="wetwall", surfaces_list=[wet_wall]) wet_wall_comp_mesh.surfaces_list() wet_wall_comp_mesh.coloring.option = "manual" wet_wall_comp_mesh.coloring.manual.faces = "pastel cyan" # liquid level -liquidlevel_comp_mesh = Mesh(solver_session, new_instance_name="liquidlevel") -liquidlevel_comp_mesh.surfaces_list = ["freesurface"] +liquidlevel_comp_mesh = Mesh.create( + solver, name="liquidlevel", surfaces_list=[freesurface] +) liquidlevel_comp_mesh.surfaces_list() liquidlevel_comp_mesh.coloring.option = "manual" liquidlevel_comp_mesh.coloring.manual.faces = "pastel cyan" # Scenes -vortex_scene = Scene(solver_session, new_instance_name="scene-1") -vortex_scene.graphics_objects.add(name="liquidlevel") -vortex_scene.graphics_objects.add(name="drywall") -vortex_scene.graphics_objects.add(name="wetwall") -vortex_scene.graphics_objects.add(name="internals") - -solver_session.settings.results.scene["scene-1"] = { - "graphics_objects": { - "liquidlevel": { - "transparency": 50, - "name": "tank", - "colormap_position": 0, - "colormap_left": 0.0, - "colormap_bottom": 0.0, - "colormap_width": 0.0, - "colormap_height": 0.0, - }, - "internals": { - "transparency": 35, - "name": "internals", - "colormap_position": 0, - "colormap_left": 0.0, - "colormap_bottom": 0.0, - "colormap_width": 0.0, - "colormap_height": 0.0, - }, - "drywall": { - "transparency": 75, - "name": "fs", - "colormap_position": 0, - "colormap_left": 0.0, - "colormap_bottom": 0.0, - "colormap_width": 0.0, - "colormap_height": 0.0, - }, - "wetwall": { - "transparency": 75, - "name": "wetwall", - "colormap_position": 0, - "colormap_left": 0.0, - "colormap_bottom": 0.0, - "colormap_width": 0.0, - "colormap_height": 0.0, - }, - } -} +vortex_scene = Scene.create(solver, name="scene-1") +liquid_gobj = vortex_scene.graphics_objects.add(name=liquidlevel_comp_mesh.name()) +liquid_gobj.transparency = 50 +liquid_gobj.color_map.position = 0 +liquid_gobj.color_map.left = 0.0 +liquid_gobj.color_map.bottom = 0.0 +liquid_gobj.color_map.width = 0.0 +liquid_gobj.color_map.height = 0.0 + +internal_gobj = vortex_scene.graphics_objects.add(name=internal_comp_mesh.name()) +internal_gobj.transparency = 35 +internal_gobj.color_map.position = 0 +internal_gobj.color_map.left = 0.0 +internal_gobj.color_map.bottom = 0.0 +internal_gobj.color_map.width = 0.0 +internal_gobj.color_map.height = 0.0 + +dry_gobj = vortex_scene.graphics_objects.add(name=dry_wall_comp_mesh.name()) +dry_gobj.transparency = 75 +dry_gobj.color_map.position = 0 +dry_gobj.color_map.left = 0.0 +dry_gobj.color_map.bottom = 0.0 +dry_gobj.color_map.width = 0.0 +dry_gobj.color_map.height = 0.0 + +wet_gobj = vortex_scene.graphics_objects.add(name=wet_wall_comp_mesh.name()) +wet_gobj.transparency = 75 +wet_gobj.color_map.position = 0 +wet_gobj.color_map.left = 0.0 +wet_gobj.color_map.bottom = 0.0 +wet_gobj.color_map.width = 0.0 +wet_gobj.color_map.height = 0.0 # Contour plot on Y-Mid plane -solver_session.settings.results.surfaces.iso_surface.create(name="ymid") -y_mid_iso_surface = IsoSurface(solver_session, name="ymid") -y_mid_iso_surface.field = "y-coordinate" -y_mid_iso_surface.iso_values = [0] - -volume_fraction_contour = Contour(solver_session, new_instance_name="contour-1") -volume_fraction_contour.surfaces_list = y_mid_iso_surface.name() -volume_fraction_contour.field = "water-vof" +y_mid_iso_surface = IsoSurface.create( + solver, name="ymid", field="y-coordinate", iso_values=[0] * m +) + +volume_fraction_contour = Contour.create( + solver, + name="contour-1", + surfaces_list=y_mid_iso_surface.name(), + field="water-vof", +) volume_fraction_contour.surfaces_list() volume_fraction_contour.display() @@ -456,28 +440,22 @@ # Animation Setup -solver_session.settings.solution.calculation_activity.solution_animations.create( - "animation-2" +CalculationActivity(solver).solution_animations.create( + name="animation-2", + animate_on="scene-1", + frequency=10, + storage_type="png", + view="top", ) -solver_session.settings.solution.calculation_activity.solution_animations[ - "animation-2" -] = { - "animate_on": "scene-1", - "frequency": 10, - "storage_type": "png", - "view": "top", -} # %% # Save Initial Files & Run Calculation # ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ # # Save the initial case file and run the calculation for 500 iterations. -solver_session.settings.file.write_case_data(file_name="vortex_init.cas.h5") +write_case_data(solver, file_name="vortex_init.cas.h5") -run_calculation = RunCalculation(solver_session) -run_calculation.iter_count = 50 # Iteration count keep it 50 for demo only purpose -run_calculation.calculate() +iterate(solver, iter_count=50) # Iteration count keep it 50 for demo only purpose # %% # LIC Visualization @@ -485,12 +463,15 @@ # # Set up the LIC (Line Integral Convolution) visualization for the midplane. -lic_visualization = LIC(solver_session, new_instance_name="lic-1") -lic_visualization.surfaces_list = y_mid_plane.name() -lic_visualization.field = "velocity-magnitude" -lic_visualization.lic_image_filter = "Strong Sharpen" -lic_visualization.lic_intensity_factor = 10 -lic_visualization.texture_size = 10 +lic_visualization = LIC.create( + solver, + name="lic-1", + surfaces_list=y_mid_plane.name(), + field="velocity-magnitude", + lic_image_filter="Strong Sharpen", + lic_intensity_factor=10, + texture_size=10, +) lic_visualization.display() graphics.views.restore_view(view_name="top") @@ -534,14 +515,14 @@ # *Steady vortex shape in the stirred tank.* # Save final case and data files -solver_session.settings.file.write_case_data(file_name="vortex_final.cas.h5") +write_case_data(solver, file_name="vortex_final.cas.h5") # %% # Close Fluent # ^^^^^^^^^^^^ # # Exit the Fluent session. -solver_session.exit() +solver.exit() # %% # Generate GIF Animation: Vortex Formation @@ -554,12 +535,7 @@ # Install imageio package if not already installed. You can install it via pip: # `pip install imageio` -png_dir = os.getcwd() -images = [] -for file_name in sorted(os.listdir(png_dir)): - if file_name.startswith("animation") and file_name.endswith(".png"): - file_path = os.path.join(png_dir, file_name) - images.append(imageio.imread(file_path)) +images = list(map(imageio.imread, sorted(Path.cwd().glob("animation*.png")))) imageio.mimsave(uri="vortex.gif", ims=images, duration=0.2) diff --git a/examples/00-fluent/transient_compressible_nozzle_workflow.py b/examples/00-fluent/transient_compressible_nozzle_workflow.py index b8b7db7fe7b..7f3b1189327 100644 --- a/examples/00-fluent/transient_compressible_nozzle_workflow.py +++ b/examples/00-fluent/transient_compressible_nozzle_workflow.py @@ -66,16 +66,16 @@ # Importing the following classes offer streamlined access to key solver settings, # eliminating the need to manually browse through the full settings structure. -import os +from pathlib import Path import platform import ansys.fluent.core as pyfluent from ansys.fluent.core import examples +from ansys.fluent.core.generated.solver.settings_builtin_261 import BoundaryCondition from ansys.fluent.core.solver import ( - BoundaryConditions, - CellRegisters, Contour, Controls, + FluidMaterial, General, Graphics, Initialization, @@ -83,24 +83,30 @@ PressureInlet, PressureOutlet, ReportDefinitions, - ReportFiles, - ReportPlots, RunCalculation, Setup, + CellRegister, + ReportFile, + ReportPlot, + calculate, + iterate, + write_case, ) from ansys.fluent.visualization import GraphicsWindow, Monitor +from ansys.units import Quantity, VariableCatalog +from ansys.units.common import Pa, m, s # %% # Launch Fluent session in meshing mode # ------------------------------------- -session = pyfluent.launch_fluent(mode="meshing") +meshing = pyfluent.Meshing.from_install() # %% # Meshing workflow # ---------------- -workflow = session.workflow +workflow = meshing.workflow filenames = { "Windows": "nozzle.dsco", @@ -110,9 +116,12 @@ geometry_filename = examples.download_file( filenames.get(platform.system(), filenames["Other"]), "pyfluent/transient_compressible_simulation", - save_path=os.getcwd(), + save_path=Path.cwd(), ) +# Upload geometry to the Meshing session so tasks can operate on it +meshing.upload(geometry_filename) + workflow.InitializeWorkflow(WorkflowType="Watertight Geometry") workflow.TaskObject["Import Geometry"].Arguments = {"FileName": geometry_filename} workflow.TaskObject["Import Geometry"].Execute() @@ -199,22 +208,20 @@ # Switch to solver # ---------------- -solver = session.switch_to_solver() +solver = meshing.switch_to_solver() # %% # Display mesh # ------------ graphics = Graphics(solver) -mesh = Mesh(solver, new_instance_name="mesh-1") -boundary_conditions = BoundaryConditions(solver) +mesh = Mesh.create(solver, name="mesh-1") +boundary_conditions = BoundaryCondition(solver) graphics.picture.x_resolution = 650 # Horizontal resolution for clear visualization graphics.picture.y_resolution = 450 # Vertical resolution matching typical aspect ratio -all_walls = mesh.surfaces_list.allowed_values() - -mesh.surfaces_list = all_walls +mesh.surfaces_list = mesh.surfaces_list.allowed_values() mesh.options.edges = True mesh.display() graphics.views.restore_view(view_name="isometric") @@ -242,22 +249,23 @@ setup = Setup(solver) setup.models.energy.enabled = True -setup.materials.fluid["air"].density = {"option": "ideal-gas"} +air = FluidMaterial(solver, name="air") +air.density.option = "ideal-gas" # %% # Set boundary conditions # ----------------------- -inlet = PressureInlet(solver, name="inlet") -outlet = PressureOutlet(solver, name="outlet") +inlet = PressureInlet.get(solver, name="inlet") +outlet = PressureOutlet.get(solver, name="outlet") -inlet.momentum.gauge_total_pressure.value = 91192.5 # Pa -inlet.momentum.supersonic_or_initial_gauge_pressure.value = 74666.3925 # Pa +inlet.momentum.gauge_total_pressure = 91192.5 * Pa +inlet.momentum.supersonic_or_initial_gauge_pressure = 74666.3925 * Pa # Low turbulent intensity of 1.5% for smooth inlet flow, typical for nozzle simulations. inlet.turbulence.turbulent_intensity = 0.015 -outlet.momentum.gauge_pressure.value = 74666.3925 # Pa +outlet.momentum.gauge_pressure = 74666.3925 * Pa outlet.turbulence.backflow_turbulent_intensity = 0.015 # %% @@ -271,94 +279,71 @@ # Define report definition # ------------------------ -report_definitions = ReportDefinitions(solver) - - -report_definitions.surface.create("mass-flow-rate") -report_definitions.surface["mass-flow-rate"] = { - "report_type": "surface-massflowrate", - "surface_names": ["outlet"], -} - -report_files = ReportFiles(solver) -report_files.create(name="mass_flow_rate_out_rfile") -report_files["mass_flow_rate_out_rfile"] = { - "report_defs": ["mass-flow-rate"], - "print": True, - "file_name": "nozzle_ss.out", -} +mass_report = ReportDefinitions(solver).surface.create( + name="mass-flow-rate", + report_type="surface-massflowrate", + surface_names=[outlet], +) -report_plots = ReportPlots(solver) +mass_rfile = ReportFile.create( + solver, + name="mass_flow_rate_out_rfile", + report_defs=[mass_report], + print=True, + file_name="nozzle_ss.out", +) -report_plots.create("mass_flow_rate_out_rplot") -report_plots["mass_flow_rate_out_rplot"] = { - "report_defs": ["mass-flow-rate"], - "print": True, -} +mass_rplot = ReportPlot.create( + solver, "mass_flow_rate_out_rplot", report_defs=[mass_report], print=True +) # %% # Steady-State Initialization and Mesh Adaptation -# -------------- +# ----------------------------------------------- -solver.settings.file.write_case(file_name="nozzle_steady.cas.h5") +write_case(solver, file_name="nozzle_steady.cas.h5") initialize = Initialization(solver) initialize.hybrid_initialize() -cell_register = CellRegisters(solver) +cell_register = CellRegister(solver) # Refinement register: Mark cells where density gradient >50% of domain average -cell_register.create(name="density_scaled_gradient_refn") -cell_register["density_scaled_gradient_refn"] = { - "type": { - "option": "field-value", - "field_value": { - "derivative": {"option": "gradient"}, - "scaling": {"option": "scale-by-global-average"}, - "option": { - "option": "more-than", - "more_than": 0.5, # Threshold: >50% average - }, - "field": "density", - }, - } -} +density_refn = CellRegister.create(solver, name="density_scaled_gradient_refn") +density_refn.type.option = "field-value" +density_refn.type.field_value.derivative = "gradient" +density_refn.type.field_value.scaling = "scale-by-global-average" +density_refn.type.field_value.option.option = "more-than" +density_refn.type.field_value.option.more_than = 0.5 # Threshold: >50% average +density_refn.type.field_value.field = "density" + # Coarsening register: Mark cells where density gradient <45% of domain average -cell_register.create(name="density_scaled_gradient_crsn") -cell_register["density_scaled_gradient_crsn"] = { - "type": { - "option": "field-value", - "field_value": { - "derivative": {"option": "gradient"}, - "scaling": {"option": "scale-by-global-average"}, - "option": { - "option": "less-than", - "less_than": 0.45, # Threshold: <45% average - }, - "field": "density", - }, - } -} +density_crsn = CellRegister.create(solver, name="density_scaled_gradient_crsn") +density_crsn.type.option = "field-value" +density_crsn.type.field_value.derivative = "gradient" +density_crsn.type.field_value.scaling = "scale-by-global-average" +density_crsn.type.field_value.option.option = "less-than" +density_crsn.type.field_value.option.less_than = 0.45 # Threshold: <45% average +density_crsn.type.field_value.field = "density" # Define adaptation criteria: Refine if gradient is high and refinement level <2; coarsen if low -solver.settings.mesh.adapt.manual_refinement_criteria = ( +mesh.adapt.manual_refinement_criteria = ( "AND(density_scaled_gradient_refn, CellRefineLevel < 2)" ) -solver.settings.mesh.adapt.manual_coarsening_criteria = "density_scaled_gradient_crsn" +mesh.adapt.manual_coarsening_criteria = "density_scaled_gradient_crsn" -solver.tui.mesh.adapt.manage_criteria.add("adaption_criteria_0") +mesh.adapt.manage_criteria.add("F") -calculation = RunCalculation(solver) -calculation.iterate(iter_count=400) +iterate(solver, iter_count=400) # %% # Post-processing # --------------- # Create pressure contour -pressure_contour = Contour(solver, new_instance_name="pressure_contour") - -pressure_contour.surfaces_list = ["symmetry"] +pressure_contour = Contour.create( + solver, name="pressure_contour", surfaces_list=["symmetry"] +) pressure_contour.display() graphics.views.restore_view(view_name="front") @@ -370,17 +355,19 @@ # :alt: Transient Compressible Flow Pressure Contour # Create velocity contour -velocity_contour = Contour(solver, new_instance_name="velocity_contour") - -velocity_contour.field = "velocity-magnitude" -velocity_contour.surfaces_list = ["symmetry"] +velocity_contour = Contour.create( + solver, + name="velocity_contour", + field=VariableCatalog.VELOCITY_MAGNITUDE, + surfaces_list=["symmetry"], +) velocity_contour.display() graphics.views.restore_view(view_name="front") graphics.picture.save_picture(file_name="transient_compressible_4.jpg") # save the case and data file -solver.settings.file.write_case_data(file_name="steady_state_nozzle") +write_case(solver, file_name="steady_state_nozzle.cas.h5") # %% # .. image:: ../../_static/transient_compressible_4.jpg @@ -394,28 +381,23 @@ solver_general_settings.solver.time = "unsteady-1st-order" # Sinusoidal pressure variation at 2200 Hz simulates pulsating flow, with mean pressure of 0.737 atm. -outlet.momentum.gauge_pressure.value = "(0.12*sin(2200[Hz]*t)+0.737)*101325.0[Pa]" +outlet.momentum.gauge_pressure = "(0.12*sin(2200[Hz]*t)+0.737)*101325.0[Pa]" # Configure mesh adaptation: Refine every 25 iterations -solver.tui.mesh.adapt.manage_criteria.edit("adaption_criteria_0", "frequency", "25") +mesh.adapt.manage_criteria.edit("adaption_criteria_0", "frequency", "25") -report_files["mass_flow_rate_out_rfile"] = { - "file_name": "trans-nozzle-rfile.out", -} - -report_plots["mass_flow_rate_out_rplot"].x_label = "time-step" +mass_rfile.file_name = "trans-nozzle-rfile.out" -solver.settings.file.write_case(file_name="nozzle_unsteady.cas.h5") +mass_rplot.x_label = "time-step" -Transient_controls = solver.settings.solution.run_calculation.transient_controls +write_case(solver, file_name="nozzle_unsteady.cas.h5") -Transient_controls.time_step_count = 100 -Transient_controls.time_step_size = 2.85596e-05 # s: Resolves 2200 Hz oscillations -Transient_controls.max_iter_per_time_step = ( - 10 # Ensures convergence within each time step -) +transient_controls = RunCalculation(solver).transient_controls +transient_controls.time_step_count = 100 +transient_controls.time_step_size = 2.85596e-05 * s +transient_controls.max_iter_per_time_step = 10 -calculation.calculate() +calculate(solver) mass_bal_rplot = Monitor(solver=solver, monitor_set_name="mass_flow_rate_out_rplot") plot_window = GraphicsWindow() diff --git a/examples/00-fluent/tyler_sofrin_modes.py b/examples/00-fluent/tyler_sofrin_modes.py index 72cc4ca62fa..836ebccc23a 100644 --- a/examples/00-fluent/tyler_sofrin_modes.py +++ b/examples/00-fluent/tyler_sofrin_modes.py @@ -114,7 +114,6 @@ # ===================================================================================== import csv import math -import os from pathlib import Path import random @@ -123,6 +122,8 @@ import ansys.fluent.core as pyfluent from ansys.fluent.core import examples +from ansys.fluent.core.solver import PointSurface, ReportDefinitions, read_case_data +from ansys.units.common import m ####################################################################################### # Downloading cas/dat file @@ -130,22 +131,20 @@ import_filename = examples.download_file( "axial_comp_fullWheel_DFT_23R2.cas.h5", "pyfluent/examples/Tyler-Sofrin-Modes-Compressor", - save_path=os.getcwd(), + save_path=Path.cwd(), ) examples.download_file( "axial_comp_fullWheel_DFT_23R2.dat.h5", "pyfluent/examples/Tyler-Sofrin-Modes-Compressor", - save_path=os.getcwd(), + save_path=Path.cwd(), ) ####################################################################################### # Launch Fluent session and print Fluent version # ===================================================================================== -session = pyfluent.launch_fluent( - processor_count=4, -) -print(session.get_fluent_version()) +solver = pyfluent.Solver.from_install(processor_count=4) +print(solver.get_fluent_version()) ####################################################################################### # Reading case and data file @@ -153,8 +152,7 @@ # # .. note:: # The dat file should correspond to the already completed DFT simulation. - -session.settings.file.read(file_type="case-data", file_name=import_filename) +read_case_data(solver, file_name=import_filename) ####################################################################################### # Define User constant/variables @@ -174,8 +172,8 @@ "dft-static-pressure-2_30.00kHz-ta", ] n_mode = [0, 1, 2, 3] # Impeller frequency harmonics -r = 0.082 # meters -z = -0.037 # meters +r = 0.082 * m +z = -0.037 * m d_theta = 5 # degrees m_max = 50 # maximum TS mode number @@ -188,49 +186,45 @@ for angle in range(0, 360, d_theta): x = math.cos(math.radians(angle)) * r y = math.sin(math.radians(angle)) * r - pt_name = "point-" + str(angle) - session.settings.results.surfaces.point_surface[pt_name] = {} - session.settings.results.surfaces.point_surface[pt_name].point = [x, y, z] + PointSurface(solver, new_instance_name=f"point-{angle}"). point=(x, y, z) ####################################################################################### # Compute Fourier coefficients at each monitor point (An, Bn) # ===================================================================================== An = np.zeros((len(varname), int(360 / d_theta))) Bn = np.zeros((len(varname), int(360 / d_theta))) +report_defs = ReportDefinitions(solver) for angle_ind, angle in enumerate(range(0, 360, d_theta)): for n_ind, variable in enumerate(varname): if variable.startswith("mean"): - session.settings.solution.report_definitions.surface["mag-report"] = { - "report_type": "surface-vertexavg", - "surface_names": ["point-" + str(angle)], - "field": str(variable), - } - mag = session.settings.solution.report_definitions.compute( - report_defs=["mag-report"] + mag_report = report_defs.surface.create( + name="mag-report", + report_type="surface-vertexavg", + surface_names=[f"point-{angle}"], + field=variable, ) - mag = mag[0]["mag-report"][0] + mag_res = report_defs.compute(report_defs=[mag_report]) + mag = mag_res[0][mag_report.name][0] An[n_ind][angle_ind] = mag Bn[n_ind][angle_ind] = 0 else: - session.settings.solution.report_definitions.surface["mag-report"] = { - "report_type": "surface-vertexavg", - "surface_names": ["point-" + str(angle)], - "field": str(variable) + "-mag", - } - mag = session.settings.solution.report_definitions.compute( - report_defs=["mag-report"] + mag_report = report_defs.surface.create( + name="mag-report", + report_type="surface-vertexavg", + surface_names=[f"point-{angle}"], + field=f"{variable}-mag", ) - mag = mag[0]["mag-report"][0] - session.settings.solution.report_definitions.surface["phase-report"] = { - "report_type": "surface-vertexavg", - "surface_names": ["point-" + str(angle)], - "field": str(variable) + "-phase", - } - phase = session.settings.solution.report_definitions.compute( - report_defs=["phase-report"] + mag_res = report_defs.compute(report_defs=[mag_report]) + mag = mag_res[0][mag_report.name][0] + phase_report = report_defs.surface.create( + name="phase-report", + report_type="surface-vertexavg", + surface_names=[f"point-{angle}"], + field=f"{variable}-phase", ) - phase = phase[0]["phase-report"][0] + phase_res = report_defs.compute(report_defs=[phase_report]) + phase = phase_res[0][phase_report.name][0] An[n_ind][angle_ind] = mag * math.cos(phase) Bn[n_ind][angle_ind] = -mag * math.sin(phase) @@ -316,7 +310,7 @@ ####################################################################################### # Close the session # ===================================================================================== -session.exit() +solver.exit() ####################################################################################### From c48f1fb7abd10690b8d6d1343809bcc2208a34be Mon Sep 17 00:00:00 2001 From: pyansys-ci-bot <92810346+pyansys-ci-bot@users.noreply.github.com> Date: Wed, 4 Feb 2026 01:38:25 +0000 Subject: [PATCH 2/9] chore: adding changelog file 4887.maintenance.md [dependabot-skip] --- doc/changelog.d/4887.maintenance.md | 1 + 1 file changed, 1 insertion(+) create mode 100644 doc/changelog.d/4887.maintenance.md diff --git a/doc/changelog.d/4887.maintenance.md b/doc/changelog.d/4887.maintenance.md new file mode 100644 index 00000000000..0ff8e9b7a54 --- /dev/null +++ b/doc/changelog.d/4887.maintenance.md @@ -0,0 +1 @@ +Update examples to use modern API From af1147af1714b24398d704ab6f2976405277bc74 Mon Sep 17 00:00:00 2001 From: Gobot1234 Date: Wed, 18 Feb 2026 02:33:23 +0000 Subject: [PATCH 3/9] respond to some feedback --- examples/00-fluent/DOE_ML.py | 28 +++---- .../Electrolysis_Modeling_workflow.py | 39 +++++++--- examples/00-fluent/ahmed_body_workflow.py | 14 ++-- examples/00-fluent/battery_pack.py | 26 ++++--- examples/00-fluent/brake.py | 65 +++++++++------- .../00-fluent/catalytic_converter_workflow.py | 45 +++++------ .../00-fluent/exhaust_system_settings_api.py | 58 ++++++++++---- .../00-fluent/external_compressible_flow.py | 14 +--- examples/00-fluent/frozen_rotor_workflow.py | 76 ++++++++++++------- examples/00-fluent/fsi_1way_workflow.py | 25 +++--- examples/00-fluent/lunar_lander_thermal.py | 21 ++--- .../00-fluent/mixing_elbow_settings_api.py | 24 +++--- examples/00-fluent/tyler_sofrin_modes.py | 2 +- 13 files changed, 263 insertions(+), 174 deletions(-) diff --git a/examples/00-fluent/DOE_ML.py b/examples/00-fluent/DOE_ML.py index 5c876de8721..b7d48d74c4e 100644 --- a/examples/00-fluent/DOE_ML.py +++ b/examples/00-fluent/DOE_ML.py @@ -8,6 +8,7 @@ # "scikit-learn", # "seaborn", # "tensorflow", +# "xgboost", # ] # /// @@ -63,26 +64,27 @@ # flake8: noqa: E402 import itertools -import json from pathlib import Path from typing import TYPE_CHECKING, cast -from ansys.units import Quantity -from ansys.units.quantity import ArrayLike import matplotlib.pyplot as plt import numpy as np import pandas as pd -# import plotly.express as px -# import plotly.graph_objects as go -# import seaborn as sns -# import tensorflow as tf -# from tensorflow import keras +import plotly.express as px +import plotly.graph_objects as go +import seaborn as sns +import tensorflow as tf +from tensorflow import keras import ansys.fluent.core as pyfluent from ansys.fluent.core import examples -from ansys.fluent.core.generated.solver.settings_builtin import SurfaceIntegrals -from ansys.fluent.core.generated.solver.settings_builtin_261 import iterate, read_case -from ansys.fluent.core.solver import Initialization, VelocityInlet, RunCalculation +from ansys.fluent.core.solver import ( + Initialization, + SurfaceIntegrals, + VelocityInlet, + iterate, + read_case, +) from ansys.units.common import m, s ########################################################################### @@ -145,7 +147,7 @@ initialize.initialization_type = "standard" initialize.standard_initialize() - iterate(solver,iter_count=200) + iterate(solver, iter_count=200) temperatures = SurfaceIntegrals(solver).get_mass_weighted_avg( surface_names=["outlet"], report_of="temperature" @@ -420,7 +422,7 @@ def fit_and_predict(model: LinearRegression | XGBRegressor | RandomForestRegress ] ) -optimizer = tf.keras.optimizers.Adam(learning_rate=0.1, beta_1=0.9, beta_2=0.999) +optimizer = keras.optimizers.Adam(learning_rate=0.1, beta_1=0.9, beta_2=0.999) model.compile(loss="mean_squared_error", optimizer=optimizer) checkpoint_cb = keras.callbacks.ModelCheckpoint( diff --git a/examples/00-fluent/Electrolysis_Modeling_workflow.py b/examples/00-fluent/Electrolysis_Modeling_workflow.py index df79da2c3e7..f3f264fac48 100644 --- a/examples/00-fluent/Electrolysis_Modeling_workflow.py +++ b/examples/00-fluent/Electrolysis_Modeling_workflow.py @@ -1,3 +1,9 @@ +# /// script +# dependencies = [ +# "ansys-fluent-core", +# ] +# /// + # Copyright (C) 2021 - 2026 ANSYS, Inc. and/or its affiliates. # SPDX-License-Identifier: MIT # @@ -78,7 +84,6 @@ import ansys.fluent.core as pyfluent from ansys.fluent.core import examples -from ansys.fluent.core.generated.solver.settings_builtin_261 import iterate, write_case_data from ansys.fluent.core.solver import ( BoundaryConditions, Contour, @@ -89,9 +94,9 @@ MassFlowInlet, Materials, Mesh, - RunCalculation, - Setup, SolidMaterial, + iterate, + write_case_data, ) from ansys.units.common import A, K, V, degree, m, ohm, s @@ -208,13 +213,22 @@ # ---------------------- materials = Materials(solver) -SolidMaterial.create(solver, name="collector-default", electric_conductivity = 20000 * S / m) +SolidMaterial.create( + solver, name="collector-default", electric_conductivity=20000 * S / m +) -SolidMaterial.create(solver, name="porous-default", electric_conductivity = 20000 * S / m) +SolidMaterial.create(solver, name="porous-default", electric_conductivity=20000 * S / m) -SolidMaterial.create(solver, name="catalyst-default", electrical_conductivity = 5000 * S / m, dual_electric_conductivity = 4.5 * S / m) +SolidMaterial.create( + solver, + name="catalyst-default", + electrical_conductivity=5000 * S / m, + dual_electric_conductivity=4.5 * S / m, +) -SolidMaterial.create(solver, name="electrolyte-default", dual_electric_conductivity = 11 * S / m) +SolidMaterial.create( + solver, name="electrolyte-default", dual_electric_conductivity=11 * S / m +) # %% # Boundary conditions @@ -253,7 +267,9 @@ # Post-processing # --------------- -potential_contour = Contour.create(solver, name="potential_contour", field = "potential", surfaces_list = ["zmid"]) +potential_contour = Contour.create( + solver, name="potential_contour", field="potential", surfaces_list=["zmid"] +) graphics.views.restore_view(view_name="front") @@ -267,7 +283,12 @@ # :align: center # :alt: Potential Contour -volume_fraction_contour = Contour.create(solver, name="volume_fraction_contour", field = "phase-1-vof", surfaces_list = ["zmid", "xmid"]) +volume_fraction_contour = Contour.create( + solver, + name="volume_fraction_contour", + field="phase-1-vof", + surfaces_list=["zmid", "xmid"], +) graphics.views.restore_view(view_name="isometric") volume_fraction_contour.display() diff --git a/examples/00-fluent/ahmed_body_workflow.py b/examples/00-fluent/ahmed_body_workflow.py index b18adc3f3da..8694f97ac42 100644 --- a/examples/00-fluent/ahmed_body_workflow.py +++ b/examples/00-fluent/ahmed_body_workflow.py @@ -64,32 +64,32 @@ from pathlib import Path import platform -from ansys.units import VariableCatalog - import ansys.fluent.core as pyfluent from ansys.fluent.core import examples from ansys.fluent.core.solver import ( - Methods, - ReferenceValues, - Residual, - iterate, write_case, FluidMaterial, Initialization, IsoSurface, + Methods, Monitor, OutputParameters, PressureOutlet, + ReferenceValues, ReportDefinitions, + Residual, VelocityInlet, Viscous, + iterate, + write_case, ) from ansys.fluent.visualization import Contour, GraphicsWindow +from ansys.units import VariableCatalog from ansys.units.common import kg, m, s ####################################################################################### # Launch Fluent session with meshing mode and print Fluent version # ===================================================================================== -meshing = pyfluent.Meshing.from_install(cleanup_on_exit=True, fluent_path=r"C:\ANSYSDev\v261\fluent\ntbin\win64\fluent.exe") +meshing = pyfluent.Meshing.from_install() print(meshing.get_fluent_version()) ####################################################################################### diff --git a/examples/00-fluent/battery_pack.py b/examples/00-fluent/battery_pack.py index 509324da4f4..f9c171abb7b 100644 --- a/examples/00-fluent/battery_pack.py +++ b/examples/00-fluent/battery_pack.py @@ -1,3 +1,10 @@ +# /// script +# dependencies = [ +# "ansys-fluent-core", +# "ansys-fluent-visualization", +# ] +# /// + # Copyright (C) 2021 - 2026 ANSYS, Inc. and/or its affiliates. # SPDX-License-Identifier: MIT # @@ -74,8 +81,6 @@ from pathlib import Path -from ansys.units import VariableCatalog - import ansys.fluent.core as pyfluent from ansys.fluent.core import examples from ansys.fluent.core.solver import ( @@ -88,24 +93,25 @@ Materials, Mesh, ReportDefinitions, + ReportPlot, RunCalculation, + SolidCellZone, SolidMaterial, Solution, Vector, - write_case_data, WallBoundary, - SolidCellZone, - ReportPlot, read_mesh, + write_case_data, ) from ansys.fluent.visualization import GraphicsWindow, Monitor +from ansys.units import VariableCatalog from ansys.units.common import K, W, m, ohm # %% # Define constants # ---------------- -S = 1 / ohm # a Siemen +S = 1 / ohm # 1 siemens # %% @@ -126,7 +132,7 @@ save_path=Path.cwd(), ) -solver.setting.file.read_mesh(file_name=mesh_file) +solver.settings.file.read_mesh(file_name=mesh_file) # %% # Display mesh @@ -138,7 +144,7 @@ graphics.picture.x_resolution = 650 # Horizontal resolution for clear visualization graphics.picture.y_resolution = 450 # Vertical resolution matching typical aspect ratio -all_walls = mesh.surfaces_list.allowed_values() +all_walls = mesh.surfaces_list.all() mesh.surfaces_list = all_walls mesh.options.edges = True mesh.display() @@ -274,6 +280,7 @@ create_report_plot=True, ) +# Format plot axes volume_max_temp = ReportPlot.get(solver, name="volume_max_temp-rplot") volume_max_temp.axes.x.number_format.precision = 0 volume_max_temp.axes.y.number_format.precision = 2 @@ -294,8 +301,7 @@ transient_controls.time_step_count = 50 # Number of time steps transient_controls.time_step_size = 30 # 30s per step -# Run transient simulation -calculation.calculate() +calculation.calculate() # Run transient simulation # %% # Post-processing diff --git a/examples/00-fluent/brake.py b/examples/00-fluent/brake.py index 686774f1777..733a6869c43 100644 --- a/examples/00-fluent/brake.py +++ b/examples/00-fluent/brake.py @@ -53,26 +53,27 @@ import itertools from pathlib import Path -from ansys.units import VariableCatalog import matplotlib.pyplot as plt import ansys.fluent.core as pyfluent from ansys.fluent.core import examples -from ansys.fluent.core.generated.solver.settings_242 import report_type -from ansys.fluent.core.generated.solver.settings_builtin_261 import read_case, write_case_data -from ansys.fluent.visualization import Contour, GraphicsWindow -from ansys.fluent.core.generated.solver.settings_builtin import Controls, Graphics from ansys.fluent.core.solver import ( + Controls, Energy, General, - SolidCellZone, - WallBoundary, - ReportDefinitions, - Monitor, + Graphics, Initialization, + Monitor, + ReportDefinitions, RunCalculation, + SolidCellZone, + WallBoundary, + read_case, + write_case_data, ) -from ansys.units.common import K, m, W, radian, s +from ansys.fluent.visualization import Contour, GraphicsWindow +from ansys.units import VariableCatalog +from ansys.units.common import K, W, m, radian, s import_filename = examples.download_file( "brake.msh.h5", @@ -88,7 +89,9 @@ # Launch Fluent session with solver mode and print Fluent version # --------------------------------------------------------------- -solver = pyfluent.Solver.from_install(precision="double", processor_count=2, dimension=3) +solver = pyfluent.Solver.from_install( + precision="double", processor_count=2, dimension=3 +) print(solver.get_fluent_version()) #################################################################################### @@ -168,27 +171,36 @@ report_defs = ReportDefinitions(solver) -max_pad_temp = report_defs.volume.create(name="max-pad-temperature", report_type="volume-max", field=VariableCatalog.TEMPERATURE, cell_zones=["geom-1-innerpad", "geom-1-outerpad"]) +max_pad_temp = report_defs.volume.create( + name="max-pad-temperature", + report_type="volume-max", + field=VariableCatalog.TEMPERATURE, + cell_zones=["geom-1-innerpad", "geom-1-outerpad"], +) -max_disc_temp = report_defs.volume.create(name="max-disc-temperature", -report_type = "volume-max", -field = "temperature", -cell_zones = ["disc1", "disc2"],) +max_disc_temp = report_defs.volume.create( + name="max-disc-temperature", + report_type="volume-max", + field="temperature", + cell_zones=["disc1", "disc2"], +) monitor = Monitor(solver) temp_plot = monitor.report_plots.create(name="max-temperature") temp_plot.report_defs = [max_pad_temp, max_disc_temp] -temp_file = monitor.report_files.create(name="max-temperature", -report_defs = [max_pad_temp, max_disc_temp, "flow-time"], -file_name = "max-temperature.out") +temp_file = monitor.report_files.create( + name="max-temperature", + report_defs=[max_pad_temp, max_disc_temp, "flow-time"], + file_name="max-temperature.out", +) graphics = Graphics(solver) -temp_contour = graphics.contour.create(name="temperature", -field = VariableCatalog.TEMPERATURE, -surfaces_list = "wall*") +temp_contour = graphics.contour.create( + name="temperature", field=VariableCatalog.TEMPERATURE, surfaces_list="wall*" +) temp_contour.color_map.visible = True temp_contour.color_map.size = 100 @@ -220,10 +232,11 @@ solver.solution.calculation_activity.solution_animations.create( name="animate-temperature", -animate_on = "temperature", -frequency_of = "flow-time", -flow_time_frequency = 0.05, -view = "animation-view",) + animate_on="temperature", + frequency_of="flow-time", + flow_time_frequency=0.05, + view="animation-view", +) ################################################################################################## # Run simulation diff --git a/examples/00-fluent/catalytic_converter_workflow.py b/examples/00-fluent/catalytic_converter_workflow.py index 6d4cc92a045..8cf8db94c39 100644 --- a/examples/00-fluent/catalytic_converter_workflow.py +++ b/examples/00-fluent/catalytic_converter_workflow.py @@ -1,3 +1,10 @@ +# /// script +# dependencies = [ +# "ansys-fluent-core", +# "ansys-fluent-visualization", +# ] +# /// + # Copyright (C) 2021 - 2026 ANSYS, Inc. and/or its affiliates. # SPDX-License-Identifier: MIT # @@ -91,24 +98,15 @@ from pathlib import Path import platform -from ansys.units import VariableCatalog - import ansys.fluent.core as pyfluent -from ansys.fluent.core import ( - Dimension, - Precision, - UIMode, - examples, -) -from ansys.fluent.core.generated.solver.settings_builtin import IsoSurface -from ansys.fluent.core.generated.solver.settings_builtin_261 import write_case_data +from ansys.fluent.core import examples from ansys.fluent.core.solver import ( # noqa: E402 CellZoneConditions, Energy, General, Graphics, Initialization, - IsoSurfaces, + IsoSurface, Materials, Mesh, Monitor, @@ -119,17 +117,19 @@ Scene, VelocityInlet, WallBoundaries, + write_case_data, ) +from ansys.units import VariableCatalog from ansys.units.common import K, Pa, m, s # %% # Launch meshing session # ---------------------------- meshing = pyfluent.Meshing.from_install( - ui_mode=UIMode.GUI, + ui_mode=pyfluent.UIMode.GUI, processor_count=4, - precision=Precision.DOUBLE, - dimension=Dimension.THREE, + precision=pyfluent.Precision.DOUBLE, + dimension=pyfluent.Dimension.THREE, ) # %% @@ -634,7 +634,7 @@ velocity_vectors_scene.graphics_objects.add(name="mesh-1") # Configure scene appearance and display settings -scene_1= Scene.create(solver, name="scene-1") +scene_1 = Scene.create(solver, name="scene-1") scene_1.graphics_objects = { "vector-vel": {"name": "vectors"}, # Label for the vector plot "mesh-1": {"transparency": 75}, # Semi-transparent mesh (75% transparent) @@ -658,7 +658,7 @@ mesh_1_scene = static_pressure_scene.graphics_objects.add(name="mesh-1") # Configure pressure contour scene settings -pressure_contour_scene.name =pressure_contour # Label for the pressure contour +pressure_contour_scene.name = pressure_contour # Label for the pressure contour mesh_1_scene.transparency = 75 # Consistent mesh transparency static_pressure_scene.display() @@ -677,11 +677,15 @@ # This scene shows speed distribution across multiple axial locations velocity_magnitude_scene = Scene.create(solver, name="scene-3") -velocity_mag_contour_scene = velocity_magnitude_scene.graphics_objects.add(name="contour-velmag") +velocity_mag_contour_scene = velocity_magnitude_scene.graphics_objects.add( + name="contour-velmag" +) mesh_1_scene = velocity_magnitude_scene.graphics_objects.add(name="mesh-1") # Configure velocity magnitude contour scene settings -velocity_mag_contour_scene.name = velocity_mag_contour # Label for velocity magnitude contour +velocity_mag_contour_scene.name = ( + velocity_mag_contour # Label for velocity magnitude contour +) mesh_1_scene.transparency = 75 # Consistent mesh transparency velocity_magnitude_scene.display() @@ -703,10 +707,7 @@ # Write final case and data -write_case_data( - solver, - file_name="out/catalytic_converter_final.cas.h5" -) +write_case_data(solver, file_name="out/catalytic_converter_final.cas.h5") # %% # Solver Exit diff --git a/examples/00-fluent/exhaust_system_settings_api.py b/examples/00-fluent/exhaust_system_settings_api.py index d5f233d4d55..efa4218a577 100644 --- a/examples/00-fluent/exhaust_system_settings_api.py +++ b/examples/00-fluent/exhaust_system_settings_api.py @@ -73,14 +73,25 @@ # the geometry file. # sphinx_gallery_thumbnail_path = '_static/exhaust_system_settings.png' -from ansys.units import VariableCatalog + import ansys.fluent.core as pyfluent from ansys.fluent.core import examples -from pathlib import Path -from ansys.fluent.core.generated.solver.settings_builtin import IsoSurface -from ansys.fluent.core.generated.solver.settings_builtin_261 import iterate, write_case_data -from ansys.fluent.core.solver import Viscous, VelocityInlet, PressureOutlet, Initialization, RunCalculation, Graphics, Pathline, Scene, Surfaces +from ansys.fluent.core.solver import ( + Graphics, + Initialization, + IsoSurface, + Pathline, + PressureOutlet, + RunCalculation, + Scene, + Surfaces, + VelocityInlet, + Viscous, + iterate, + write_case_data, +) from ansys.units.common import m, s + import_file_name = examples.download_file( "exhaust_system.fmd", "pyfluent/exhaust_system" ) @@ -129,9 +140,9 @@ "/dirty_manifold-for-wrapper," + "1/dirty_manifold-for-wrapper,1/object1,1", ] ) -meshing.PartManagement.ObjectSetting[ - "DefaultObjectSetting" -].OneZonePer.set_state("part") +meshing.PartManagement.ObjectSetting["DefaultObjectSetting"].OneZonePer.set_state( + "part" +) cad_import = meshing.workflow.TaskObject["Import CAD and Part Management"] cad_import.Arguments.set_state( { @@ -640,7 +651,8 @@ # Write the case and data files # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -write_case_data(solver, +write_case_data( + solver, file_name="exhaust_system.cas.h5", ) @@ -669,10 +681,12 @@ # :width: 500pt # :align: center -pathlines = Pathline.create(solver, name="pathlines-1", -field = "time", -skip = 5, -release_from_surfaces = list(inlets), +pathlines = Pathline.create( + solver, + name="pathlines-1", + field="time", + skip=5, + release_from_surfaces=list(inlets), ) pathlines.accuracy_control.tolerance = 0.001 pathlines.display() @@ -686,7 +700,13 @@ # ~~~~~~~~~~~~~~~~~~ # Create an iso-surface through the manifold geometry. -IsoSurface.create(solver, name="surf-x-coordinate", field="x-coordinate", zones=["fluid-region-1"], iso_values=[0.38] * m) +IsoSurface.create( + solver, + name="surf-x-coordinate", + field="x-coordinate", + zones=["fluid-region-1"], + iso_values=[0.38] * m, +) ############################################################################### # Create contours of velocity magnitude @@ -699,8 +719,14 @@ # :width: 500pt # :align: center -graphics = Graphics(solver) -vel_contour = Contour.create(solver, name="contour-velocity", field = "velocity-magnitude", surfaces_list = ["surf-x-coordinate"], node_values = False) +graphics = Graphics(solver) +vel_contour = Contour.create( + solver, + name="contour-velocity", + field="velocity-magnitude", + surfaces_list=["surf-x-coordinate"], + node_values=False, +) vel_contour.range_option.option = "auto-range-on" vel_contour.range_option.auto_range_on.global_range = False diff --git a/examples/00-fluent/external_compressible_flow.py b/examples/00-fluent/external_compressible_flow.py index 6a27febb107..e14f1052851 100644 --- a/examples/00-fluent/external_compressible_flow.py +++ b/examples/00-fluent/external_compressible_flow.py @@ -78,14 +78,14 @@ import ansys.fluent.core as pyfluent from ansys.fluent.core import examples -from ansys.fluent.core.generated.solver.settings_builtin import RunCalculation -from ansys.fluent.core.generated.solver.settings_builtin_261 import write_case from ansys.fluent.core.solver import ( FluidMaterial, General, Initialization, PressureFarFieldBoundary, + RunCalculation, Viscous, + write_case, ) from ansys.units.common import K, Pa, kg, m, s @@ -354,10 +354,7 @@ # ~~~~~~~~~~~~~~ # Save the case file ``external_compressible1.cas.h5``. -write_case( - solver, - file_name="external_compressible.cas.h5" -) +write_case(solver, file_name="external_compressible.cas.h5") ############################################################################### # Solve for 25 iterations @@ -371,10 +368,7 @@ # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ # Write the final case file and the data. -write_case( - solver, - file_name="external_compressible1.cas.h5" -) +write_case(solver, file_name="external_compressible1.cas.h5") ############################################################################### # Close Fluent diff --git a/examples/00-fluent/frozen_rotor_workflow.py b/examples/00-fluent/frozen_rotor_workflow.py index 17996774486..56804b45a3d 100644 --- a/examples/00-fluent/frozen_rotor_workflow.py +++ b/examples/00-fluent/frozen_rotor_workflow.py @@ -1,6 +1,7 @@ # /// script # dependencies = [ # "ansys-fluent-core", +# "ansys-fluent-visualization", # ] # /// @@ -80,18 +81,16 @@ # Import required libraries/modules # ============================================================================================================== import math -from mimetypes import init -from nt import write from pathlib import Path -from ansys.units import VariableCatalog - import ansys.fluent.core as pyfluent from ansys.fluent.core import examples -from ansys.fluent.core.generated.solver.settings_builtin import ( - BoundaryCondition, +from ansys.fluent.core.solver import ( BoundaryConditions, + FluidCellZone, + General, Initialization, + MassFlowOutlet, Materials, MeshInterfaces, Methods, @@ -101,20 +100,15 @@ PressureInlet, ReportDefinitions, ReportPlot, + RunCalculation, Setup, - Surfaces, -) -from ansys.fluent.core.generated.solver.settings_builtin_261 import write_case, write_case_data -from ansys.fluent.core.solver import ( - FluidCellZone, - General, - MassFlowOutletBoundary, - PressureInletBoundary, Viscous, WallBoundary, + write_case, + write_case_data, ) -from ansys.fluent.core.solver import RunCalculation from ansys.fluent.visualization import Contour, Graphics +from ansys.units import VariableCatalog from ansys.units.common import Pa, kg, m, s ################################################################################################################ @@ -144,7 +138,7 @@ viscosity_water = 0.001002 * Pa * s g = 9.81 * m / s**2 impeller_speed = 1450 # rpm -# Convert to rad/s (numeric) +# Convert to rad/s impeller_speed_rad = impeller_speed * 2 * math.pi / 60 ################################################################################################################ @@ -278,7 +272,7 @@ ) # Outlet Boundary Condition -mass_flow_outlet = MassFlowOutletBoundary.get(solver, name="mass-flow-inlet-11") +mass_flow_outlet = MassFlowOutlet.get(solver, name="mass-flow-inlet-11") mass_flow_outlet.momentum.mass_flow_rate.value = 90 * kg / s @@ -332,12 +326,22 @@ per_surface=False, ) -outlet_pressure_report_plot = ReportPlot(solver, name="p-out-rplot",report_defs = "p-out") +outlet_pressure_report_plot = ReportPlot( + solver, name="p-out-rplot", report_defs="p-out" +) -outlet_pressure_report_file = ReportPlot(solver, name="p-out-rfile",report_defs = "p-out") +outlet_pressure_report_file = ReportPlot( + solver, name="p-out-rfile", report_defs="p-out" +) # p-in -inlet_pressure_report_def = report_definitions.surface.create("p-in", report_type = "surface-massavg", surface_names = ["inlet"], field = "total-pressure", per_surface = False) +inlet_pressure_report_def = report_definitions.surface.create( + "p-in", + report_type="surface-massavg", + surface_names=["inlet"], + field="total-pressure", + per_surface=False, +) # Pump Head @@ -346,20 +350,32 @@ pump_head_report_def.definition = "head" # report plot -pump_head_report_plot = monitor.report_plots.create("pump-head-rplot", report_defs=pump_head_report_def) +pump_head_report_plot = monitor.report_plots.create( + "pump-head-rplot", report_defs=pump_head_report_def +) # report file -pump_head_report_file = monitor.report_files.create("pump-head-rfile", report_defs=pump_head_report_def) +pump_head_report_file = monitor.report_files.create( + "pump-head-rfile", report_defs=pump_head_report_def +) # p-blade -blade_pressure_report_def = report_definitions.surface.create("p-blade", report_type = "surface-massavg", surface_names = ["blade"], field = "pressure", per_surface = False) +blade_pressure_report_def = report_definitions.surface.create( + "p-blade", + report_type="surface-massavg", + surface_names=["blade"], + field="pressure", + per_surface=False, +) ################################################################################################################ # Initialization and run solver # ============================================================================================================== initialization = Initialization(solver) initialization.reference_frame = "absolute" -initialization.hybrid_init_options.general_settings.initialization_options.initial_pressure = True +initialization.hybrid_init_options.general_settings.initialization_options.initial_pressure = ( + True +) initialization.hybrid_initialize() # Run calculation settings @@ -377,12 +393,16 @@ # ============================================================================================================== # Create a mid-plane surface at z = -0.015 m -z_mid_plane = PlaneSurface.create(solver, name="z_mid_plane", method = "xy-plane", z = -0.015) +z_mid_plane = PlaneSurface.create( + solver, name="z_mid_plane", method="xy-plane", z=-0.015 +) z_mid_plane.display() # Define and display the contour for static pressure using typed API graphics = Graphics(solver) -pressure_contour = Contour.create(solver=solver, field=VariableCatalog.PRESSURE, surfaces=["z_mid_plane"]) +pressure_contour = Contour.create( + solver=solver, field=VariableCatalog.PRESSURE, surfaces=["z_mid_plane"] +) pressure_contour.display() graphics.views.restore_view(view_name="front") graphics.views.auto_scale() @@ -397,9 +417,7 @@ ################################################################################################################ # Save the case file # ============================================================================================================== -write_case_data(solver, - file_name="pump_volute_setup_solved.cas.h5" -) +write_case_data(solver, file_name="pump_volute_setup_solved.cas.h5") ################################################################################################################ # Close the session diff --git a/examples/00-fluent/fsi_1way_workflow.py b/examples/00-fluent/fsi_1way_workflow.py index 2ce7ba21497..e8a2553e4cc 100644 --- a/examples/00-fluent/fsi_1way_workflow.py +++ b/examples/00-fluent/fsi_1way_workflow.py @@ -1,3 +1,9 @@ +# /// script +# dependencies = [ +# "ansys-fluent-core", +# ] +# /// + # Copyright (C) 2021 - 2026 ANSYS, Inc. and/or its affiliates. # SPDX-License-Identifier: MIT # @@ -70,22 +76,23 @@ from pathlib import Path import ansys.fluent.core as pyfluent -from ansys.fluent.core import Precision, examples -from ansys.fluent.core.generated.solver.settings_242 import read_case -from ansys.fluent.core.generated.solver.settings_builtin import Controls -from ansys.fluent.core.generated.solver.settings_builtin_261 import BoundaryCondition, Materials, iterate, write_case, write_case_data +from ansys.fluent.core import examples from ansys.fluent.core.solver import ( - BoundaryConditions, + BoundaryCondition, Contour, + Controls, Graphics, Initialization, - RunCalculation, + Materials, Setup, SolidCellZone, - Solution, Structure, VelocityInlet, WallBoundary, + iterate, + read_case, + write_case, + write_case_data, ) from ansys.units import VariableCatalog from ansys.units.common import m, s @@ -94,7 +101,7 @@ # Launch Fluent session in solver mode # ------------------------------------ -solver = pyfluent.Solver.from_install(precision=Precision.DOUBLE) +solver = pyfluent.Solver.from_install(precision=pyfluent.Precision.DOUBLE) # %% # Download and read the mesh file @@ -112,7 +119,7 @@ # ---------------------------------------- velocity_inlet = VelocityInlet.get(solver, name="velocity_inlet") -velocity_inlet.momentum.velocity_magnitude = 100.0 * m / s +velocity_inlet.momentum.velocity_magnitude = 100.0 * m / s # High-speed inlet flow velocity_inlet.turbulence.turbulent_viscosity_ratio = ( 5 # Dimensionless, typically 1-10 for moderate turbulence ) diff --git a/examples/00-fluent/lunar_lander_thermal.py b/examples/00-fluent/lunar_lander_thermal.py index 982d322da84..7ebb9e50a18 100644 --- a/examples/00-fluent/lunar_lander_thermal.py +++ b/examples/00-fluent/lunar_lander_thermal.py @@ -101,30 +101,25 @@ import ansys.fluent.core as pyfluent from ansys.fluent.core import examples -from ansys.fluent.core.solver import write_case -from ansys.fluent.core.generated.solver.settings_builtin import ( - BoundaryCondition, - CellZoneConditions, - Monitor, - RunCalculation, -) -from ansys.fluent.core.generated.solver.settings_builtin_261 import ( - CellZoneCondition, - calculate, -) from ansys.fluent.core.session_solver import Solver from ansys.fluent.core.solver import ( + BoundaryCondition, + CellZoneCondition, Energy, General, Initialization, + Monitor, Radiation, ReportDefinitions, + RunCalculation, SolidCellZone, SolidMaterial, Viscous, WallBoundary, + calculate, + write_case, ) -from ansys.units import Quantity, VariableCatalog +from ansys.units import VariableCatalog from ansys.units.common import J, K, W, kg, m, s lander_spaceclaim_file, lander_mesh_file, apollo17_temp_data = [ @@ -554,7 +549,7 @@ def get_surf_mean_temp( name=f"regolith-layer-{i}-temp", report_type="surface-facetavg", field=VariableCatalog.TEMPERATURE, - surface_names = [f"regolith{f'-{i-1}:{i}' if i > 1 else ''}"], + surface_names=[f"regolith{f'-{i - 1}:{i}' if i > 1 else ''}"], ) for i in range(1, 5 + 1) ] diff --git a/examples/00-fluent/mixing_elbow_settings_api.py b/examples/00-fluent/mixing_elbow_settings_api.py index a04095c0f51..34d75dd7c44 100644 --- a/examples/00-fluent/mixing_elbow_settings_api.py +++ b/examples/00-fluent/mixing_elbow_settings_api.py @@ -58,17 +58,18 @@ # sphinx_gallery_thumbnail_path = '_static/mixing_elbow_settings.png' import ansys.fluent.core as pyfluent from ansys.fluent.core import examples -from ansys.fluent.core.generated.solver.settings_builtin import Fluxes, Vector -from ansys.fluent.core.generated.solver.settings_builtin_261 import Materials, read_case from ansys.fluent.core.solver import ( Energy, FluidCellZone, + Graphics, Initialization, + Materials, PressureOutlet, ReportDefinitions, - VelocityInlet, RunCalculation, - Graphics, + Vector, + VelocityInlet, + read_case, ) from ansys.units.common import K, inch, m, s @@ -115,9 +116,7 @@ # ~~~~~~~~~~~~~~~ # Create a material named ``"water-liquid"``. -Materials(solver).database.copy_by_name( - type="fluid", name="water-liquid" -) +Materials(solver).database.copy_by_name(type="fluid", name="water-liquid") ############################################################################### # Set up cell zone conditions @@ -211,7 +210,12 @@ graphics = solver.settings.results.graphics graphics.vector["velocity_vector_symmetry"] = {} -velocity_symmetry = Vector.create(solver, name= "velocity_vector_symmetry", field = "velocity-magnitude",surfaces_list = ["symmetry-xyplane"],style = "arrow" +velocity_symmetry = Vector.create( + solver, + name="velocity_vector_symmetry", + field="velocity-magnitude", + surfaces_list=["symmetry-xyplane"], + style="arrow", ) velocity_symmetry.options.scale = 4 velocity_symmetry.display() @@ -231,7 +235,9 @@ # Compute the mass flow rate. report_defs = ReportDefinitions(solver) -mass_flow_rate = report_defs.flux.create(name="mass_flow_rate", boundaries = [cold_inlet, hot_inlet, outlet]) +mass_flow_rate = report_defs.flux.create( + name="mass_flow_rate", boundaries=[cold_inlet, hot_inlet, outlet] +) report_defs.compute(report_defs=[mass_flow_rate]) ######################################################################### diff --git a/examples/00-fluent/tyler_sofrin_modes.py b/examples/00-fluent/tyler_sofrin_modes.py index 836ebccc23a..0271711d418 100644 --- a/examples/00-fluent/tyler_sofrin_modes.py +++ b/examples/00-fluent/tyler_sofrin_modes.py @@ -186,7 +186,7 @@ for angle in range(0, 360, d_theta): x = math.cos(math.radians(angle)) * r y = math.sin(math.radians(angle)) * r - PointSurface(solver, new_instance_name=f"point-{angle}"). point=(x, y, z) + PointSurface.create(solver, name=f"point-{angle}", point=(x, y, z)) ####################################################################################### # Compute Fourier coefficients at each monitor point (An, Bn) From d3d147adf9166c00690326ec299befd388c9d162 Mon Sep 17 00:00:00 2001 From: Gobot1234 Date: Thu, 19 Feb 2026 09:23:07 +0000 Subject: [PATCH 4/9] respond to some feedback --- examples/00-fluent/species_transport.py | 1 + examples/00-fluent/steady_vortex.py | 23 +++++++++++-------- .../transient_compressible_nozzle_workflow.py | 18 ++++++++++----- examples/00-fluent/tyler_sofrin_modes.py | 10 ++++---- 4 files changed, 31 insertions(+), 21 deletions(-) diff --git a/examples/00-fluent/species_transport.py b/examples/00-fluent/species_transport.py index 3349d846555..11984eddb83 100644 --- a/examples/00-fluent/species_transport.py +++ b/examples/00-fluent/species_transport.py @@ -122,6 +122,7 @@ BoundaryCondition, Methods, Monitor, + SolverIntegrals, Graphics, ) diff --git a/examples/00-fluent/steady_vortex.py b/examples/00-fluent/steady_vortex.py index 83006075481..a4098289c8c 100644 --- a/examples/00-fluent/steady_vortex.py +++ b/examples/00-fluent/steady_vortex.py @@ -84,16 +84,16 @@ import imageio.v2 as imageio import ansys.fluent.core as pyfluent -from ansys.fluent.core import Dimension, Precision from ansys.fluent.core.examples import download_file from ansys.fluent.core.solver import ( # noqa: E402 LIC, + CalculationActivity, CellRegister, CellZoneCondition, Contour, + FluidMaterial, General, Graphics, - FluidMaterial, Initialization, IsoClip, IsoSurface, @@ -107,9 +107,8 @@ Scene, Viscous, WallBoundary, - read_case, - CalculationActivity, iterate, + read_case, write_case_data, ) from ansys.units.common import m, s @@ -121,8 +120,8 @@ # Launch Fluent in 3D double precision solver mode. solver = pyfluent.Solver.from_install( - dimension=Dimension.THREE, - precision=Precision.DOUBLE, + dimension=pyfluent.Dimension.THREE, + precision=pyfluent.Precision.DOUBLE, cleanup_on_exit=True, cwd=Path.cwd(), ) @@ -198,7 +197,7 @@ general = General(solver) general.operating_conditions.gravity.enable = True -general.operating_conditions.gravity.components = [0.0, 0.0, -g] +general.operating_conditions.gravity.components = (0.0, 0.0, -g) # %% # Copy Materials from Fluent Database @@ -261,8 +260,12 @@ model_setup.viscous = viscous solution_methods = Methods(solver) -solution_methods.multiphase_numerics.solution_stabilization.execute_settings_optimization = True -solution_methods.multiphase_numerics.solution_stabilization.execute_advanced_stabilization = True +solution_methods.multiphase_numerics.solution_stabilization.execute_settings_optimization = ( + True +) +solution_methods.multiphase_numerics.solution_stabilization.execute_advanced_stabilization = ( + True +) # Change phase names # TODO check @@ -365,7 +368,7 @@ # liquid level liquidlevel_comp_mesh = Mesh.create( - solver, name="liquidlevel", surfaces_list=[freesurface] + solver, name="liquidlevel", surfaces_list=[free_surface] ) liquidlevel_comp_mesh.surfaces_list() liquidlevel_comp_mesh.coloring.option = "manual" diff --git a/examples/00-fluent/transient_compressible_nozzle_workflow.py b/examples/00-fluent/transient_compressible_nozzle_workflow.py index 7f3b1189327..ba2e75e0e99 100644 --- a/examples/00-fluent/transient_compressible_nozzle_workflow.py +++ b/examples/00-fluent/transient_compressible_nozzle_workflow.py @@ -1,3 +1,9 @@ +# /// script +# dependencies = [ +# "ansys-fluent-core", +# ] +# /// + # Copyright (C) 2021 - 2026 ANSYS, Inc. and/or its affiliates. # SPDX-License-Identifier: MIT # @@ -71,8 +77,9 @@ import ansys.fluent.core as pyfluent from ansys.fluent.core import examples -from ansys.fluent.core.generated.solver.settings_builtin_261 import BoundaryCondition from ansys.fluent.core.solver import ( + BoundaryCondition, + CellRegister, Contour, Controls, FluidMaterial, @@ -83,18 +90,17 @@ PressureInlet, PressureOutlet, ReportDefinitions, - RunCalculation, - Setup, - CellRegister, ReportFile, ReportPlot, + RunCalculation, + Setup, calculate, iterate, write_case, ) from ansys.fluent.visualization import GraphicsWindow, Monitor -from ansys.units import Quantity, VariableCatalog -from ansys.units.common import Pa, m, s +from ansys.units import VariableCatalog +from ansys.units.common import Pa, s # %% # Launch Fluent session in meshing mode diff --git a/examples/00-fluent/tyler_sofrin_modes.py b/examples/00-fluent/tyler_sofrin_modes.py index 0271711d418..795d01718b7 100644 --- a/examples/00-fluent/tyler_sofrin_modes.py +++ b/examples/00-fluent/tyler_sofrin_modes.py @@ -264,16 +264,16 @@ Pnm = np.zeros((len(varname), len(m_mode))) for n_ind, variable in enumerate(varname): # loop over n modes - for m_ind, m in enumerate(m_mode): # loop over m modes + for m_ind, _m in enumerate(m_mode): # loop over m modes for angle_ind, angle in enumerate( np.arange(0, math.radians(360), math.radians(d_theta)) ): # loop over all angles, in radians - Anm[n_ind][m_ind] += An[n_ind][angle_ind] * math.cos(m * angle) - Bn[n_ind][ + Anm[n_ind][m_ind] += An[n_ind][angle_ind] * math.cos(_m * angle) - Bn[n_ind][ angle_ind - ] * math.sin(m * angle) - Bnm[n_ind][m_ind] += An[n_ind][angle_ind] * math.sin(m * angle) + Bn[n_ind][ + ] * math.sin(_m * angle) + Bnm[n_ind][m_ind] += An[n_ind][angle_ind] * math.sin(_m * angle) + Bn[n_ind][ angle_ind - ] * math.cos(m * angle) + ] * math.cos(_m * angle) Anm[n_ind][m_ind] = Anm[n_ind][m_ind] / (2 * math.pi) * math.radians(d_theta) Bnm[n_ind][m_ind] = Bnm[n_ind][m_ind] / (2 * math.pi) * math.radians(d_theta) Pnm[n_ind][m_ind] = math.sqrt(Anm[n_ind][m_ind] ** 2 + Bnm[n_ind][m_ind] ** 2) From 1ffeecb2b57f4a3deff155c579c5fb0b5c311129 Mon Sep 17 00:00:00 2001 From: Gobot1234 Date: Thu, 19 Feb 2026 09:26:08 +0000 Subject: [PATCH 5/9] fix couple more imports etc --- examples/00-fluent/species_transport.py | 56 ++++++++++++++---------- examples/00-fluent/tyler_sofrin_modes.py | 14 +++--- 2 files changed, 40 insertions(+), 30 deletions(-) diff --git a/examples/00-fluent/species_transport.py b/examples/00-fluent/species_transport.py index 11984eddb83..14ac7fc6539 100644 --- a/examples/00-fluent/species_transport.py +++ b/examples/00-fluent/species_transport.py @@ -89,12 +89,9 @@ from pathlib import Path -from ansys.units import VariableCatalog - import ansys.fluent.core as pyfluent -from ansys.units.common import K, m, Pa, W, s - -from ansys.fluent.core.generated.solver.settings_builtin_261 import Fluxes, General, Iterate, SurfaceIntegrals, WriteCase, WriteCaseData, write_case +from ansys.units import VariableCatalog +from ansys.units.common import K, Pa, W, m, s solver = pyfluent.Solver.from_install(dimension=2) print(solver.get_fluent_version()) @@ -107,23 +104,30 @@ from ansys.fluent.core import FluentVersion # noqa: E402 from ansys.fluent.core.examples import download_file # noqa: E402 from ansys.fluent.core.solver import ( # noqa: E402 + BoundaryCondition, Contour, Energy, + Fluxes, + General, + Graphics, Initialize, + Iterate, Mesh, + Methods, MixtureMaterial, + Monitor, PressureOutlet, RunCalculation, + SolverIntegrals, Species, + SurfaceIntegrals, Vector, VelocityInlet, Viscous, WallBoundary, - BoundaryCondition, - Methods, - Monitor, - SolverIntegrals, - Graphics, + WriteCase, + WriteCaseData, + write_case, ) # %% @@ -341,11 +345,11 @@ # * Species mass fraction for ch4: 1 fuel_inlet = VelocityInlet(solver, name="fuel-inlet") -fuel_inlet.momentum.velocity_magnitude = 80 * m / s +fuel_inlet.momentum.velocity_magnitude = 80 * m / s fuel_inlet.turbulence.turbulence_specification = "Intensity and Hydraulic Diameter" fuel_inlet.turbulence.turbulent_intensity = 0.1 -fuel_inlet.turbulence.hydraulic_diameter = 0.01 * m -fuel_inlet.thermal.temperature = 300 * K +fuel_inlet.turbulence.hydraulic_diameter = 0.01 * m +fuel_inlet.thermal.temperature = 300 * K fuel_inlet.species.species_mass_fraction["ch4"] = 1 # %% @@ -360,11 +364,11 @@ # Always assign reasonable values because backflow may occur during intermediate iterations and could affect the solution stability.* pressure_outlet = PressureOutlet.get(solver, name="pressure-outlet-9") -pressure_outlet.momentum.gauge_pressure = 0 * Pa +pressure_outlet.momentum.gauge_pressure = 0 * Pa pressure_outlet.turbulence.turbulence_specification = "Intensity and Hydraulic Diameter" pressure_outlet.turbulence.backflow_turbulent_intensity = 0.1 -pressure_outlet.turbulence.backflow_hydraulic_diameter = 0.45 * m -pressure_outlet.thermal.backflow_total_temperature = 300 * K +pressure_outlet.turbulence.backflow_hydraulic_diameter = 0.45 * m +pressure_outlet.thermal.backflow_total_temperature = 300 * K pressure_outlet.species.backflow_species_mass_fraction["o2"] = 0.23 # %% @@ -409,7 +413,7 @@ nozzle = WallBoundary.get(solver, name="nozzle") nozzle.thermal.thermal_condition = nozzle.thermal.thermal_condition.HEAT_FLUX -nozzle.thermal.heat_flux = 0 * W * m ** -2 +nozzle.thermal.heat_flux = 0 * W * m**-2 # %% # Verify the state of thermal properties of the nozzle boundary condition after the changes. @@ -451,7 +455,9 @@ # *The Time Scale Factor allows us to further manipulate the computed time step size calculated by Fluent. # Larger time steps can lead to faster convergence. However, if the time step is too large it can lead to solution instability.* -RunCalculation(solver).pseudo_time_settings.time_step_method.time_step_size_scale_factor = 5 +RunCalculation( + solver +).pseudo_time_settings.time_step_method.time_step_size_scale_factor = 5 # %% # Run the calculation for 200 iterations. @@ -475,7 +481,9 @@ # %% # Display filled contours of temperature and save the image to a file. -contour1 = Contour.create(solver, name="contour-temp", field = VariableCatalog.TEMPERATURE) +contour1 = Contour.create( + solver, name="contour-temp", field=VariableCatalog.TEMPERATURE +) contour1.surfaces_list = contour1.surfaces_list.allowed_values() contour1.colorings.banded = True contour1.display() @@ -494,7 +502,7 @@ # %% # Display velocity vectors and save the image to a file. -vector1 = Vector.create(solver, name="vector-vel", surfaces_list = ["interior-4"]) +vector1 = Vector.create(solver, name="vector-vel", surfaces_list=["interior-4"]) vector1.options.scale = 0.01 vector1.vector_opt.fixed_length = True @@ -520,7 +528,7 @@ # %% # Display filled contours of mass fraction of :math:`CH_4` and save the image to a file. -contour2 = Contour.create(solver, name="contour-ch4-mass-fraction", field = "ch4") +contour2 = Contour.create(solver, name="contour-ch4-mass-fraction", field="ch4") contour2.surfaces_list = contour2.surfaces_list.allowed_values() contour2.display() graphics.views.auto_scale() @@ -537,7 +545,7 @@ # %% # Display filled contours of mass fraction of :math:`O_2` and save the image to a file. -contour3 = Contour.create(solver, name="contour-o2-mass-fraction", field = "o2") +contour3 = Contour.create(solver, name="contour-o2-mass-fraction", field="o2") contour3.surfaces_list = contour3.surfaces_list.allowed_values() contour3.display() graphics.views.auto_scale() @@ -553,7 +561,7 @@ # %% # Display filled contours of mass fraction of :math:`CO_2` and save the image to a file. -contour4 = Contour.create(solver, name="contour-co2-mass-fraction", field = "co2") +contour4 = Contour.create(solver, name="contour-co2-mass-fraction", field="co2") contour4.surfaces_list = contour4.surfaces_list.allowed_values() contour4.display() graphics.views.auto_scale() @@ -569,7 +577,7 @@ # %% # Display filled contours of mass fraction of :math:`H_2O` and save the image to a file. -contour5 = Contour.create(solver, name="contour-h2o-mass-fraction", field = "h2o") +contour5 = Contour.create(solver, name="contour-h2o-mass-fraction", field="h2o") contour5.surfaces_list = contour5.surfaces_list.allowed_values() contour5.display() graphics.views.auto_scale() diff --git a/examples/00-fluent/tyler_sofrin_modes.py b/examples/00-fluent/tyler_sofrin_modes.py index 795d01718b7..d3de1f48c9f 100644 --- a/examples/00-fluent/tyler_sofrin_modes.py +++ b/examples/00-fluent/tyler_sofrin_modes.py @@ -268,12 +268,14 @@ for angle_ind, angle in enumerate( np.arange(0, math.radians(360), math.radians(d_theta)) ): # loop over all angles, in radians - Anm[n_ind][m_ind] += An[n_ind][angle_ind] * math.cos(_m * angle) - Bn[n_ind][ - angle_ind - ] * math.sin(_m * angle) - Bnm[n_ind][m_ind] += An[n_ind][angle_ind] * math.sin(_m * angle) + Bn[n_ind][ - angle_ind - ] * math.cos(_m * angle) + Anm[n_ind][m_ind] += ( # fmt: skip + An[n_ind][angle_ind] * math.cos(_m * angle) + - Bn[n_ind][angle_ind] * math.sin(_m * angle) + ) + Bnm[n_ind][m_ind] += ( # fmt: skip + An[n_ind][angle_ind] * math.sin(_m * angle) + + Bn[n_ind][angle_ind] * math.cos(_m * angle) + ) Anm[n_ind][m_ind] = Anm[n_ind][m_ind] / (2 * math.pi) * math.radians(d_theta) Bnm[n_ind][m_ind] = Bnm[n_ind][m_ind] / (2 * math.pi) * math.radians(d_theta) Pnm[n_ind][m_ind] = math.sqrt(Anm[n_ind][m_ind] ** 2 + Bnm[n_ind][m_ind] ** 2) From 79f0eb6c102159650e919f01cf0452186bf250f4 Mon Sep 17 00:00:00 2001 From: Gobot1234 Date: Thu, 19 Feb 2026 09:37:26 +0000 Subject: [PATCH 6/9] variable rename --- examples/00-fluent/tyler_sofrin_modes.py | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/examples/00-fluent/tyler_sofrin_modes.py b/examples/00-fluent/tyler_sofrin_modes.py index d3de1f48c9f..30488aa64e7 100644 --- a/examples/00-fluent/tyler_sofrin_modes.py +++ b/examples/00-fluent/tyler_sofrin_modes.py @@ -165,7 +165,7 @@ # .. image:: ../../_static/var_names.jpg # :alt: variable names -varname = [ +var_names = [ "mean-static-pressure-dataset", "dft-static-pressure_10.00kHz-ta", "dft-static-pressure-1_21.43kHz-ta", @@ -191,12 +191,12 @@ ####################################################################################### # Compute Fourier coefficients at each monitor point (An, Bn) # ===================================================================================== -An = np.zeros((len(varname), int(360 / d_theta))) -Bn = np.zeros((len(varname), int(360 / d_theta))) +An = np.zeros((len(var_names), int(360 / d_theta))) +Bn = np.zeros((len(var_names), int(360 / d_theta))) report_defs = ReportDefinitions(solver) for angle_ind, angle in enumerate(range(0, 360, d_theta)): - for n_ind, variable in enumerate(varname): + for n_ind, variable in enumerate(var_names): if variable.startswith("mean"): mag_report = report_defs.surface.create( name="mag-report", @@ -241,7 +241,7 @@ writer = csv.writer(f) writer.writerow(["n", "theta", "An", "Bn"]) - for n_ind, variable in enumerate(varname): + for n_ind, variable in enumerate(var_names): for ind, _ in enumerate(An[n_ind, :]): writer.writerow( [n_mode[n_ind], ind * d_theta, An[n_ind, ind], Bn[n_ind, ind]] @@ -259,11 +259,11 @@ m_mode = range(-m_max, m_max + m_inc, m_inc) # Initialize solution matrices with zeros -Anm = np.zeros((len(varname), len(m_mode))) -Bnm = np.zeros((len(varname), len(m_mode))) -Pnm = np.zeros((len(varname), len(m_mode))) +Anm = np.zeros((len(var_names), len(m_mode))) +Bnm = np.zeros((len(var_names), len(m_mode))) +Pnm = np.zeros((len(var_names), len(m_mode))) -for n_ind, variable in enumerate(varname): # loop over n modes +for n_ind, variable in enumerate(var_names): # loop over n modes for m_ind, _m in enumerate(m_mode): # loop over m modes for angle_ind, angle in enumerate( np.arange(0, math.radians(360), math.radians(d_theta)) From 80092df67c49ec2257b7964af549f696ad7b27e1 Mon Sep 17 00:00:00 2001 From: Gobot1234 Date: Mon, 16 Mar 2026 11:19:35 +0000 Subject: [PATCH 7/9] update allowed_values to all --- .../Electrolysis_Modeling_workflow.py | 19 +++++++++---------- .../Modeling_solidification_workflow.py | 2 +- 2 files changed, 10 insertions(+), 11 deletions(-) diff --git a/examples/00-fluent/Electrolysis_Modeling_workflow.py b/examples/00-fluent/Electrolysis_Modeling_workflow.py index f3f264fac48..124aac17f30 100644 --- a/examples/00-fluent/Electrolysis_Modeling_workflow.py +++ b/examples/00-fluent/Electrolysis_Modeling_workflow.py @@ -130,13 +130,13 @@ # Display mesh # ------------ graphics = Graphics(solver) -mesh = Mesh(solver, new_instance_name="mesh-1") +mesh = Mesh(solver).create(name="mesh-1") graphics.picture.x_resolution = 650 # Horizontal resolution for clear visualization graphics.picture.y_resolution = 450 # Vertical resolution matching typical aspect ratio -all_walls = mesh.surfaces_list.allowed_values() +all_walls = mesh.surfaces_list.all() mesh.surfaces_list = all_walls mesh.options.edges = True @@ -213,21 +213,20 @@ # ---------------------- materials = Materials(solver) -SolidMaterial.create( - solver, name="collector-default", electric_conductivity=20000 * S / m +solid_material = SolidMaterial(solver) +solid_material.create( + name="collector-default", electric_conductivity=20000 * S / m ) +solid_material.create(name="porous-default", electric_conductivity=20000 * S / m) -SolidMaterial.create(solver, name="porous-default", electric_conductivity=20000 * S / m) - -SolidMaterial.create( - solver, +solid_material.create( name="catalyst-default", electrical_conductivity=5000 * S / m, dual_electric_conductivity=4.5 * S / m, ) -SolidMaterial.create( - solver, name="electrolyte-default", dual_electric_conductivity=11 * S / m +solid_material.create( + name="electrolyte-default", dual_electric_conductivity=11 * S / m ) # %% diff --git a/examples/00-fluent/Modeling_solidification_workflow.py b/examples/00-fluent/Modeling_solidification_workflow.py index 5bf0f62f44a..662765faaf6 100644 --- a/examples/00-fluent/Modeling_solidification_workflow.py +++ b/examples/00-fluent/Modeling_solidification_workflow.py @@ -134,7 +134,7 @@ graphics.picture.x_resolution = 650 # Horizontal resolution for clear visualization graphics.picture.y_resolution = 450 # Vertical resolution matching typical aspect ratio -all_walls = mesh.surfaces_list.allowed_values() +all_walls = mesh.surfaces_list.all() mesh.surfaces_list = all_walls mesh.options.edges = True From 4a54bea456af081c343a9a963a7211620469dd1b Mon Sep 17 00:00:00 2001 From: James Hilton-Balfe Date: Tue, 14 Apr 2026 10:16:49 +0100 Subject: [PATCH 8/9] Update modeling_cavitation.py --- examples/00-fluent/modeling_cavitation.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/examples/00-fluent/modeling_cavitation.py b/examples/00-fluent/modeling_cavitation.py index d85fbcbe420..39091e61f0d 100644 --- a/examples/00-fluent/modeling_cavitation.py +++ b/examples/00-fluent/modeling_cavitation.py @@ -86,7 +86,7 @@ PressureInlet, PressureOutlet, Residual, - RunCalculation, git apply --check -p1 C:\ANSYSDev\pyfluent\the-patch.utf8.diff git apply --check -p1 C:\ANSYSDev\pyfluent\the-patch.utf8.diff Get-Content C:\ANSYSDev\pyfluent\patch.patch -TotalCount 60 Get-Content C:\ANSYSDev\pyfluent\patch.patch -TotalCount 60write_case_data + RunCalculation, ) from ansys.units import VariableCatalog from ansys.units.common import Pa, kg, m, s From 13b5ddda31dbce20da581dfc2c7ae6ce4950a753 Mon Sep 17 00:00:00 2001 From: Gobot1234 Date: Thu, 14 May 2026 17:30:07 +0100 Subject: [PATCH 9/9] update some examples to new meshing workflow --- examples/00-fluent/ahmed_body_workflow.py | 152 +++++++--------- examples/00-fluent/battery_pack.py | 38 ++-- examples/00-fluent/brake.py | 21 ++- .../00-fluent/catalytic_converter_workflow.py | 167 +++++++----------- examples/00-fluent/radiation_headlamp.py | 20 ++- 5 files changed, 166 insertions(+), 232 deletions(-) diff --git a/examples/00-fluent/ahmed_body_workflow.py b/examples/00-fluent/ahmed_body_workflow.py index 8694f97ac42..831b57b491c 100644 --- a/examples/00-fluent/ahmed_body_workflow.py +++ b/examples/00-fluent/ahmed_body_workflow.py @@ -66,6 +66,8 @@ import ansys.fluent.core as pyfluent from ansys.fluent.core import examples +import ansys.fluent.core.meshing.meshing_workflow_new as mesh_wf_new +from ansys.fluent.core.session_pure_meshing import PureMeshing from ansys.fluent.core.solver import ( FluidMaterial, Initialization, @@ -89,7 +91,7 @@ ####################################################################################### # Launch Fluent session with meshing mode and print Fluent version # ===================================================================================== -meshing = pyfluent.Meshing.from_install() +meshing: PureMeshing = pyfluent.Meshing.from_install() print(meshing.get_fluent_version()) ####################################################################################### @@ -100,7 +102,7 @@ # Initialize the Meshing Workflow # ===================================================================================== -workflow = meshing.workflow +workflow: mesh_wf_new.WatertightMeshingWorkflow = meshing.watertight(legacy=False) filenames = { "Windows": "ahmed_body_20_0degree_boi_half.scdoc", @@ -114,117 +116,89 @@ ) meshing.upload(geometry_filename) -workflow.InitializeWorkflow(WorkflowType="Watertight Geometry") -workflow.TaskObject["Import Geometry"].Arguments = {"FileName": geometry_filename} -workflow.TaskObject["Import Geometry"].Execute() +workflow.application.import_geometry(file_name=geometry_filename) ####################################################################################### # Add Local Face Sizing # ===================================================================================== -add_local_sizing = workflow.TaskObject["Add Local Sizing"] -add_local_sizing.Arguments = { - "AddChild": "yes", - "BOIControlName": "facesize_front", - "BOIFaceLabelList": ["wall_ahmed_body_front"], - "BOIGrowthRate": 1.15, - "BOISize": 8, -} -add_local_sizing.Execute() - -add_local_sizing.InsertCompoundChildTask() -workflow.TaskObject["Add Local Sizing"].Execute() -add_local_sizing = workflow.TaskObject["Add Local Sizing"] -add_local_sizing.Arguments = { - "AddChild": "yes", - "BOIControlName": "facesize_rear", - "BOIFaceLabelList": ["wall_ahmed_body_rear"], - "BOIGrowthRate": 1.15, - "BOISize": 5, -} -add_local_sizing.Execute() - -add_local_sizing.InsertCompoundChildTask() -workflow.TaskObject["Add Local Sizing"].Execute() -add_local_sizing = workflow.TaskObject["Add Local Sizing"] -add_local_sizing.Arguments = { - "AddChild": "yes", - "BOIControlName": "facesize_main", - "BOIFaceLabelList": ["wall_ahmed_body_main"], - "BOIGrowthRate": 1.15, - "BOISize": 12, -} -add_local_sizing.Execute() + +add_local_sizing = workflow.application.add_local_sizing_wtm( + add_child=True, + boi_control_name="facesize_front", + boi_face_label_list=["wall_ahmed_body_front"], + boi_growth_rate=1.15, + boi_size=8, +) + +workflow.application.add_local_sizing_wtm( + add_child=True, + boi_control_name="facesize_rear", + boi_face_label_list=["wall_ahmed_body_rear"], + boi_growth_rate=1.15, + boi_size=5, +) + + +workflow.application.add_local_sizing_wtm( + add_child=True, + boi_control_name="facesize_main", + boi_face_label_list=["wall_ahmed_body_main"], + boi_growth_rate=1.15, + boi_size=12, +) ####################################################################################### # Add BOI (Body of Influence) Sizing # ===================================================================================== -add_boi_sizing = workflow.TaskObject["Add Local Sizing"] -add_boi_sizing.InsertCompoundChildTask() -add_boi_sizing.Arguments = { - "AddChild": "yes", - "BOIControlName": "boi_1", - "BOIExecution": "Body Of Influence", - "BOIFaceLabelList": ["ahmed_body_20_0degree_boi_half-boi"], - "BOISize": 20, -} -add_boi_sizing.Execute() -add_boi_sizing.InsertCompoundChildTask() +workflow.application.add_local_sizing_wtm( + add_child=True, + boi_control_name="boi_1", + boi_execution="Body Of Influence", # Using a string as no enum is currently available + boi_face_label_list=["ahmed_body_20_0degree_boi_half-boi"], + boi_size=20, +) ####################################################################################### # Add Surface Mesh Sizing # ===================================================================================== -generate_surface_mesh = workflow.TaskObject["Generate the Surface Mesh"] -generate_surface_mesh.Arguments = { - "CFDSurfaceMeshControls": { - "CurvatureNormalAngle": 12, - "GrowthRate": 1.15, - "MaxSize": 50, - "MinSize": 1, - "SizeFunctions": "Curvature", - } -} +workflow.application.create_surface_mesh.cfd_surface_mesh_controls( # TODO double check this works (new_meshing_workflows.rst kinda implies it does) + curvature_normal_angle=12, + growth_rate=1.15, + max_size=50, + min_size=1, + size_functions="curvature", # Using a string as no enum is currently available +) -generate_surface_mesh.Execute() -generate_surface_mesh.InsertNextTask(CommandName="ImproveSurfaceMesh") -improve_surface_mesh = workflow.TaskObject["Improve Surface Mesh"] -improve_surface_mesh.Arguments.update_dict({"FaceQualityLimit": 0.4}) -improve_surface_mesh.Execute() +workflow.application.improve_surface_mesh(face_quality_limit=0.4) ####################################################################################### # Describe Geometry, Update Boundaries, Update Regions # ===================================================================================== -workflow.TaskObject["Describe Geometry"].Arguments = { - "CappingRequired": "Yes", - "SetupType": "The geometry consists of only fluid regions with no voids", -} -workflow.TaskObject["Describe Geometry"].Execute() -workflow.TaskObject["Update Boundaries"].Execute() -workflow.TaskObject["Update Regions"].Execute() +workflow.application.describe_geometry( + capping_required=True, + setup_type="fluid", # Using a string as no enum is currently available +) +update_boundaries = workflow.application.update_boundaries() +update_regions = workflow.application.update_regions() ####################################################################################### # Add Boundary Layers # ===================================================================================== -add_boundary_layers = workflow.TaskObject["Add Boundary Layers"] -add_boundary_layers.AddChildToTask() -add_boundary_layers.InsertCompoundChildTask() -workflow.TaskObject["smooth-transition_1"].Arguments.update_dict( - { - "BLControlName": "smooth-transition_1", - "NumberOfLayers": 14, - "Rate": 1.15, - "TransitionRatio": 0.5, - } +workflow.application.add_boundary_layers( + control_name="smooth-transition_1", + number_of_layers=14, + rate=1.15, + transition_ratio=0.5, ) -add_boundary_layers.Execute() ####################################################################################### # Generate the Volume Mesh # ===================================================================================== -generate_volume_mesh = workflow.TaskObject["Generate the Volume Mesh"] -generate_volume_mesh.Arguments.update_dict({"VolumeFill": "poly-hexcore"}) -generate_volume_mesh.Execute() +workflow.application.create_volume_mesh_wtm( + volume_fill="poly-hexcore" # Using a string as no enum is currently available +) ####################################################################################### # Switch to the Solver Mode @@ -259,7 +233,7 @@ ####################################################################################### # Define Materials # ===================================================================================== -air = FluidMaterial.get(solver, name="air") +air = FluidMaterial(solver).get("air") air.density = density viscous = Viscous(solver=solver) @@ -270,7 +244,7 @@ ####################################################################################### # Define Boundary Conditions # ===================================================================================== -inlet = VelocityInlet.get(solver, name="inlet") +inlet = VelocityInlet(solver).get(name="inlet") inlet.turbulence.turb_intensity = 0.05 inlet.momentum.velocity.value = inlet_velocity inlet.turbulence.turb_viscosity_ratio = 5 @@ -297,7 +271,7 @@ discretization_scheme["k"] = "second-order-upwind" discretization_scheme["epsilon"] = "second-order-upwind" initialization = Initialization(solver) -initialization.defaults.k = 0.000001 +initialization.defaults.k = 1e-6 residual = Residual(solver) for monitor in ( @@ -342,7 +316,7 @@ ####################################################################################### # Post-Processing Workflow # ===================================================================================== -iso = IsoSurface.create(solver, name="xmid", field="x-coordinate", iso_values=[0 * m]) +iso = IsoSurface(solver).create(name="xmid", field="x-coordinate", iso_values=[0 * m]) velocity_mag = Contour( solver=solver, field=VariableCatalog.VELOCITY_MAGNITUDE, surfaces=["xmid"] diff --git a/examples/00-fluent/battery_pack.py b/examples/00-fluent/battery_pack.py index f9c171abb7b..2f6631408a6 100644 --- a/examples/00-fluent/battery_pack.py +++ b/examples/00-fluent/battery_pack.py @@ -139,7 +139,7 @@ # ------------ graphics = Graphics(solver) -mesh = Mesh.create(solver, name="mesh-1") +mesh = Mesh(solver).create(name="mesh-1") graphics.picture.x_resolution = 650 # Horizontal resolution for clear visualization graphics.picture.y_resolution = 450 # Vertical resolution matching typical aspect ratio @@ -195,10 +195,12 @@ # ---------------- materials = Materials(solver) +solid_material = SolidMaterial(solver) # Active material (cells): conductivity via UDS-0 and UDS-1 -e_material = SolidMaterial.create(solver, name="e_material", chemical_formula="e") -e_material.thermal_conductivity = 20 * W / (m * K) +e_material = solid_material.create( + name="e_material", chemical_formula="e", thermal_conductivity=20 * W / (m * K) +) e_material.uds_diffusivity.option = "defined-per-uds" e_material.uds_diffusivity.uds_diffusivities["uds-0"] = ( 1e6 * S / m @@ -208,8 +210,9 @@ ) # Ionic conductivity # Passive material (busbars & tabs): high constant conductivity -busbar_material = SolidMaterial.create( - solver, name="busbar_material", chemical_formula="bus" +busbar_material = solid_material.create( + name="busbar_material", + chemical_formula="bus", ) busbar_material.uds_diffusivity.option = "value" busbar_material.uds_diffusivity.value = 3.541e7 * S / m # Copper-like conductivity @@ -218,18 +221,19 @@ # Assign materials to cell zones # ------------------------------ +solid_cell_zone = SolidCellZone(solver) # Assign e_material to cell_1 2 and 3 all at once -SolidCellZone.get(solver, name="cell_*").general.material = e_material +solid_cell_zone.get("cell_*").general.material = e_material # Assign busbar_material to bar1 and all passive zones -SolidCellZone.get(solver, name="*bar*|*tabzone*").general.material = busbar_material +solid_cell_zone.get("*bar*|*tabzone*").general.material = busbar_material # %% # Boundary conditions # ------------------- # Convection on all walls (tabs, busbars, cells) -wall_bc = WallBoundary.get(solver, name="wall*") +wall_bc = WallBoundary(solver).get("wall*") wall_bc.thermal.thermal_condition = wall_bc.thermal.thermal_condition.CONVECTION wall_bc.thermal.heat_transfer_coeff = 5 * W / (m**2 * K) @@ -264,7 +268,7 @@ ) # Format plot axes -voltage_surface_areaavg = ReportPlot.get(solver, name="voltage_surface_areaavg-rplot") +voltage_surface_areaavg = ReportPlot(solver).get("voltage_surface_areaavg-rplot") voltage_surface_areaavg.axes.x.number_format.precision = 0 # Integer time steps voltage_surface_areaavg.axes.y.number_format.precision = ( 2 # 2 decimal places for voltage @@ -281,7 +285,7 @@ ) # Format plot axes -volume_max_temp = ReportPlot.get(solver, name="volume_max_temp-rplot") +volume_max_temp = ReportPlot(solver).get("volume_max_temp-rplot") volume_max_temp.axes.x.number_format.precision = 0 volume_max_temp.axes.y.number_format.precision = 2 @@ -308,8 +312,7 @@ # --------------- # Current density vector plot -vector = Vector.create( - solver, +vector = Vector(solver).create( name="current-magnitude-vector", vector_field="current-density-j", # A/m² (Current density vector) field="current-magnitude", # A/m² (Magnitude for coloring) @@ -329,8 +332,7 @@ # :alt: Current density vector plot # Temperature contour -temp_contour = Contour.create( - solver, +temp_contour = Contour(solver).create( name="temp_contour", field=VariableCatalog.TEMPERATURE, # K surfaces_list=["tab_n", "tab_p", "wall*"], @@ -347,8 +349,7 @@ # :alt: Temperature contour # Joule heat source contour -joule_contour = Contour.create( - solver, +joule_contour = Contour(solver).create( field="battery-joule-heat-source", # W/m³ surfaces_list=["tab_n", "tab_p", "wall*"], ) @@ -364,10 +365,9 @@ # :alt: Joule heat source contour # Total heat source contour -total_heat_contour = Contour.create( - solver, +total_heat_contour = Contour(solver).create( name="total_heating_contour", - field="total-heat-source", # W/m³ (Joule + reaction heat) + field="total-heat-source", # W/m³ (Joule + reaction heat) # Using a string as no enum is currently available surfaces_list=["tab_n", "tab_p", "wall*"], ) total_heat_contour.colorings.banded = True diff --git a/examples/00-fluent/brake.py b/examples/00-fluent/brake.py index 733a6869c43..4c5178518aa 100644 --- a/examples/00-fluent/brake.py +++ b/examples/00-fluent/brake.py @@ -58,6 +58,7 @@ import ansys.fluent.core as pyfluent from ansys.fluent.core import examples from ansys.fluent.core.solver import ( + CalculationActivity, Controls, Energy, General, @@ -122,7 +123,7 @@ ########################################################################################## # Define disc rotation # -------------------- -discs = SolidCellZone.get(solver, name="disc*") +discs = SolidCellZone(solver).get("disc*") discs.solid_motion.enable = True discs.solid_motion.solid_motion_zone_motion_function = "none" discs.solid_motion.solid_motion_axis_direction = [0, 1, 0] @@ -138,7 +139,9 @@ # ---------------------------------------------- # Wall thickness 0f 2 mm has been assumed and 2e9 w/m3 is the heat generation which # has been calculated from kinetic energy change due to braking. -wall_pad_discs = WallBoundary.get(solver, name="wall-pad-disc*") +wall_boundary = WallBoundary(solver) + +wall_pad_discs = wall_boundary.get("wall-pad-disc*") wall_pad_discs.thermal.q_dot = 2e9 * W / m**3 wall_pad_discs.thermal.wall_thickness = 0.002 * m @@ -148,7 +151,7 @@ # Outer surfaces are applied a constant htc of 100 W/(m2 K) # and 300 K free stream temperature -walls = WallBoundary.get(solver, name="wall-disc*|wall-geom*") +walls = wall_boundary.get("wall-disc*|wall-geom*") walls.thermal.thermal_condition = walls.thermal.thermal_condition.CONVECTION walls.thermal.convection.convective_heat_transfer_coefficient = 100 * W / (m**2 * K) walls.thermal.convection.free_stream_temperature = 300 * K @@ -173,7 +176,7 @@ max_pad_temp = report_defs.volume.create( name="max-pad-temperature", - report_type="volume-max", + report_type=report_defs.volume.report_type.VOLUME_MAX, field=VariableCatalog.TEMPERATURE, cell_zones=["geom-1-innerpad", "geom-1-outerpad"], ) @@ -181,8 +184,8 @@ max_disc_temp = report_defs.volume.create( name="max-disc-temperature", - report_type="volume-max", - field="temperature", + report_type=report_defs.volume.report_type.VOLUME_MAX, + field=VariableCatalog.TEMPERATURE, cell_zones=["disc1", "disc2"], ) @@ -230,7 +233,7 @@ graphics.views.camera.zoom(factor=2) graphics.views.save_view(view_name="animation-view") -solver.solution.calculation_activity.solution_animations.create( +CalculationActivity(solver).solution_animations.create( name="animate-temperature", animate_on="temperature", frequency_of="flow-time", @@ -277,7 +280,9 @@ # Set contour properties # ---------------------- -contour1.range.option = "auto-range-off" +contour1.range.option = ( + "auto-range-off" # Using a string as no enum is currently available. +) contour1.range.auto_range_off.minimum = 300 contour1.range.auto_range_off.maximum = 400 diff --git a/examples/00-fluent/catalytic_converter_workflow.py b/examples/00-fluent/catalytic_converter_workflow.py index 8cf8db94c39..a1061cdf448 100644 --- a/examples/00-fluent/catalytic_converter_workflow.py +++ b/examples/00-fluent/catalytic_converter_workflow.py @@ -100,6 +100,7 @@ import ansys.fluent.core as pyfluent from ansys.fluent.core import examples +import ansys.fluent.core.meshing.meshing_workflow_new as mesh_wf_new from ansys.fluent.core.solver import ( # noqa: E402 CellZoneConditions, Energy, @@ -139,8 +140,7 @@ # Initialize watertight geometry workflow -workflow = meshing.workflow -workflow.InitializeWorkflow(WorkflowType=r"Watertight Geometry") +workflow: mesh_wf_new.WatertightMeshingWorkflow = meshing.watertight(legacy=False) # %% # Import Geometry @@ -160,9 +160,8 @@ save_path=Path.cwd(), ) -workflow.InitializeWorkflow(WorkflowType="Watertight Geometry") -workflow.TaskObject["Import Geometry"].Arguments = {"FileName": geometry_filename} -workflow.TaskObject["Import Geometry"].Execute() +meshing.upload(geometry_filename) +workflow.application.import_geometry(file_name=geometry_filename) # %% # Local Sizing Controls @@ -171,22 +170,18 @@ # Add local sizing for sensor components -workflow.TaskObject["Add Local Sizing"].Arguments = { - "AddChild": "yes", - "BOIControlName": "sensor", - "BOIExecution": "Curvature", - "BOIFaceLabelList": [ +workflow.application.add_local_sizing_wtm( + add_child=True, + boi_control_name="sensor", + boi_execution="Curvature", + boi_face_label_list=[ "sensing_element-65-solid", "sensor_innertube-67-solid", "sensor_protectiontube-66-solid1", ], - "BOIMaxSize": 1.2, - "BOIMinSize": 0.1, -} -workflow.TaskObject["Add Local Sizing"].AddChildToTask() -workflow.TaskObject["Add Local Sizing"].InsertCompoundChildTask() -workflow.TaskObject["Add Local Sizing"].Arguments = {"AddChild": "yes"} -workflow.TaskObject["sensor"].Execute() + boi_max_size=1.2, + boi_min_size=0.1, +) # %% # Surface Mesh Generation @@ -195,15 +190,10 @@ # Configure surface mesh settings -workflow.TaskObject["Generate the Surface Mesh"].Arguments = { - "CFDSurfaceMeshControls": {"MinSize": 1.5}, - "SurfaceMeshPreferences": { - "SMQualityImprove": "yes", - "SMQualityImproveLimit": 0.95, - "ShowSurfaceMeshPreferences": True, - }, -} -workflow.TaskObject["Generate the Surface Mesh"].Execute() +workflow.application.create_surface_mesh.cfd_surface_mesh_controls( + min_size=1.5, +) +workflow.application.improve_surface_mesh(face_quality_limit=0.95) # %% # Geometry Description @@ -212,25 +202,11 @@ # Describe geometry type -workflow.TaskObject["Describe Geometry"].UpdateChildTasks(SetupTypeChanged=False) -workflow.TaskObject["Describe Geometry"].Arguments = { - "SetupType": "The geometry consists of both fluid and solid regions and/or voids" -} -workflow.TaskObject["Describe Geometry"].UpdateChildTasks(SetupTypeChanged=True) - -# Enable capping and wall-to-internal conversion - -workflow.TaskObject["Describe Geometry"].Arguments = { - "CappingRequired": "Yes", - "SetupType": "The geometry consists of both fluid and solid regions and/or voids", -} -workflow.TaskObject["Describe Geometry"].UpdateChildTasks(SetupTypeChanged=False) -workflow.TaskObject["Describe Geometry"].Arguments = { - "CappingRequired": "Yes", - "SetupType": "The geometry consists of both fluid and solid regions and/or voids", - "WallToInternal": "Yes", -} -workflow.TaskObject["Describe Geometry"].Execute() +workflow.application.describe_geometry( + capping_required=True, + setup_type="both", # Using a string as no enum is currently available. # TODO double check this is correct + wall_to_internal=True, +) # %% # Boundary Capping @@ -239,38 +215,24 @@ # Create inlet boundary -workflow.TaskObject["Enclose Fluid Regions (Capping)"].Arguments = { - "LabelSelectionList": ["in1"], - "PatchName": "inlet", -} -workflow.TaskObject["Enclose Fluid Regions (Capping)"].AddChildToTask() -workflow.TaskObject["Enclose Fluid Regions (Capping)"].InsertCompoundChildTask() -workflow.TaskObject["inlet"].Execute() +workflow.application.capping( + label_selection_list=["in1"], + patch_name="inlet", +) # Create outlet boundary as pressure outlet -workflow.TaskObject["Enclose Fluid Regions (Capping)"].Arguments = { - "LabelSelectionList": ["out1"], - "PatchName": "outlet", -} -workflow.TaskObject["Enclose Fluid Regions (Capping)"].AddChildToTask() -workflow.TaskObject["Enclose Fluid Regions (Capping)"].InsertCompoundChildTask() -workflow.TaskObject["outlet"].Execute() - -# Configure outlet as pressure-outlet - -workflow.TaskObject["outlet"].Revert() -workflow.TaskObject["outlet"].Arguments = { - "CompleteLabelSelectionList": ["out1"], - "LabelSelectionList": ["out1"], - "PatchName": "outlet", - "ZoneType": "pressure-outlet", -} -workflow.TaskObject["outlet"].Execute() +workflow.application.capping( + label_selection_list=["out1"], + patch_name="outlet", + complete_label_selection_list=["out1"], + zone_type="pressure-outlet", # Using a string as no enum is currently available. +) + # Update boundaries -workflow.TaskObject["Update Boundaries"].Execute() +workflow.application.update_boundaries() # %% # Region Setup @@ -279,18 +241,16 @@ # Create multiple flow volumes -workflow.TaskObject["Create Regions"].Arguments = {"NumberOfFlowVolumes": 3} -workflow.TaskObject["Create Regions"].Execute() +workflow.application.create_regions(number_of_flow_volumes=3) # Convert solid substrate regions to fluid regions -workflow.TaskObject["Update Regions"].Arguments = { - "OldRegionNameList": ["honeycomb-solid1", "honeycomb_af0-solid1"], - "OldRegionTypeList": ["solid", "solid"], - "RegionNameList": ["fluid:substrate:1", "fluid:substrate:2"], - "RegionTypeList": ["fluid", "fluid"], -} -workflow.TaskObject["Update Regions"].Execute() +workflow.application.update_regions( + old_region_name_list=["honeycomb-solid1", "honeycomb_af0-solid1"], + old_region_type_list=["solid", "solid"], + region_name_list=["fluid:substrate:1", "fluid:substrate:2"], + region_type_list=["fluid", "fluid"], +) # %% # Boundary Layer Mesh @@ -299,13 +259,11 @@ # Add boundary layers -workflow.TaskObject["Add Boundary Layers"].AddChildToTask() -workflow.TaskObject["Add Boundary Layers"].InsertCompoundChildTask() -workflow.TaskObject["smooth-transition_1"].Arguments = { - "BLControlName": "smooth-transition_1" -} - -workflow.TaskObject["smooth-transition_1"].Execute() +workflow.application.add_boundary_layers( + control_name="smooth-transition_1", + number_of_layers=10, + rate=1.1, +) # %% # Volume Mesh Generation @@ -314,10 +272,7 @@ # Generate volume mesh -workflow.TaskObject["Generate the Volume Mesh"].Arguments = { - "VolumeMeshPreferences": {"MergeBodyLabels": "yes"} -} -workflow.TaskObject["Generate the Volume Mesh"].Execute() +workflow.application.create_volume_mesh_wtm(volume_fill="poly-hexcore") # %% # Mesh Quality Check & Write Mesh File @@ -364,11 +319,7 @@ # First, get all wall boundary names and create a mesh object for visualization context all_walls = WallBoundaries(solver).get_object_names() -mesh = Mesh( - solver, - new_instance_name="mesh-1", - surfaces_list=all_walls, -) +mesh = Mesh(solver).create(surfaces_list=all_walls) mesh.options.edges = True mesh.display() graphics.picture.save_picture(file_name="out/catalytic_converter_mesh.png") @@ -454,7 +405,7 @@ # Configure velocity inlet -velocity_inlet = VelocityInlet.get(solver, name="inlet") +velocity_inlet = VelocityInlet(solver).get(name="inlet") velocity_inlet.momentum.velocity_magnitude = 125.0 * m / s velocity_inlet.turbulence.hydraulic_diameter = 0.5 * m velocity_inlet.turbulence.turbulence_specification = "Intensity and Hydraulic Diameter" @@ -462,7 +413,7 @@ # Configure pressure outlet -pressure_outlet = PressureOutlet.get(solver, name="outlet") +pressure_outlet = PressureOutlet(solver).get(name="outlet") pressure_outlet.momentum.gauge_pressure = 0.0 * Pa pressure_outlet.turbulence.backflow_hydraulic_diameter = 0.5 * m pressure_outlet.turbulence.turbulence_specification = "Intensity and Hydraulic Diameter" @@ -626,15 +577,15 @@ # Scene 1: Display velocity vectors with mesh context # Scenes combine multiple graphics objects for comprehensive visualization -velocity_vectors_scene = Scene(solver, new_instance_name="scene-1") -velocity_vectors_scene.graphics_objects.add(name="vector-vel") +velocity_vectors_scene = Scene(solver).create() +velocity_vectors_scene.graphics_objects.add(name=vec) # adding mesh for context which is created earlier steps just after switching to solver velocity_vectors_scene.graphics_objects.add(name="mesh-1") # Configure scene appearance and display settings -scene_1 = Scene.create(solver, name="scene-1") +scene_1 = Scene(solver).create() scene_1.graphics_objects = { "vector-vel": {"name": "vectors"}, # Label for the vector plot "mesh-1": {"transparency": 75}, # Semi-transparent mesh (75% transparent) @@ -653,8 +604,10 @@ # Scene 2: Display static pressure contours with mesh context # This scene focuses on pressure distribution across the catalytic converter -static_pressure_scene = Scene.create(solver, name="scene-2") -pressure_contour_scene = static_pressure_scene.graphics_objects.add(name="contour-ps") +static_pressure_scene = Scene(solver).create() +pressure_contour_scene = static_pressure_scene.graphics_objects.add( + name=pressure_contour +) mesh_1_scene = static_pressure_scene.graphics_objects.add(name="mesh-1") # Configure pressure contour scene settings @@ -676,16 +629,14 @@ # Scene 3: Display velocity magnitude contours with mesh context # This scene shows speed distribution across multiple axial locations -velocity_magnitude_scene = Scene.create(solver, name="scene-3") +velocity_magnitude_scene = Scene(solver).create() velocity_mag_contour_scene = velocity_magnitude_scene.graphics_objects.add( - name="contour-velmag" + name=cont_velmag ) mesh_1_scene = velocity_magnitude_scene.graphics_objects.add(name="mesh-1") # Configure velocity magnitude contour scene settings -velocity_mag_contour_scene.name = ( - velocity_mag_contour # Label for velocity magnitude contour -) +velocity_mag_contour_scene.name = cont_velmag # Label for velocity magnitude contour mesh_1_scene.transparency = 75 # Consistent mesh transparency velocity_magnitude_scene.display() diff --git a/examples/00-fluent/radiation_headlamp.py b/examples/00-fluent/radiation_headlamp.py index 06033637815..a02b3fc5542 100644 --- a/examples/00-fluent/radiation_headlamp.py +++ b/examples/00-fluent/radiation_headlamp.py @@ -77,19 +77,19 @@ import ansys.fluent.core as pyfluent from ansys.fluent.core import examples -from ansys.fluent.core.generated.solver.settings_builtin import CellZoneConditions -from ansys.fluent.core.generated.solver.settings_builtin_261 import BoundaryCondition, ReportPlot, initialize, iterate, write_case, write_case_data from ansys.fluent.core.solver import ( - BoundaryConditions, - Initialization, Models, Monitor, ReportDefinitions, - RunCalculation, SolidCellZone, SolidMaterial, Solution, - WallBoundary, + WallBoundary,BoundaryCondition, + ReportPlot,CellZoneConditions, + initialize, + iterate, + write_case, + write_case_data, ) from ansys.units.common import J, K, W, kg, m @@ -468,9 +468,13 @@ ) monitor = Monitor(solver) -max_temp_surf_report_plot = ReportPlot.create(name="max-temp-rplot", report_defs = [max_temp_surf_report], print = True) +max_temp_surf_report_plot = ReportPlot.create( + name="max-temp-rplot", report_defs=[max_temp_surf_report], print=True +) -max_temp_rplot = ReportPlot.create(name="max-temp-rplot", report_defs = [max_temp_surf_report], print = True) +max_temp_rplot = ReportPlot.create( + name="max-temp-rplot", report_defs=[max_temp_surf_report], print=True +) ############################################################################### # Save case file