Example #1
0
void ColorFuncMakeClut( NimblePixel clut[SAMPLE_CLUT_SIZE], int rockType, const NimblePixMap& map, float showGeology, float showSeismic, ColorFunc colorFunc ) {
	// Note: rockType==RockTypeMax is used for the seismogram coloring.
	Assert(rockType<=RockTypeMax);
	Assert(0<=showGeology && showGeology<=1);
	Assert(0<=showSeismic && showSeismic<=1);
	int w = GuideColors.width();
	int h = GuideColors.height();
	Assert(w%2==1);
	float scale = showSeismic*float(w/2);
    if( colorFunc==CF_Log ) 
        scale /= asinhf(LogScaleStretch);
	for( int j=0; j<=SAMPLE_CLUT_SIZE/2; ++j ) {
		// u is normalized amplitude in range [-1,1]
		float u = j*(2.0f/SAMPLE_CLUT_SIZE);
		float v;
		switch( colorFunc ) {
			case CF_SignOnly:
				v = u==0 ? 0 : 2.0f/3;
				break;
			case CF_Log:
				v = asinhf(u*LogScaleStretch);
				break;
			case CF_Linear:
				v = u;
				break;
		}
		TransferFunc[SAMPLE_CLUT_SIZE/2+j] = v*scale;
		TransferFunc[SAMPLE_CLUT_SIZE/2-j] = -v*scale;
	}

	// Get rock-independent color.  The "-2" is there instead of "-1" because "-1"
	// is for an unused "light" color scale as opposed to the "dark" scale at "-2".
	const NimbleColor* colorScale0 = GuideColors[h-2]+w/2;
	// Get rock-dependent color
	const NimbleColor* colorScale1 = GuideColors[rockType]+w/2;
	for( int j=0; j<SAMPLE_CLUT_SIZE; ++j ) {
		int k = int(TransferFunc[j]);
		float residue = TransferFunc[j]-k;
		Assert( k<GuideColors.width() );
		NimbleColor c0 = colorScale0[k];
		NimbleColor c1 = colorScale1[k];
		if( residue>0 ) {
			c0.mix(colorScale0[k+1],residue);
			c1.mix(colorScale1[k+1],residue);
		}
		if( residue<0 ) {
			c0.mix(colorScale0[k-1],-residue);
			c1.mix(colorScale1[k-1],-residue);
		}
		c0.mix(c1,showGeology);
		clut[j] = map.pixel(c0); 
	}
}
Example #2
0
void GameUpdateDraw( NimblePixMap& map, NimbleRequest request ) {
#if WRITING_DOCUMENTATION
	new(&TheMap) NimblePixMap( map );
#endif /* WRITING_DOCUMENTATION */
	WavefieldRect = NimbleRect(PanelWidth,map.height()/2,map.width(),map.height());
	NimblePixMap subsurface(map,WavefieldRect); 
	NimblePixMap seismogramClip( map,NimbleRect(PanelWidth,0,map.width(),map.height()/2) );

	if( request & NimbleUpdate ) {
		ShowGeology.update(); 
		ShowSeismic.update(); 
	}
	const NimbleRequest pausedRequest = IsPaused ? request-NimbleUpdate : request;
    SeismogramUpdateDraw( seismogramClip, pausedRequest&NimbleUpdate, TheColorFunc, IsAutoGainOn );
 	WavefieldFunctor wf(subsurface, pausedRequest);
    SeismogramFunctor sf( seismogramClip, pausedRequest&NimbleDraw );
    ReservoirFunctor rf( pausedRequest );
#if PARALLEL
	tbb::parallel_invoke( wf, sf, rf );
#else
    wf();
	sf();
	rf();
#endif
	if( pausedRequest & NimbleUpdate ) {
		DrillBit.update();
		UpdateDuckAndRig();
	}
	if( request & NimbleDraw ) {
		ClickableSetEnd = ClickableSet;
		const int wavefieldWidth = map.width()-PanelWidth;
		Assert(wavefieldWidth%4==0);
		const int wavefieldHeight = map.height()/2;
		ReservoirDrawHoles( subsurface );
		if( DrillY>0 )
			DrillBit.drawOn( subsurface, RigX-DrillBit.width()/2, DrillY-5 );
		if( ShowReservoir )
			ReservoirDraw( subsurface );
		NimblePixMap spriteClip( map, NimbleRect( PanelWidth, 0, map.width(), map.height() ));\
		NimblePixel greenPixel = map.pixel( NimbleColor( 0, NimbleColor::FULL, 0 ));
		NimblePixel redPixel = map.pixel( NimbleColor( NimbleColor::FULL, 0, 0 ));
		const int lineHeight = map.height()/2-1; 
		if( CultureBeginX<CultureEndX ) {
		    spriteClip.draw( NimbleRect( 0, lineHeight, CultureBeginX, lineHeight+1 ), greenPixel ); 
		    spriteClip.draw( NimbleRect( CultureBeginX, lineHeight-1, CultureEndX, lineHeight+2 ), redPixel ); 
		    spriteClip.draw( NimbleRect( CultureEndX, lineHeight, spriteClip.width(), lineHeight+1 ), greenPixel ); 
			Culture.drawOn( spriteClip, CultureBeginX+(CultureEndX-CultureBeginX)/2-Culture.width()/2, map.height()/2-Culture.height() );
		} else {
		    spriteClip.draw( NimbleRect( 0, lineHeight, spriteClip.width(), lineHeight+1 ), greenPixel ); 
		}
		OilRig->drawOn( spriteClip, RigX-OilRig->width()/2, OilRigVerticalOffset ); 
		if( DuckGoingLeft )
			DuckLeft.drawOn( spriteClip, DuckX-50, map.height()/2-DuckLeft.height()+12 );
		else
			DuckRight.drawOn( spriteClip, DuckX-(DuckRight.width()-50), map.height()/2-DuckLeft.height()+12 );
		NimblePixMap panelClip( map, NimbleRect( 0, 0, PanelWidth, map.height() ));

		PanelBackground.drawOn( panelClip );

		int cashMeterY = map.height()- 50 -CashMeter.height();
		int levelMeterY = cashMeterY - 10 - LevelMeter.height();
		// The Min is there so that if there is room, the green line artistically lines up 
		// with the top of the fluid meters.
		int fluidMeterY = Min(levelMeterY - 10 - WaterMeter.height(), map.height()/2 );
		if( ScoreState.isDisplayingScore() ) {
			LevelMeter.drawOn( map, PanelWidth/2-LevelMeter.width()/2, levelMeterY );
		    CashMeter.drawOn( map, PanelWidth/2-CashMeter.width()/2, cashMeterY );
		}
		int meterMarginX = (PanelWidth-WaterMeter.width()-OilMeter.width()-GasMeter.width())/4;
		WaterMeter.drawOn( map, meterMarginX, fluidMeterY );
		OilMeter.drawOn( map, PanelWidth/2-OilMeter.width()/2, fluidMeterY );
		GasMeter.drawOn( map, PanelWidth-meterMarginX-GasMeter.width(), fluidMeterY );
		if( VisibleDialog ) {
			if( VisibleDialog==&TheAboutTheAuthorDialog || VisibleDialog==&TheLevelContinueDialog )
				// Center it on screen
				VisibleDialog->drawOn( map, map.width()/2-VisibleDialog->width()/2, map.height()/2-VisibleDialog->height()/2 );
			else if( VisibleDialog==&TheKeyboardHelpDialog )
				// Put in upper right corner
				VisibleDialog->drawOn( map, map.width()*.95f-VisibleDialog->width(), map.height()*.05f );
			else
				// Put it in upper left portion of seismogram
				VisibleDialog->drawOn( map, PanelWidth+24, 24 );
		}
		int tabTop1 = 50;
		int tabTop2 = tabTop1+2*TheFont.height();
		int tabLeft1 = PanelWidth/8;
		int tabLeft2 = PanelWidth*5/8;
		int airGunTop = tabTop2+2*TheFont.height();;
		AirgunMeter.drawOn( map, PanelWidth/2-AirgunMeter.width()/2, airGunTop );
		if( ShowFrameRate ) {
			FrameRateMeter.setValue( EstimateFrameRate() );
			FrameRateMeter.drawOn( map, PanelWidth/2-FrameRateMeter.width()/2, fluidMeterY-FrameRateMeter.height()-15 ); 
		}
		const int tabSpacing = PanelWidth/4;
		DrawClickable( TheFileMenu, map, tabLeft1, tabTop1 );
		DrawClickable( TheHelpMenu, map, tabLeft2, tabTop1 );
		// The "isTabbed" tests below do some ad-hoc occlusion testing.
		if( TheFileMenu.isTabbed() ) 
			DrawClickable( TheModelMenu, map, tabLeft1, tabTop2 );
		if( TheFileMenu.isTabbed() && TheHelpMenu.isTabbed() )
			DrawClickable( TheViewMenu, map, tabLeft2, tabTop2 );
	}
	ScoreState.update();
}