static gboolean preview_event_scroll (GtkWidget *widget, GdkEventScroll *event, GschemToplevel *w_current) { if (!PREVIEW (widget)->active) { return TRUE; } return x_event_scroll (widget, event, PREVIEW (widget)->preview_w_current); }
/*! \brief Completes initialitation of the widget after realization. * \par Function Description * This function terminates the initialization of preview's GschemToplevel * and TOPLEVEL environments after the widget has been realized. * * It creates a preview page in the TOPLEVEL environment. * * \param [in] widget The preview widget. * \param [in] user_data Unused user data. */ static void preview_callback_realize (GtkWidget *widget, gpointer user_data) { Preview *preview = PREVIEW (widget); GschemToplevel *preview_w_current = preview->preview_w_current; GschemPageView *preview_view = GSCHEM_PAGE_VIEW (preview); g_return_if_fail (preview_view != NULL); PAGE *preview_page = preview_view->page; g_return_if_fail (preview_page != NULL); TOPLEVEL *preview_toplevel = preview_page->toplevel; g_return_if_fail (preview_toplevel != NULL); preview_w_current->window = preview_w_current->drawing_area->window; gtk_widget_grab_focus (preview_w_current->drawing_area); preview_w_current->win_width = preview_w_current->drawing_area->allocation.width; preview_w_current->win_height = preview_w_current->drawing_area->allocation.height; preview_w_current->drawable = preview_w_current->window; x_window_setup_gc (preview_w_current); gschem_page_view_zoom_extents (preview_view, NULL); }
/*! \brief Redraws the view when widget is exposed. * \par Function Description * It redraws the preview pixmap every time the widget is exposed. * * \param [in] widget The preview widget. * \param [in] event The event structure. * \param [in] user_data Unused user data. * \returns FALSE to propagate the event further. */ static gboolean preview_callback_expose (GtkWidget *widget, GdkEventExpose *event, gpointer user_data) { Preview *preview = PREVIEW (widget); GSCHEM_TOPLEVEL *preview_w_current = preview->preview_w_current; GdkRectangle *rectangles; int n_rectangles; cairo_t *save_cr; PangoLayout *save_pl; save_cr = preview_w_current->cr; save_pl = preview_w_current->pl; preview_w_current->cr = gdk_cairo_create (widget->window); preview_w_current->pl = pango_cairo_create_layout (preview_w_current->cr); gdk_region_get_rectangles (event->region, &rectangles, &n_rectangles); o_redraw_rects (preview_w_current, rectangles, n_rectangles); g_free (rectangles); g_object_unref (preview_w_current->pl); cairo_destroy (preview_w_current->cr); preview_w_current->cr = save_cr; preview_w_current->pl = save_pl; return FALSE; }
/*! \brief Handles the press on a mouse button. * \par Function Description * It handles the user inputs. * * Three action are available: zoom in, pan and zoom out on preview display. * * \param [in] widget The preview widget. * \param [in] event The event structure. * \param [in] user_data Unused user data. * \returns FALSE to propagate the event further. */ static gboolean preview_callback_button_press (GtkWidget *widget, GdkEventButton *event, gpointer user_data) { Preview *preview = PREVIEW (widget); GSCHEM_TOPLEVEL *preview_w_current = preview->preview_w_current; gint wx, wy; if (!preview->active) { return TRUE; } switch (event->button) { case 1: /* left mouse button: zoom in */ a_zoom (preview_w_current, ZOOM_IN, HOTKEY, A_PAN_DONT_REDRAW); o_invalidate_all (preview_w_current); break; case 2: /* middle mouse button: pan */ if (!x_event_get_pointer_position(preview_w_current, FALSE, &wx, &wy)) return FALSE; a_pan (preview_w_current, wx, wy); break; case 3: /* right mouse button: zoom out */ a_zoom (preview_w_current, ZOOM_OUT, HOTKEY, A_PAN_DONT_REDRAW); o_invalidate_all (preview_w_current); break; } return FALSE; }
/*! \brief Completes initialitation of the widget after realization. * \par Function Description * This function terminates the initialization of preview's GSCHEM_TOPLEVEL * and TOPLEVEL environments after the widget has been realized. * * It creates a preview page in the TOPLEVEL environment. * * \param [in] widget The preview widget. * \param [in] user_data Unused user data. */ static void preview_callback_realize (GtkWidget *widget, gpointer user_data) { Preview *preview = PREVIEW (widget); GSCHEM_TOPLEVEL *preview_w_current = preview->preview_w_current; TOPLEVEL *preview_toplevel = preview_w_current->toplevel; PAGE *preview_page; preview_w_current->window = preview_w_current->drawing_area->window; gtk_widget_grab_focus (preview_w_current->drawing_area); preview_toplevel->width = preview_w_current->drawing_area->allocation.width; preview_toplevel->height = preview_w_current->drawing_area->allocation.height; preview_w_current->win_width = preview_toplevel->width; preview_w_current->win_height = preview_toplevel->height; preview_w_current->drawable = preview_w_current->window; x_window_setup_gc (preview_w_current); preview_page = s_page_new (preview_toplevel, "unknown"); s_page_goto (preview_toplevel, preview_page); a_zoom_extents(preview_w_current, s_page_objects (preview_page), A_PAN_DONT_REDRAW); o_invalidate_all (preview_w_current); }
static gboolean preview_event_configure (GtkWidget *widget, GdkEventConfigure *event, gpointer user_data) { gboolean retval; GschemToplevel *preview_w_current = PREVIEW (widget)->preview_w_current; retval = x_event_configure (GSCHEM_PAGE_VIEW (widget), event, preview_w_current); return retval; }
static gboolean preview_event_configure (GtkWidget *widget, GdkEventConfigure *event, gpointer user_data) { gboolean retval; GSCHEM_TOPLEVEL *preview_w_current = PREVIEW (widget)->preview_w_current; PAGE *preview_page = preview_w_current->toplevel->page_current; retval = x_event_configure (widget, event, preview_w_current); if (preview_page != NULL) { a_zoom_extents(preview_w_current, s_page_objects (preview_page), 0); } return retval; }
static void preview_dispose (GObject *self) { Preview *preview = PREVIEW (self); GschemToplevel *preview_w_current = preview->preview_w_current; if (preview_w_current != NULL) { preview_w_current->drawing_area = NULL; x_window_free_gc (preview_w_current); gschem_toplevel_free (preview_w_current); preview->preview_w_current = NULL; } G_OBJECT_CLASS (preview_parent_class)->dispose (self); }
static void preview_set_property (GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { Preview *preview = PREVIEW (object); GSCHEM_TOPLEVEL *preview_w_current = preview->preview_w_current; g_assert (preview_w_current != NULL); switch(property_id) { case PROP_FILENAME: if (preview->buffer != NULL) { g_free (preview->buffer); preview->buffer = NULL; g_object_notify (object, "buffer"); } g_free (preview->filename); preview->filename = g_strdup (g_value_get_string (value)); preview_update (preview); break; case PROP_BUFFER: if (preview->filename != NULL) { g_free (preview->filename); preview->filename = NULL; g_object_notify (object, "filename"); } g_free (preview->buffer); preview->buffer = g_strdup (g_value_get_string (value)); preview_update (preview); break; case PROP_ACTIVE: preview->active = g_value_get_boolean (value); preview_update (preview); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec); } }
static void preview_dispose (GObject *self) { Preview *preview = PREVIEW (self); GSCHEM_TOPLEVEL *preview_w_current = preview->preview_w_current; if (preview_w_current != NULL) { preview_w_current->drawing_area = NULL; x_window_free_gc (preview_w_current); s_toplevel_delete (preview_w_current->toplevel); g_free (preview_w_current); preview->preview_w_current = NULL; } G_OBJECT_CLASS (preview_parent_class)->dispose (self); }
static void preview_get_property (GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { Preview *preview = PREVIEW (object); switch(property_id) { case PROP_FILENAME: g_value_set_string (value, preview_get_filename (preview)); break; case PROP_ACTIVE: g_value_set_boolean (value, preview->active); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec); } }
/*! \brief Updates the preview when the selection changes. * \par Function Description * This is the callback function connected to the 'update-preview' * signal of the <B>GtkFileChooser</B>. * * It updates the preview widget with the name of the newly selected * file. * * \param [in] chooser The file chooser to add the preview to. * \param [in] user_data A pointer on the preview widget. */ static void x_fileselect_callback_update_preview (GtkFileChooser *chooser, gpointer user_data) { Preview *preview = PREVIEW (user_data); gchar *filename, *preview_filename = NULL; filename = gtk_file_chooser_get_preview_filename (chooser); if (filename != NULL && !g_file_test (filename, G_FILE_TEST_IS_DIR)) { preview_filename = filename; } /* update preview */ g_object_set (preview, "filename", preview_filename, "active", (preview_filename != NULL), NULL); g_free (filename); }
/*! \brief Handles the press on a mouse button. * \par Function Description * It handles the user inputs. * * Three action are available: zoom in, pan and zoom out on preview display. * * \param [in] widget The preview widget. * \param [in] event The event structure. * \param [in] user_data Unused user data. * \returns FALSE to propagate the event further. */ static gboolean preview_callback_button_press (GtkWidget *widget, GdkEventButton *event, gpointer user_data) { Preview *preview = PREVIEW (widget); GschemToplevel *preview_w_current = preview->preview_w_current; gint wx, wy; if (!preview->active) { return TRUE; } switch (event->button) { case 1: /* left mouse button: zoom in */ a_zoom (preview_w_current, GSCHEM_PAGE_VIEW (preview), ZOOM_IN, HOTKEY); gschem_page_view_invalidate_all (GSCHEM_PAGE_VIEW (widget)); break; case 2: /* middle mouse button: pan */ if (!x_event_get_pointer_position(preview_w_current, FALSE, &wx, &wy)) return FALSE; gschem_page_view_pan (GSCHEM_PAGE_VIEW (preview), wx, wy); break; case 3: /* right mouse button: zoom out */ a_zoom (preview_w_current, GSCHEM_PAGE_VIEW (preview), ZOOM_OUT, HOTKEY); gschem_page_view_invalidate_all (GSCHEM_PAGE_VIEW (widget)); break; } return FALSE; }
static void preview_get_property (GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { Preview *preview = PREVIEW (object); GSCHEM_TOPLEVEL *preview_w_current = preview->preview_w_current; switch(property_id) { case PROP_FILENAME: g_assert (preview_w_current != NULL); /* return the filename of the current page in toplevel */ g_value_set_string (value, preview_w_current->toplevel->page_current->page_filename); break; case PROP_ACTIVE: g_value_set_boolean (value, preview->active); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec); } }
OP_ERROR SOP_CudaParticles::cookMySop(OP_Context &context) { oldf = f; f = context.getFrame(); GEO_ParticleVertex* pvtx; double t = context.getTime(); particlesSystem->dt = 1/(OPgetDirector()->getChannelManager()->getSamplesPerSec() * SUBSTEPS(t)); particlesSystem->preview = PREVIEW(t); particlesSystem->partsLife = LIFE(t); particlesSystem->partsLifeVar = LIFEVAR(t); particlesSystem->velDamp = VELDAMP(t); particlesSystem->gravityStrength = GRAVITYSTR(t); particlesSystem->gravityDir = cu::make_float3(GRAVITYX(t),GRAVITYY(t),GRAVITYZ(t)); particlesSystem->fluidStrength = FLUIDSTR(t); particlesSystem->noiseAmp = cu::make_float3(NOISEAMP(t),NOISEAMP(t),NOISEAMP(t)); particlesSystem->noiseOct = NOISEOCT(t); particlesSystem->noiseFreq = NOISEFREQ(t); particlesSystem->noiseLac = NOISELACUN(t); particlesSystem->noiseOffset = cu::make_float3(NOISEOFFSETX(t),NOISEOFFSETY(t),NOISEOFFSETZ(t)); particlesSystem->pointSize = POINTSIZE(t); particlesSystem->opacity = OPACITY(t); particlesSystem->startColor = cu::make_float3(STARTCOLORX(t),STARTCOLORY(t),STARTCOLORZ(t)); particlesSystem->endColor = cu::make_float3(ENDCOLORX(t),ENDCOLORY(t),ENDCOLORZ(t)); UT_Interrupt *boss; OP_Node::flags().timeDep = 1; if (error() < UT_ERROR_ABORT) { boss = UTgetInterrupt(); // Start the interrupt server if (boss->opStart("Building Particles")){ //gdp->clearAndDestroy(); static float zero = 0.0; GB_AttributeRef partsAtt = gdp->addAttrib("cudaParticlesPreview", sizeof(int), GB_ATTRIB_INT, &zero); gdp->attribs().getElement().setValue<int>(partsAtt, particlesSystem->preview); GB_AttributeRef systemIdAtt = gdp->addAttrib("systemId", sizeof(int), GB_ATTRIB_INT, &zero); gdp->attribs().getElement().setValue<int>(systemIdAtt, particlesSystem->id); if (f < STARTFRAME(t)) { gdp->clearAndDestroy(); particlesSystem->resetParticles(); } else if (f == STARTFRAME(t)) { gdp->clearAndDestroy(); particlesSystem->resetParticles(); int maxParts = MAXPARTS(t); if (particlesSystem->nParts!=maxParts) particlesSystem->changeMaxParts(maxParts); //hSystem = (GEO_PrimParticle *)gdp->appendPrimitive(GEOPRIMPART); //hSystem->clearAndDestroy(); GB_AttributeRef hVelocity = gdp->addPointAttrib("v", sizeof(UT_Vector3),GB_ATTRIB_VECTOR, 0); GB_AttributeRef hLife = gdp->addPointAttrib("life", sizeof(float)*2,GB_ATTRIB_FLOAT, 0); if(particlesSystem->preview!=1) { UT_Vector4 orig = UT_Vector4(0,0,0,1); for (int i = 0; i<particlesSystem->nParts; i++) { GEO_Point* newPoint = gdp->appendPoint(); newPoint->setPos(orig); /*pvtx = hSystem->giveBirth(); GEO_Point* ppt = pvtx->getPt(); //ppt->getPos().assign(0,0,0,1);*/ hSystemInit = 1; } } } else { if(particlesSystem->nParts != -1) { if(lockInputs(context) >= UT_ERROR_ABORT) return error(); if(getInput(0)){ GU_Detail* emittersInput = (GU_Detail*)inputGeo(0, context); GEO_PointList emittersList = emittersInput->points(); int numEmitters = emittersList.entries(); if (numEmitters != particlesSystem->nEmit) { delete particlesSystem->emitters; particlesSystem->nEmit = numEmitters; particlesSystem->emitters = new ParticlesEmitter[numEmitters]; } GEO_AttributeHandle radAh, amountAh; GEO_AttributeHandle initVelAh, radVelAmpAh, noiseVelAmpAh, noiseVelOffsetAh, noiseVelOctAh, noiseVelLacAh, noiseVelFreqAh; radAh = emittersInput->getPointAttribute("radius"); amountAh = emittersInput->getPointAttribute("amount"); initVelAh = emittersInput->getPointAttribute("initVel"); radVelAmpAh = emittersInput->getPointAttribute("radVelAmp"); noiseVelAmpAh = emittersInput->getPointAttribute("noiseVelAmp"); noiseVelOffsetAh = emittersInput->getPointAttribute("noiseVelOffset"); noiseVelOctAh = emittersInput->getPointAttribute("noiseVelOct"); noiseVelLacAh = emittersInput->getPointAttribute("noiseVelLac"); noiseVelFreqAh = emittersInput->getPointAttribute("noiseVelFreq"); for (int i = 0; i < numEmitters; i++) { UT_Vector4 emitPos = emittersList[i]->getPos(); UT_Vector3 emitPos3(emitPos); particlesSystem->emitters[i].posX = emitPos.x(); particlesSystem->emitters[i].posY = emitPos.y(); particlesSystem->emitters[i].posZ = emitPos.z(); radAh.setElement(emittersList[i]); amountAh.setElement(emittersList[i]); initVelAh.setElement(emittersList[i]); radVelAmpAh.setElement(emittersList[i]); noiseVelAmpAh.setElement(emittersList[i]); noiseVelOffsetAh.setElement(emittersList[i]); noiseVelOctAh.setElement(emittersList[i]); noiseVelLacAh.setElement(emittersList[i]); noiseVelFreqAh.setElement(emittersList[i]); particlesSystem->emitters[i].radius = radAh.getF(0); particlesSystem->emitters[i].amount = amountAh.getF(0); particlesSystem->emitters[i].velX = initVelAh.getF(0); particlesSystem->emitters[i].velY = initVelAh.getF(1); particlesSystem->emitters[i].velZ = initVelAh.getF(2); particlesSystem->emitters[i].radVelAmp = radVelAmpAh.getF(0); particlesSystem->emitters[i].noiseVelAmpX = noiseVelAmpAh.getF(0); particlesSystem->emitters[i].noiseVelAmpY = noiseVelAmpAh.getF(1); particlesSystem->emitters[i].noiseVelAmpZ = noiseVelAmpAh.getF(2); particlesSystem->emitters[i].noiseVelOffsetX = noiseVelOffsetAh.getF(0); particlesSystem->emitters[i].noiseVelOffsetY = noiseVelOffsetAh.getF(1); particlesSystem->emitters[i].noiseVelOffsetZ = noiseVelOffsetAh.getF(2); particlesSystem->emitters[i].noiseVelOct = noiseVelOctAh.getF(0); particlesSystem->emitters[i].noiseVelLac = noiseVelLacAh.getF(0); particlesSystem->emitters[i].noiseVelFreq = noiseVelFreqAh.getF(0); } } else { particlesSystem->nEmit = 0; } if(getInput(1)){ GU_Detail* fluidInput = (GU_Detail*)inputGeo(1, context); GEO_AttributeHandle fluidIdAh= fluidInput->getDetailAttribute("solverId"); fluidIdAh.setElement(fluidInput); int sId = fluidIdAh.getI(); VHFluidSolver3D* curr3DSolver = VHFluidSolver3D::solverList[sId]; particlesSystem->fluidSolver = curr3DSolver; } unlockInputs(); if (f!=oldf) { particlesSystem->emitParticles(); particlesSystem->updateParticles(); } if(particlesSystem->preview!=1 && hSystemInit == 1) { cu::cudaMemcpy( particlesSystem->host_pos, particlesSystem->dev_pos, particlesSystem->nParts*sizeof(cu::float3), cu::cudaMemcpyDeviceToHost ); GEO_Point* ppt; int i = 0; UT_Vector4 p; FOR_ALL_GPOINTS(gdp, ppt) { ppt->getPos() = UT_Vector4(particlesSystem->host_pos[i*3], particlesSystem->host_pos[i*3+1], particlesSystem->host_pos[i*3+2], 1); i++; } /*pvtx = hSystem->iterateInit(); for (int i =0; i<particlesSystem->nParts; i++){ pvtx->getPos().assign(particlesSystem->host_pos[i*3], particlesSystem->host_pos[i*3+1], particlesSystem->host_pos[i*3+2], 1); pvtx = hSystem->iterateFastNext(pvtx); }*/ } } }
OP_ERROR SOP_FluidSolver2D::cookMySop(OP_Context &context) { oldf = f; double t = context.getTime(); int f = context.getFrame(); UT_Interrupt *boss; GU_PrimVolume *volume; OP_Node::flags().timeDep = 1; fluidSolver->fps = OPgetDirector()->getChannelManager()->getSamplesPerSec(); int newResX = RESX(t); int newResY = RESY(t); if ( newResX != fluidSolver->res.x || newResY != fluidSolver->res.y) { fluidSolver->changeFluidRes(newResX,newResY); } UT_Vector3 fluidPos(POSX(t), POSY(t), POSZ(t)); UT_Vector3 fluidRot(ROTX(t), ROTY(t), ROTZ(t)); fluidRot.degToRad(); fluidSolver->fluidSize.x = FLUIDSIZEX(t); fluidSolver->fluidSize.y = FLUIDSIZEY(t); fluidSolver->borderNegX = BORDERNEGX(t); fluidSolver->borderPosX = BORDERPOSX(t); fluidSolver->borderNegY = BORDERNEGY(t); fluidSolver->borderPosY = BORDERPOSY(t); fluidSolver->preview = PREVIEW(t); fluidSolver->previewType = PREVIEWTYPE(t); fluidSolver->bounds = BOUNDS(t); fluidSolver->substeps = SUBSTEPS(t); fluidSolver->jacIter = JACITER(t); fluidSolver->densDis = DENSDIS(t); fluidSolver->densBuoyStrength = DENSBUOYSTRENGTH(t); float ddirX = DENSBUOYDIRX(t); float ddirY = DENSBUOYDIRY(t); fluidSolver->densBuoyDir = cu::make_float2(ddirX,ddirY); fluidSolver->velDamp = VELDAMP(t); fluidSolver->vortConf = VORTCONF(t); fluidSolver->noiseStr = NOISESTR(t); fluidSolver->noiseFreq = NOISEFREQ(t); fluidSolver->noiseOct = NOISEOCT(t); fluidSolver->noiseLacun = NOISELACUN(t); fluidSolver->noiseSpeed = NOISESPEED(t); fluidSolver->noiseAmp = NOISEAMP(t); if (error() < UT_ERROR_ABORT) { boss = UTgetInterrupt(); gdp->clearAndDestroy(); // Start the interrupt server if (boss->opStart("Building Volume")){ static float zero = 0.0; #ifdef HOUDINI_11 GB_AttributeRef fluidAtt = gdp->addAttrib("cudaFluidPreview", sizeof(int), GB_ATTRIB_INT, &zero); gdp->attribs().getElement().setValue<int>(fluidAtt, fluidSolver->preview); GB_AttributeRef solverIdAtt = gdp->addAttrib("solverId", sizeof(int), GB_ATTRIB_INT, &zero); gdp->attribs().getElement().setValue<int>(solverIdAtt, fluidSolver->id); #else GA_WOAttributeRef fluidAtt = gdp->addIntTuple(GA_ATTRIB_DETAIL, "cudaFluidPreview", 1); gdp->element().setValue<int>(fluidAtt, fluidSolver->preview); GA_WOAttributeRef solverIdAtt = gdp->addIntTuple(GA_ATTRIB_DETAIL, "solverId", 1); gdp->element().setValue<int>(solverIdAtt, fluidSolver->id); #endif UT_Matrix3 xform; const UT_XformOrder volXFormOrder; volume = (GU_PrimVolume *)GU_PrimVolume::build(gdp); #ifdef HOUDINI_11 volume->getVertex().getPt()->getPos() = fluidPos; #else volume->getVertexElement(0).getPt()->setPos(fluidPos); #endif xform.identity(); xform.scale(fluidSolver->fluidSize.x*0.5, fluidSolver->fluidSize.y*0.5, 0.25); xform.rotate(fluidRot.x(), fluidRot.y(), fluidRot.z(), volXFormOrder); volume->setTransform(xform); xform.identity(); xform.rotate(fluidRot.x(), fluidRot.y(), fluidRot.z(), volXFormOrder); xform.invert(); if(lockInputs(context) >= UT_ERROR_ABORT) return error(); if(getInput(0)){ GU_Detail* emittersInput = (GU_Detail*)inputGeo(0, context); GEO_PointList emittersList = emittersInput->points(); int numEmitters = emittersList.entries(); if (numEmitters != fluidSolver->nEmit) { delete fluidSolver->emitters; fluidSolver->nEmit = numEmitters; fluidSolver->emitters = new FluidEmitter[numEmitters]; } GEO_AttributeHandle radAh, amountAh; radAh = emittersInput->getPointAttribute("radius"); amountAh = emittersInput->getPointAttribute("amount"); for (int i = 0; i < numEmitters; i++) { UT_Vector4 emitPos = emittersList[i]->getPos(); UT_Vector3 emitPos3(emitPos); emitPos3 -= fluidPos; emitPos3 = emitPos3*xform; fluidSolver->emitters[i].posX = emitPos3.x(); fluidSolver->emitters[i].posY = emitPos3.y(); radAh.setElement(emittersList[i]); amountAh.setElement(emittersList[i]); fluidSolver->emitters[i].radius = radAh.getF(0); fluidSolver->emitters[i].amount = amountAh.getF(0); } } else { fluidSolver->nEmit = 0; } if(getInput(1)) { GU_Detail* collidersInput = (GU_Detail*)inputGeo(1, context); GEO_PointList collidersList = collidersInput->points(); int numColliders = collidersList.entries(); if (numColliders != fluidSolver->nColliders) { delete fluidSolver->colliders; fluidSolver->nColliders = numColliders; fluidSolver->colliders = new Collider[numColliders]; } GEO_AttributeHandle colRadAh; colRadAh = collidersInput->getPointAttribute("radius"); for (int i = 0; i < numColliders; i++) { UT_Vector4 colPos = collidersList[i]->getPos(); UT_Vector3 colPos3(colPos); colPos3 -= fluidPos; colPos3 = colPos3*xform; if (f > STARTFRAME(t)) { fluidSolver->colliders[i].oldPosX = fluidSolver->colliders[i].posX; fluidSolver->colliders[i].oldPosY = fluidSolver->colliders[i].posY; } else { fluidSolver->colliders[i].oldPosX = colPos3.x(); fluidSolver->colliders[i].oldPosY = colPos3.y(); } fluidSolver->colliders[i].posX = colPos3.x(); fluidSolver->colliders[i].posY = colPos3.y(); colRadAh.setElement(collidersList[i]); fluidSolver->colliders[i].radius = colRadAh.getF(0); } } else { fluidSolver->nColliders = 0; } unlockInputs(); if (f <= STARTFRAME(t)) { fluidSolver->resetFluid(); if (fluidSolver->preview != 1) { { UT_VoxelArrayWriteHandleF handle = volume->getVoxelWriteHandle(); handle->constant(0); } } } else { if (f!=oldf) { fluidSolver->solveFluid(); } if (fluidSolver->preview != 1) { cu::cudaMemcpy( fluidSolver->host_dens, fluidSolver->dev_dens, fluidSolver->res.x*fluidSolver->res.y*sizeof(float), cu::cudaMemcpyDeviceToHost ); { UT_VoxelArrayWriteHandleF handle = volume->getVoxelWriteHandle(); handle->size(fluidSolver->res.x, fluidSolver->res.y, 1); for (int i = 0; i < fluidSolver->res.x; i++) { for (int j = 0; j < fluidSolver->res.y; j++) { handle->setValue(i, j, 0, fluidSolver->host_dens[(j*fluidSolver->res.x + i)]); } } } } } select(GU_SPrimitive); } // Tell the interrupt server that we've completed. Must do this // regardless of what opStart() returns. boss->opEnd(); } gdp->notifyCache(GU_CACHE_ALL); return error(); }
OP_ERROR SOP_FluidSolver3D::cookMySop(OP_Context &context) { oldf = f; f = context.getFrame(); double t = context.getTime(); fluidSolver->fps = OPgetDirector()->getChannelManager()->getSamplesPerSec(); UT_Interrupt *boss; GU_PrimVolume *volume; GU_PrimVolume *velXVolume; GU_PrimVolume *velYVolume; GU_PrimVolume *velZVolume; OP_Node::flags().timeDep = 1; int newResX = RESX(t); int newResY = RESY(t); int newResZ = RESZ(t); if ( newResX != fluidSolver->res.width || newResY != fluidSolver->res.height || newResZ != fluidSolver->res.depth) { fluidSolver->changeFluidRes(newResX,newResY,newResZ); } UT_Vector3 fluidPos(POSX(t), POSY(t), POSZ(t)); UT_Vector3 fluidRot(ROTX(t), ROTY(t), ROTZ(t)); fluidRot.degToRad(); fluidSolver->fluidSize.x = FLUIDSIZEX(t); fluidSolver->fluidSize.y = FLUIDSIZEY(t); fluidSolver->fluidSize.z = FLUIDSIZEZ(t); fluidSolver->borderNegX = BORDERNEGX(t); fluidSolver->borderPosX = BORDERPOSX(t); fluidSolver->borderNegY = BORDERNEGY(t); fluidSolver->borderPosY = BORDERPOSY(t); fluidSolver->borderNegZ = BORDERNEGZ(t); fluidSolver->borderPosZ = BORDERPOSZ(t); fluidSolver->substeps = SUBSTEPS(t); fluidSolver->jacIter = JACITER(t); fluidSolver->densDis = DENSDIS(t); fluidSolver->densBuoyStrength = DENSBUOYSTRENGTH(t); float ddirX = DENSBUOYDIRX(t); float ddirY = DENSBUOYDIRY(t); float ddirZ = DENSBUOYDIRZ(t); fluidSolver->densBuoyDir = cu::make_float3(ddirX,ddirY,ddirZ); fluidSolver->velDamp = VELDAMP(t); fluidSolver->vortConf = VORTCONF(t); fluidSolver->noiseStr = NOISESTR(t); fluidSolver->noiseFreq = NOISEFREQ(t); fluidSolver->noiseOct = NOISEOCT(t); fluidSolver->noiseLacun = NOISELACUN(t); fluidSolver->noiseSpeed = NOISESPEED(t); fluidSolver->noiseAmp = NOISEAMP(t); fluidSolver->preview = PREVIEW(t); fluidSolver->drawCube = DRAWCUBE(t); fluidSolver->opaScale = OPASCALE(t); fluidSolver->stepMul = STEPMUL(t); fluidSolver->displayRes = DISPLAYRES(t); fluidSolver->doShadows = DOSHADOWS(t); float lightPosX = LIGHTPOSX(t); float lightPosY = LIGHTPOSY(t); float lightPosZ = LIGHTPOSZ(t); fluidSolver->lightPos = cu::make_float3(lightPosX,lightPosY,lightPosZ); fluidSolver->shadowDens = SHADOWDENS(t); fluidSolver->shadowStepMul = SHADOWSTEPMUL(t); fluidSolver->shadowThres = SHADOWTHRES(t); fluidSolver->displaySlice = DISPLAYSLICE(t); fluidSolver->sliceType = SLICETYPE(t); fluidSolver->sliceAxis = SLICEAXIS(t); fluidSolver->slicePos = SLICEPOS(t); fluidSolver->sliceBounds = SLICEBOUNDS(t); if (error() < UT_ERROR_ABORT) { boss = UTgetInterrupt(); gdp->clearAndDestroy(); // Start the interrupt server if (boss->opStart("Building Volume")){ static float zero = 0.0; GB_AttributeRef fluidAtt = gdp->addAttrib("cudaFluid3DPreview", sizeof(int), GB_ATTRIB_INT, &zero); gdp->attribs().getElement().setValue<int>(fluidAtt, fluidSolver->preview); GB_AttributeRef fluidSliceAtt = gdp->addAttrib("sliceDisplay", sizeof(int), GB_ATTRIB_INT, &zero); gdp->attribs().getElement().setValue<int>(fluidSliceAtt, fluidSolver->displaySlice); GB_AttributeRef solverIdAtt = gdp->addAttrib("solverId", sizeof(int), GB_ATTRIB_INT, &zero); gdp->attribs().getElement().setValue<int>(solverIdAtt, fluidSolver->id); GEO_AttributeHandle name_gah; int def = -1; gdp->addPrimAttrib("name", sizeof(int), GB_ATTRIB_INDEX, &def); name_gah = gdp->getPrimAttribute("name"); UT_Matrix3 xform; const UT_XformOrder volXFormOrder; volume = (GU_PrimVolume *)GU_PrimVolume::build(gdp); volume->getVertex().getPt()->getPos() = fluidPos; xform.identity(); xform.scale(fluidSolver->fluidSize.x*0.5, fluidSolver->fluidSize.y*0.5, fluidSolver->fluidSize.z*0.5); xform.rotate(fluidRot.x(), fluidRot.y(), fluidRot.z(), volXFormOrder); volume->setTransform(xform); name_gah.setElement(volume); name_gah.setString("density"); velXVolume = (GU_PrimVolume *)GU_PrimVolume::build(gdp); velXVolume->getVertex().getPt()->getPos() = fluidPos; velXVolume->setTransform(xform); name_gah.setElement(velXVolume); name_gah.setString("vel.x"); velYVolume = (GU_PrimVolume *)GU_PrimVolume::build(gdp); velYVolume->getVertex().getPt()->getPos() = fluidPos; velYVolume->setTransform(xform); name_gah.setElement(velYVolume); name_gah.setString("vel.y"); velZVolume = (GU_PrimVolume *)GU_PrimVolume::build(gdp); velZVolume->getVertex().getPt()->getPos() = fluidPos; velZVolume->setTransform(xform); name_gah.setElement(velZVolume); name_gah.setString("vel.z"); xform.identity(); xform.rotate(fluidRot.x(), fluidRot.y(), fluidRot.z(), volXFormOrder); xform.invert(); if(lockInputs(context) >= UT_ERROR_ABORT) return error(); if(getInput(0)){ GU_Detail* emittersInput = (GU_Detail*)inputGeo(0, context); GEO_PointList emittersList = emittersInput->points(); int numEmitters = emittersList.entries(); if (numEmitters != fluidSolver->nEmit) { delete fluidSolver->emitters; fluidSolver->nEmit = numEmitters; fluidSolver->emitters = new VHFluidEmitter[numEmitters]; } GEO_AttributeHandle radAh, amountAh; radAh = emittersInput->getPointAttribute("radius"); amountAh = emittersInput->getPointAttribute("amount"); for (int i = 0; i < numEmitters; i++) { UT_Vector4 emitPos = emittersList[i]->getPos(); UT_Vector3 emitPos3(emitPos); emitPos3 -= fluidPos; emitPos3 = emitPos3*xform; fluidSolver->emitters[i].posX = emitPos3.x(); fluidSolver->emitters[i].posY = emitPos3.y(); fluidSolver->emitters[i].posZ = emitPos3.z(); radAh.setElement(emittersList[i]); amountAh.setElement(emittersList[i]); fluidSolver->emitters[i].radius = radAh.getF(0); fluidSolver->emitters[i].amount = amountAh.getF(0); } } else { fluidSolver->nEmit = 0; } if(getInput(1)) { GU_Detail* collidersInput = (GU_Detail*)inputGeo(1, context); GEO_PointList collidersList = collidersInput->points(); int numColliders = collidersList.entries(); if (numColliders != fluidSolver->nColliders) { delete fluidSolver->colliders; fluidSolver->nColliders = numColliders; fluidSolver->colliders = new VHFluidCollider[numColliders]; } GEO_AttributeHandle colRadAh; colRadAh = collidersInput->getPointAttribute("radius"); for (int i = 0; i < numColliders; i++) { UT_Vector4 colPos = collidersList[i]->getPos(); UT_Vector3 colPos3(colPos); colPos3 -= fluidPos; colPos3 = colPos3*xform; if (f > STARTFRAME(t)) { fluidSolver->colliders[i].oldPosX = fluidSolver->colliders[i].posX; fluidSolver->colliders[i].oldPosY = fluidSolver->colliders[i].posY; fluidSolver->colliders[i].oldPosZ = fluidSolver->colliders[i].posZ; } else { fluidSolver->colliders[i].oldPosX = colPos3.x(); fluidSolver->colliders[i].oldPosY = colPos3.y(); fluidSolver->colliders[i].oldPosZ = colPos3.z(); } fluidSolver->colliders[i].posX = colPos3.x(); fluidSolver->colliders[i].posY = colPos3.y(); fluidSolver->colliders[i].posZ = colPos3.z(); colRadAh.setElement(collidersList[i]); fluidSolver->colliders[i].radius = colRadAh.getF(0); } } else { fluidSolver->nColliders = 0; } unlockInputs(); if (f <= STARTFRAME(t)) { fluidSolver->resetFluid(); if (COPYDENS(t)) { { UT_VoxelArrayWriteHandleF handle = volume->getVoxelWriteHandle(); handle->constant(0); UT_VoxelArrayWriteHandleF velXHandle = velXVolume->getVoxelWriteHandle(); velXHandle->constant(0); UT_VoxelArrayWriteHandleF velYHandle = velYVolume->getVoxelWriteHandle(); velYHandle->constant(0); UT_VoxelArrayWriteHandleF velZHandle = velZVolume->getVoxelWriteHandle(); velZHandle->constant(0); } } } else { if (f!=oldf) { fluidSolver->solveFluid(); } if (COPYDENS(t)) { cu::cudaMemcpy( fluidSolver->host_dens, fluidSolver->dev_dens, fluidSolver->res.width*fluidSolver->res.height*fluidSolver->res.depth*sizeof(float), cu::cudaMemcpyDeviceToHost ); { UT_VoxelArrayWriteHandleF handle = volume->getVoxelWriteHandle(); handle->size(fluidSolver->res.width, fluidSolver->res.height, fluidSolver->res.depth); for (int i = 0; i < fluidSolver->res.width; i++) { for (int j = 0; j < fluidSolver->res.height; j++) { for (int k = 0; k < fluidSolver->res.depth; k++) { handle->setValue(i, j, k, fluidSolver->host_dens[k*fluidSolver->res.width*fluidSolver->res.height + j*fluidSolver->res.width + i]); } } } } if (COPYVEL(t)) { cu::cudaMemcpy( fluidSolver->host_vel, fluidSolver->dev_vel, fluidSolver->res.width*fluidSolver->res.height*fluidSolver->res.depth*sizeof(cu::float4), cu::cudaMemcpyDeviceToHost ); { UT_VoxelArrayWriteHandleF velXHandle = velXVolume->getVoxelWriteHandle(); velXHandle->size(fluidSolver->res.width, fluidSolver->res.height, fluidSolver->res.depth); UT_VoxelArrayWriteHandleF velYHandle = velYVolume->getVoxelWriteHandle(); velYHandle->size(fluidSolver->res.width, fluidSolver->res.height, fluidSolver->res.depth); UT_VoxelArrayWriteHandleF velZHandle = velZVolume->getVoxelWriteHandle(); velZHandle->size(fluidSolver->res.width, fluidSolver->res.height, fluidSolver->res.depth); for (int i = 0; i < fluidSolver->res.width; i++) { for (int j = 0; j < fluidSolver->res.height; j++) { for (int k = 0; k < fluidSolver->res.depth; k++) { velXHandle->setValue(i, j, k, fluidSolver->host_vel[4*(k*fluidSolver->res.width*fluidSolver->res.height + j*fluidSolver->res.width + i)]); velYHandle->setValue(i, j, k, fluidSolver->host_vel[4*(k*fluidSolver->res.width*fluidSolver->res.height + j*fluidSolver->res.width + i)+1]); velZHandle->setValue(i, j, k, fluidSolver->host_vel[4*(k*fluidSolver->res.width*fluidSolver->res.height + j*fluidSolver->res.width + i)+2]); } } } } } } } select(GU_SPrimitive); } // Tell the interrupt server that we've completed. Must do this // regardless of what opStart() returns. boss->opEnd(); } gdp->notifyCache(GU_CACHE_ALL); return error(); }