Commit: 86c49311a45fa1fb8ebea122ce2f8cc569c6079a
Author: Sebastián Barschkis
Date: Sat Mar 31 17:54:45 2018 +0200
Branches: fluid-mantaflow
https://developer.blender.org/rB86c49311a45fa1fb8ebea122ce2f8cc569c6079a
updated adaptive time stepping
moved adaptive stepping loop out of manta simulation (python) and into big step
(update flows + update obstacles + manta simulation) (blender c)
===================================================================
M intern/mantaflow/extern/manta_fluid_API.h
M intern/mantaflow/intern/FLUID.cpp
M intern/mantaflow/intern/FLUID.h
M intern/mantaflow/intern/manta_fluid_API.cpp
M intern/mantaflow/intern/strings/liquid_script.h
M intern/mantaflow/intern/strings/shared_script.h
M intern/mantaflow/intern/strings/smoke_script.h
M source/blender/blenkernel/BKE_smoke.h
M source/blender/blenkernel/intern/smoke.c
M source/blender/editors/physics/physics_fluid.c
===================================================================
diff --git a/intern/mantaflow/extern/manta_fluid_API.h
b/intern/mantaflow/extern/manta_fluid_API.h
index 93f7c94bee5..da8065dfe72 100644
--- a/intern/mantaflow/extern/manta_fluid_API.h
+++ b/intern/mantaflow/extern/manta_fluid_API.h
@@ -182,6 +182,11 @@ int fluid_bake_mesh_low(struct FLUID* fluid, struct
SmokeModifierData *smd, int
int fluid_bake_mesh_high(struct FLUID* fluid, struct SmokeModifierData *smd,
int framenr);
int fluid_bake_particles_low(struct FLUID* fluid, struct SmokeModifierData
*smd, int framenr);
int fluid_bake_particles_high(struct FLUID* fluid, struct SmokeModifierData
*smd, int framenr);
+void fluid_update_variables_low(struct FLUID* fluid, struct SmokeModifierData
*smd);
+void fluid_update_variables_high(struct FLUID* fluid, struct SmokeModifierData
*smd);
+int fluid_get_frame(struct FLUID* fluid);
+float fluid_get_timestep(struct FLUID* fluid);
+void fluid_adapt_timestep(struct FLUID* fluid);
#ifdef __cplusplus
}
diff --git a/intern/mantaflow/intern/FLUID.cpp
b/intern/mantaflow/intern/FLUID.cpp
index d5e4022e35b..dbe3fbedf9c 100644
--- a/intern/mantaflow/intern/FLUID.cpp
+++ b/intern/mantaflow/intern/FLUID.cpp
@@ -1233,22 +1233,10 @@ int FLUID::bakeDataLow(SmokeModifierData *smd, int
framenr)
cacheDirGeometry[0] = '\0';
cacheDirData[0] = '\0';
- // Get variables at every step -> every property is animatable!
- tmpString += fluid_variables_low;
- tmpString += fluid_adaptive_time_stepping_low;
- if (mUsingSmoke)
- tmpString += smoke_variables_low;
- if (mUsingLiquid)
- tmpString += liquid_variables_low;
- finalString = parseScript(tmpString, smd);
- pythonCommands.push_back(finalString);
- runPythonString(pythonCommands);
-
// Actual call to bake routine
BLI_path_join(cacheDirGeometry, sizeof(cacheDirGeometry),
smd->domain->cache_directory, FLUID_CACHE_DIR_GEOMETRY, NULL);
BLI_path_join(cacheDirData, sizeof(cacheDirData),
smd->domain->cache_directory, FLUID_CACHE_DIR_DATA_LOW, NULL);
ss << "bake_fluid_low_" << mCurrentID << "('" << cacheDirGeometry <<
"', '" << cacheDirData << "', " << framenr << ")";
- pythonCommands.clear();
pythonCommands.push_back(ss.str());
runPythonString(pythonCommands);
@@ -1260,7 +1248,6 @@ int FLUID::bakeDataHigh(SmokeModifierData *smd, int
framenr)
if (with_debug)
std::cout << "FLUID::bakeDataHigh()" << std::endl;
- std::string tmpString, finalString;
std::ostringstream ss;
std::vector<std::string> pythonCommands;
@@ -1268,16 +1255,6 @@ int FLUID::bakeDataHigh(SmokeModifierData *smd, int
framenr)
cacheDirDataLow[0] = '\0';
cacheDirDataHigh[0] = '\0';
- // Get variables at every step -> every property is animatable!
- tmpString += fluid_variables_high;
- tmpString += fluid_adaptive_time_stepping_high;
- if (mUsingSmoke)
- tmpString += smoke_variables_high;
- if (mUsingLiquid)
- tmpString += liquid_variables_high;
- finalString = parseScript(tmpString, smd);
- pythonCommands.push_back(finalString);
-
// Actual call to bake routine
BLI_path_join(cacheDirDataLow, sizeof(cacheDirDataLow),
smd->domain->cache_directory, FLUID_CACHE_DIR_DATA_LOW, NULL);
BLI_path_join(cacheDirDataHigh, sizeof(cacheDirDataHigh),
smd->domain->cache_directory, FLUID_CACHE_DIR_DATA_HIGH, NULL);
@@ -1380,6 +1357,37 @@ int FLUID::bakeParticlesHigh(SmokeModifierData *smd, int
framenr)
runPythonString(pythonCommands);
return 1;
}
+void FLUID::updateVariablesLow(SmokeModifierData *smd)
+{
+ std::string tmpString, finalString;
+ std::vector<std::string> pythonCommands;
+
+ tmpString += fluid_variables_low;
+ if (mUsingSmoke)
+ tmpString += smoke_variables_low;
+ if (mUsingLiquid)
+ tmpString += liquid_variables_low;
+ finalString = parseScript(tmpString, smd);
+ pythonCommands.push_back(finalString);
+
+ runPythonString(pythonCommands);
+}
+
+void FLUID::updateVariablesHigh(SmokeModifierData *smd)
+{
+ std::string tmpString, finalString;
+ std::vector<std::string> pythonCommands;
+
+ tmpString += fluid_variables_high;
+ if (mUsingSmoke)
+ tmpString += smoke_variables_high;
+ if (mUsingLiquid)
+ tmpString += liquid_variables_high;
+ finalString = parseScript(tmpString, smd);
+ pythonCommands.push_back(finalString);
+
+ runPythonString(pythonCommands);
+}
void FLUID::exportSmokeData(SmokeModifierData *smd)
{
@@ -1506,32 +1514,99 @@ void FLUID::exportLiquidData(SmokeModifierData *smd)
FLUID::saveFluidSndPartsData(parent_dir);
}
-void* FLUID::getDataPointer(std::string varName, std::string parentName)
+/* Call Mantaflow python functions through this function. Use isAttribute for
object attributes, e.g. s.cfl (here 's' is varname, 'cfl' functionName, and
isAttribute true) */
+static PyObject* callPythonFunction(std::string varName, std::string
functionName, bool isAttribute=false)
{
- if ((varName == "") && (parentName == "")) return NULL;
+ if ((varName == "") || (functionName == "")) {
+ if (FLUID::with_debug)
+ std::cout << "Missing Python variable name and/or
function name -- name is: " << varName << ", function name is: " <<
functionName << std::endl;
+ return NULL;
+ }
PyGILState_STATE gilstate = PyGILState_Ensure();
+ PyObject *main, *var, *func, *returnedValue;
+
+ // Get pyobject that holds result value
+ main = PyImport_AddModule("__main__");
+ var = PyObject_GetAttrString(main, varName.c_str());
+ func = PyObject_GetAttrString(var, functionName.c_str());
+
+ Py_DECREF(var);
+
+ if (!isAttribute) {
+ returnedValue = PyObject_CallObject(func, NULL);
+ Py_DECREF(func);
+ }
+
+ PyGILState_Release(gilstate);
+ return (!isAttribute) ? returnedValue : func;
+}
+
+static char* pyObjectToString(PyObject* inputObject)
+{
+ PyObject* encoded = PyUnicode_AsUTF8String(inputObject);
+ char *result = PyBytes_AsString(encoded);
+ Py_DECREF(encoded);
+ Py_DECREF(inputObject);
+ return result;
+}
- // Get pyobject that holds pointer address as string
- PyObject* main = PyImport_AddModule("__main__");
- PyObject* gridObject = PyObject_GetAttrString(main, varName.c_str());
- PyObject* func = PyObject_GetAttrString(gridObject, (char*)
"getDataPointer");
- PyObject* returnedValue = PyObject_CallObject(func, NULL);
- PyObject* encoded = PyUnicode_AsUTF8String(returnedValue);
+static double pyObjectToDouble(PyObject* inputObject)
+{
+ // Cannot use PyFloat_AsDouble() since its error check crashes - likely
because of Real (aka float) type in Mantaflow
+ return PyFloat_AS_DOUBLE(inputObject);
+}
+
+static long pyObjectToLong(PyObject* inputObject)
+{
+ return PyLong_AsLong(inputObject);
+}
- // Convert string pointer to void pointer
- std::string pointerString = PyBytes_AsString(encoded);
- std::istringstream in(pointerString);
+static void* stringToPointer(char* inputString)
+{
+ std::string str(inputString);
+ std::istringstream in(str);
void *dataPointer = NULL;
in >> dataPointer;
+ return dataPointer;
+}
+
+int FLUID::getFrame()
+{
+ if (with_debug)
+ std::cout << "FLUID::getFrame()" << std::endl;
- Py_DECREF(gridObject);
- Py_DECREF(func);
- Py_DECREF(returnedValue);
- Py_DECREF(encoded);
+ std::string func = "frame";
+ std::string id = std::to_string(mCurrentID);
+ std::string solver = "s" + id;
- PyGILState_Release(gilstate);
- return dataPointer;
+ return pyObjectToLong(callPythonFunction(solver, func, true));
+}
+
+float FLUID::getTimestep()
+{
+ if (with_debug)
+ std::cout << "FLUID::getTimestep()" << std::endl;
+
+ std::string func = "timestep";
+ std::string id = std::to_string(mCurrentID);
+ std::string solver = "s" + id;
+
+ return pyObjectToDouble(callPythonFunction(solver, func, true));
+}
+
+void FLUID::adaptTimestep()
+{
+ if (with_debug)
+ std::cout << "FLUID::adaptTimestep()" << std::endl;
+
+ std::vector<std::string> pythonCommands;
+ std::ostringstream ss;
+
+ ss << "fluid_adapt_time_step_low_" << mCurrentID << "()";
+ pythonCommands.push_back(ss.str());
+
+ runPythonString(pythonCommands);
}
void FLUID::updateMeshData(const char* filename)
@@ -1750,100 +1825,103 @@ void FLUID::updateParticleData(const char* filename,
bool isSecondary)
void FLUID::updatePointers()
{
if (with_debug)
- std::cout << "Updating pointers low res, ID: " << mCurrentID <<
std::endl;
+ std::cout << "FLUID::updatePointers()" << std::endl;
+ std::string func = "getDataPointer";
std::string id = std::to_string(mCurrentID);
std::string solver = "s" + id;
std::string parts = "pp" + id;
std::string solver_ext = "_" + solver;
std::string parts_ext = "_" + parts;
- mObstacle = (int*) getDataPointer("flags" + solver_ext, solver);
+ mObstacle = (int*)
stringToPointer(pyObjectToString(callPythonFunction("flags" + solver_ext,
func)));
- mVelocityX = (float*) getDataPointer("x_vel" + solver_ext, solver);
- mVelocityY = (float*) getDataPointer("y_vel" + solver_ext, solver);
- mVelocityZ = (float*) getDataPointer("z_vel" + solver_ext, solver);
+ mVelocityX = (float*)
stringToPointer(pyObjectToString(callPythonFunction("x_vel" + solver_ext,
func)));
+ mVelocityY = (float*)
stringToPointer(pyObjectToString(callPythonFunction("y_vel" + solver_ext,
func)));
+ mVelocityZ = (float*)
stringToPointer(pyObjectToString(callPythonFunction("z_vel" + solver_ext,
func)));
- mForceX = (float*) getDataPointer("x_force" + solver_ext, solver);
- mForceY = (float*) getDataPointer("y_force" + solver_ext, solver);
- mForceZ = (float*) getDataPointer("z_force" + solver_ext, solver);
+ mForceX = (float*)
stringToPointer(pyObjectToString(callPythonFunction("x_force" + solver_ext,
func)));
+ mForceY = (float*)
stringToPointer(pyObjectToString(callPythonFunction("y_force" + solver_ext,
func)));
+ mForceZ = (float*)
stringToPointer(pyObjectToString(callPythonFunction("z_force" + solver_ext,
func)));
- mPhiOutIn = (float*) getDataPointer("phiOutIn" + solver_ext, solver);
- mFlowType = (int*) getDataPointer("flowType" + solver_ext,
solver);
- mNumFlow = (int*) getDataPointer("numFlow" + solver_ext,
solver);
+ mPhiOutIn = (float*)
stringToPointer(pyObjectToString(callPythonFunction("phiOutIn" + solver_ext,
func)));
+ mFlowType = (int*)
stringToPointer(pyObjectToString(callPythonFunction("flowType" + solver_ext,
func)));
+ mNumFlow = (int*)
stringToPointer(pyObjectToString(callPythonFunction("numFlow" + solver_e
@@ Diff output truncated at 10240 characters. @@
_______________________________________________
Bf-blender-cvs mailing list
[email protected]
https://lists.blender.org/mailman/listinfo/bf-blender-cvs