bool AttributeAttractRepelParticleAffector::affect(ParticleSystemRefPtr System, Int32 ParticleIndex, const Time& elps)
{
    if(System != NULL)
    {
        Vec3f Displacement(System->getSecPosition(ParticleIndex) - System->getPosition(ParticleIndex) );

        Real32 Distance(Displacement.squareLength());

        if((Distance > getMinDistance()*getMinDistance()) &&
           (Distance < getMaxDistance()*getMaxDistance()))
        {
            Distance = osgSqrt(Distance);
            Displacement.normalize();

            Real32 t((getQuadratic() * (Distance*Distance) + getLinear() * Distance + getConstant())*elps);
            if(t > Distance)
            {
                t=Distance;
            }

            System->setPosition(System->getPosition(ParticleIndex) + (Displacement * t),ParticleIndex) ;
        }
    }
    return false;
}
Exemple #2
0
bool ofxArtool5::setupCamera(string pthCamParam, ofVec2f _camSize, ofVec2f _viewportSize, ofPixelFormat pf){
    ARParam cParam;
    AR_PIXEL_FORMAT pixFormat = toAR(pf);
    
    const char * cPathCamParam = ofToDataPath(pthCamParam).c_str();
    
    camSize=_camSize;
    viewportSize=_viewportSize;
    
    if(arParamLoad(cPathCamParam, 1, &cParam)){
        ofLogError("ofxArtool5::setupCamera()", "error loading param file");
        return false;
    }
    
    if(cParam.xsize!=camSize.x||cParam.ysize!=camSize.y){
        ofLogWarning("ofxArtool5::setupCamera()","camera param needs resizing");
        arParamChangeSize(&cParam, camSize.x, camSize.y, &cParam);
    }
    
    if((gCparamLT = arParamLTCreate(&cParam, AR_PARAM_LT_DEFAULT_OFFSET))==NULL){
        ofLogError("ofxArtool5::setupCamera()","Error: arParamLTCreate");
        return false;
    }
    
    if(artMode==ART_PATTERN){
        
        if((gARHandle = arCreateHandle(gCparamLT))==NULL){
            ofLogError("ofxArtool5::setupCamera()","Error: arCreateHandle");
            return false;
        }
        
        if(arSetPixelFormat(gARHandle, pixFormat)<0){
            ofLogError("ofxArtool5::setupCamera()","Error arSetPixelFormat");
            return false;
        }
        
        if(arSetDebugMode(gARHandle, AR_DEBUG_DISABLE)<0){
            ofLogError("ofxArtool5::setupCamera()","Error arSetDebugMode");
            return false;
        }
        
        if((gAR3DHandle = ar3DCreateHandle(&cParam))==NULL){
            ofLogError("ofxArtool5::setupCamera()","Error ar3DCreateHandle");
            return false;
        }
    }else if(artMode==ART_NFT){
        arglCameraFrustumRH(&(gCparamLT->param), getMinDistance(), getMaxDistance(), cameraLens);
    }
    
    cvColorFrame.allocate(camSize.x, camSize.y);
    cvGrayFrame.allocate(camSize.x, camSize.y);
    
    return true;
}
Exemple #3
0
// Dijkstra 알고리즘
int *shortestPathDijkstra(LinkedGraph* pGraph, int startVertexID) {
	int *pReturn = NULL;
	int *pSelected = NULL;
	int nodeCount = 0, maxNodeCount = 0;
	int i = 0, j = 0, weight = 0;
	int vertexID = 0, y_w = 0, y_v = 0;
	ListNode *pListNode = NULL;
	LinkedList *pEdgeList = NULL;

	if (pGraph == NULL) {
		printf("Graph is NULL\n");
		return pReturn;
	}
	maxNodeCount = getMaxVertexCountLG(pGraph);
	nodeCount = getVertexCountLG(pGraph);

	pReturn = (int *)malloc(sizeof(int) * maxNodeCount);
	pSelected = (int *)malloc(sizeof(int) * maxNodeCount);
	if (pReturn == NULL || pSelected == NULL) {
		if (pReturn != NULL) free(pReturn);
		printf("오류, 메모리 할당 in shortestPathDijkstra()\n");
		return NULL;
	}

	// Step 0. 초기화
	for(i = 0; i < maxNodeCount; i++) {
		if (i == startVertexID) {
			pReturn[i] = 0;
		}
		else {
			if (pGraph->pVertex[i] == USED) {
				pSelected[i] = TRUE;
				pReturn[i] = getEdgeWeight(pGraph, startVertexID, i);
			}
			else {
				pSelected[i] = FALSE;
				pReturn[i] = MAX_INT;
			}
		}
	}
	for(i = 0; i < maxNodeCount; i++) {
		printf("(%d,%d)->%d\n", startVertexID, i, pReturn[i]);
	}

	for(i = 0; i < nodeCount - 1; i++) {
		printf("[%d]-Iteration\n", i+1);

		// Step-1.
		// 집합 S중 최단 거리를 가지는 정점(vertexID)을 선택
		vertexID = getMinDistance(pReturn, pSelected, maxNodeCount);
		pSelected[vertexID] = FALSE;
	
		// 선택된 정점(vertexID)에 인접한 정점들에 대해 거리 변경 조건 점검.
		pEdgeList = pGraph->ppAdjEdge[vertexID];
		pListNode = pEdgeList->headerNode.pLink;
		while(pListNode != NULL) {
			int toVertexID = pListNode->data.vertexID;
			int weight = pListNode->data.weight;

			// y_v + c_v,w 와 y_w 비교
			y_v = pReturn[vertexID];
			y_w = pReturn[toVertexID];
			if (y_v + weight < y_w) {
				pReturn[toVertexID] = y_v + weight;
			}
			pListNode = pListNode->pLink;
		}

		for(j = 0; j < maxNodeCount; j++) {
			printf("\t(%d,%d)->%d\n", startVertexID, j, pReturn[j]);
		}
	}

	free(pSelected);
	
	return pReturn;
}
void 
simpleFluidEmitter::omniFluidEmitter(
	MFnFluid& 		fluid,
	const MMatrix&	fluidWorldMatrix,
	int 			plugIndex,
	MDataBlock& 	block,
	double 			dt,
	double			conversion,
	double			dropoff
)
//==============================================================================
//
//	Method:	
//
//		simpleFluidEmitter::omniFluidEmitter
//
//	Description:
//
//		Emits fluid from a point, or from a set of object control points.
//
//	Parameters:
//
//		fluid:				fluid into which we are emitting
//		fluidWorldMatrix:	object->world matrix for the fluid
//		plugIndex:			identifies which fluid connected to the emitter
//							we are emitting into
//		block:				datablock for the emitter, to retrieve attribute
//							values
//		dt:					time delta for this frame
//		conversion:			mapping from UI emission rates to internal units
//		dropoff:			specifies how much emission rate drops off as
//							we move away from each emission point.
//
//	Notes:
//
//		If no owner object is present for the emitter, we simply emit from
//		the emitter position.  If an owner object is present, then we emit
//		from each control point of that object in an identical fashion.
//		
//		To associate an owner object with an emitter, use the
//		addDynamic MEL command, e.g. "addDynamic simpleFluidEmitter1 pPlane1".
//
//==============================================================================
{
	//	find the positions that we need to emit from
	//
	MVectorArray emitterPositions;
	
	//	first, try to get them from an owner object, which will have its
	//	"ownerPositionData" attribute feeding into the emitter.  These
	//	values are in worldspace
	//
	bool gotOwnerPositions = false;
	MObject ownerShape = getOwnerShape();
	if( ownerShape != MObject::kNullObj )
	{
		MStatus status;
		MDataHandle hOwnerPos = block.inputValue( mOwnerPosData, &status );
		if( status == MS::kSuccess )
		{
			MObject dOwnerPos = hOwnerPos.data();
			MFnVectorArrayData fnOwnerPos( dOwnerPos );
			MVectorArray posArray = fnOwnerPos.array( &status );
			if( status == MS::kSuccess )
			{
				// assign vectors from block to ownerPosArray.
				//
				for( unsigned int i = 0; i < posArray.length(); i ++ )
				{
					emitterPositions.append( posArray[i] );
				}
				
				gotOwnerPositions = true;
			}
		}
	}
	
	//	there was no owner object, so we just use the emitter position for
	//	emission.
	//
	if( !gotOwnerPositions )
	{
		MPoint emitterPos = getWorldPosition();
		emitterPositions.append( emitterPos );
	}

	//	get emission rates for density, fuel, heat, and emission color
	//	
	double densityEmit = fluidDensityEmission( block );
	double fuelEmit = fluidFuelEmission( block );
	double heatEmit = fluidHeatEmission( block );
	bool doEmitColor = fluidEmitColor( block );
	MColor emitColor = fluidColor( block );

	//	rate modulation based on frame time, user value conversion factor, and
	//	standard emitter "rate" value (not actually exposed in most fluid
	//	emitters, but there anyway).
	//
	double theRate = getRate(block) * dt * conversion;

	//	get voxel dimensions and sizes (object space)
	//
	double size[3];
	unsigned int res[3];
	fluid.getDimensions( size[0], size[1], size[2] );
	fluid.getResolution( res[0], res[1], res[2] );
	
	//	voxel sizes
	double dx = size[0] / res[0];
	double dy = size[1] / res[1];
	double dz = size[2] / res[2];
	
	//	voxel centers
	double Ox = -size[0]/2;
	double Oy = -size[1]/2;
	double Oz = -size[2]/2;	

	//	emission will only happen for voxels whose centers lie within
	//	"minDist" and "maxDist" of an emitter position
	//
	double minDist = getMinDistance( block );
	double maxDist = getMaxDistance( block );

	//	bump up the min/max distance values so that they
	//	are both > 0, and there is at least about a half
	//	voxel between the min and max values, to prevent aliasing
	//	artifacts caused by emitters missing most voxel centers
	//
	MTransformationMatrix fluidXform( fluidWorldMatrix );
	double fluidScale[3];
	fluidXform.getScale( fluidScale, MSpace::kWorld );
	
	//	compute smallest voxel diagonal length
	double wsX =  fabs(fluidScale[0]*dx);
	double wsY = fabs(fluidScale[1]*dy);
	double wsZ = fabs(fluidScale[2]*dz);
	double wsMin = MIN( MIN( wsX, wsY), wsZ );
	double wsMax = MAX( MAX( wsX, wsY), wsZ );
	double wsDiag  = wsMin * sqrt(3.0);

	//	make sure emission range is bigger than 0.5 voxels
	if ( maxDist <= minDist || maxDist <= (wsDiag/2.0) ) {
		if ( minDist < 0 ) minDist = 0;

		maxDist = minDist + wsDiag/2.0;
		dropoff = 0;
	}

	//	Now, it's time to actually emit into the fluid:
	//	
	//	foreach emitter point
	//		foreach voxel
	//			- select some points in the voxel
	//			- compute a dropoff function from the emitter point
	//			- emit an appropriate amount of fluid into the voxel
	//
	//	Since we've already expanded the min/max distances to cover
	//	the smallest voxel dimension, we should only need 1 sample per
	//	voxel, unless the voxels are highly non-square.  We increase the
	//	number of samples in these cases.
	//
	//	If the "jitter" flag is enabled, we jitter each sample position,
	//	using the rangen() function, which keeps track of independent 
	//	random states for each fluid, to make sure that results are
	//	repeatable for multiple simulation runs.
	//	

	// basic sample count
	int numSamples = 1;

	// increase samples if necessary for non-square voxels
	if(wsMin >.00001) 
	{
		numSamples = (int)(wsMax/wsMin + .5);
		if(numSamples > 8) 
			numSamples = 8;
		if(numSamples < 1)
			numSamples = 1;
	}
	
	bool jitter =  fluidJitter(block);
	if( !jitter )
	{
		//	I don't have a good uniform sample generator for an 
		//	arbitrary number of samples.  It would be a good idea to use
		//	one here.  For now, just use 1 sample for the non-jittered case.
		//
		numSamples = 1;
	}

	for( unsigned int p = 0; p < emitterPositions.length(); p++ )
	{
		MPoint emitterWorldPos = emitterPositions[p];

		//	loop through all voxels, looking for ones that lie at least
		//	partially within the dropoff field around this emitter point
		//
		for( unsigned int i = 0; i < res[0]; i++ )
		{
			double x = Ox + i*dx;
			
			for( unsigned int j = 0; j < res[1]; j++ )
			{
				double y = Oy + j*dy;
				
				for( unsigned int k = 0; k < res[2]; k++ )
				{
					double z = Oz + k*dz;
	
					int si;
					for( si = 0; si < numSamples; si++ )
					{
						//	compute sample point (fluid object space)
						//
						double rx, ry, rz;
						if( jitter )
						{
							rx = x + randgen()*dx;
							ry = y + randgen()*dy;
							rz = z + randgen()*dz;
						}
						else
						{
							rx = x + 0.5*dx;
							ry = y + 0.5*dy;
							rz = z + 0.5*dz;
						}

						//	compute distance from sample to emitter point
						//	
						MPoint point( rx, ry, rz );
						point *= fluidWorldMatrix;
						MVector diff = point - emitterWorldPos;
						double distSquared = diff * diff;
						double dist = diff.length();
					
						//	discard if outside min/max range
						//
						if( (dist < minDist) || (dist > maxDist) )
						{
							continue;
						}
						
						//	drop off the emission rate according to the falloff
						//	parameter, and divide to accound for multiple samples
						//	in the voxel
						//
						double distDrop = dropoff * distSquared;
						double newVal = theRate * exp( -distDrop ) / (double)numSamples;

						//	emit density/heat/fuel/color into the current voxel
						//
						if( newVal != 0 )
						{
							fluid.emitIntoArrays( (float) newVal, i, j, k, (float)densityEmit, (float)heatEmit, (float)fuelEmit, doEmitColor, emitColor );
						}

						float *fArray = fluid.falloff();
						if( fArray != NULL )
						{
							MPoint midPoint( x+0.5*dx, y+0.5*dy, z+0.5*dz );
							midPoint.x *= 0.2;
							midPoint.y *= 0.2;
							midPoint.z *= 0.2;

							float fdist = (float) sqrt( midPoint.x*midPoint.x + midPoint.y*midPoint.y + midPoint.z*midPoint.z );
							fdist /= sqrtf(3.0f);
							fArray[fluid.index(i,j,k)] = 1.0f-fdist;
						}
					}
				}
			}
		}
	}
}
Exemple #5
0
float sfSoundStream_getMinDistance(const sfSoundStream* soundStream)
{
    CSFML_CALL_RETURN(soundStream, getMinDistance(), 0.f);
}
Exemple #6
0
float sfSound_getMinDistance(const sfSound* sound)
{
    CSFML_CALL_RETURN(sound, getMinDistance(), 0.f);
}