示例#1
0
void TileLayerComponentManager::_fillBuffer(VertexBuffer& buffer, const TileMapSP tileMap, unsigned layer,
                                            float tileWidth, float tileHeight, const Matrix4& wt) const {
	buffer.clear();

	unsigned width      = tileMap->width (layer);
	unsigned height     = tileMap->height(layer);
	Vector2i nTiles(tileMap->tileSetHTiles(), tileMap->tileSetVTiles());
	for(unsigned y = 0; y < height; ++y) {
		for(unsigned x = 0; x < width; ++x) {
			TileMap::TileIndex tile = tileMap->tile(x, y, layer);
			if(tile == 0)
				continue;

			unsigned index = buffer.vertexCount();
			Box2 tc  = boxView(tileBox(nTiles, tile - 1),
			                   Box2(Vector2(0.001, 0.001), Vector2(0.999, 0.999)));
			for(unsigned vi = 0; vi < 4; ++vi) {
				unsigned x2 = (vi & 0x01)? 1: 0;
				unsigned y2 = (vi & 0x02)? 1: 0;
				Vector4 pos = wt * Vector4((         x + x2) * tileWidth,
				                           (height - y - y2) * tileHeight, 0, 1);
				buffer.addVertex(SpriteVertex{ pos, Vector4::Constant(1),
				                               tc.corner(Box2::CornerType(x2 + y2*2)) });
			}

			buffer.addIndex(index + 0);
			buffer.addIndex(index + 1);
			buffer.addIndex(index + 2);
			buffer.addIndex(index + 2);
			buffer.addIndex(index + 1);
			buffer.addIndex(index + 3);
		}
	}
}
示例#2
0
// SamplerIntegrator Method Definitions
void SamplerIntegrator::Render(const Scene &scene) {
    ProfilePhase p(Prof::IntegratorRender);
    Preprocess(scene, *sampler);
    // Render image tiles in parallel

    // Compute number of tiles, _nTiles_, to use for parallel rendering
    Bounds2i sampleBounds = camera->film->GetSampleBounds();
    Vector2i sampleExtent = sampleBounds.Diagonal();
    const int tileSize = 16;
    Point2i nTiles((sampleExtent.x + tileSize - 1) / tileSize,
                   (sampleExtent.y + tileSize - 1) / tileSize);
    ProgressReporter reporter(nTiles.x * nTiles.y, "Rendering");
    {
        StatTimer timer(&renderingTime);
        ParallelFor2D([&](Point2i tile) {
            // Render section of image corresponding to _tile_

            // Allocate _MemoryArena_ for tile
            MemoryArena arena;

            // Get sampler instance for tile
            int seed = tile.y * nTiles.x + tile.x;
            std::unique_ptr<Sampler> tileSampler = sampler->Clone(seed);

            // Compute sample bounds for tile
            int x0 = sampleBounds.pMin.x + tile.x * tileSize;
            int x1 = std::min(x0 + tileSize, sampleBounds.pMax.x);
            int y0 = sampleBounds.pMin.y + tile.y * tileSize;
            int y1 = std::min(y0 + tileSize, sampleBounds.pMax.y);
            Bounds2i tileBounds(Point2i(x0, y0), Point2i(x1, y1));

            // Get _FilmTile_ for tile
            std::unique_ptr<FilmTile> filmTile =
                camera->film->GetFilmTile(tileBounds);

            // Loop over pixels in tile to render them
            for (Point2i pixel : tileBounds) {
                {
                    ProfilePhase pp(Prof::StartPixel);
                    tileSampler->StartPixel(pixel);
                }
                do {
                    // Initialize _CameraSample_ for current sample
                    CameraSample cameraSample =
                        tileSampler->GetCameraSample(pixel);

                    // Generate camera ray for current sample
                    RayDifferential ray;
                    Float rayWeight =
                        camera->GenerateRayDifferential(cameraSample, &ray);
                    ray.ScaleDifferentials(
                        1 / std::sqrt((Float)tileSampler->samplesPerPixel));
                    ++nCameraRays;

                    // Evaluate radiance along camera ray
                    Spectrum L(0.f);
                    if (rayWeight > 0) L = Li(ray, scene, *tileSampler, arena);

                    // Issue warning if unexpected radiance value returned
                    if (L.HasNaNs()) {
                        Error(
                            "Not-a-number radiance value returned "
                            "for image sample.  Setting to black.");
                        L = Spectrum(0.f);
                    } else if (L.y() < -1e-5) {
                        Error(
                            "Negative luminance value, %f, returned "
                            "for image sample.  Setting to black.",
                            L.y());
                        L = Spectrum(0.f);
                    } else if (std::isinf(L.y())) {
                        Error(
                            "Infinite luminance value returned "
                            "for image sample.  Setting to black.");
                        L = Spectrum(0.f);
                    }

                    // Add camera ray's contribution to image
                    filmTile->AddSample(cameraSample.pFilm, L, rayWeight);

                    // Free _MemoryArena_ memory from computing image sample
                    // value
                    arena.Reset();
                } while (tileSampler->StartNextSample());
            }

            // Merge image tile into _Film_
            camera->film->MergeFilmTile(std::move(filmTile));
            reporter.Update();
        }, nTiles);
        reporter.Done();
    }

    // Save final image after rendering
    camera->film->WriteImage();
}