Cleaning up the basic jobs of render

This commit is contained in:
samcake 2017-04-07 18:35:27 -07:00
parent 58cec3fb96
commit e6844f4294
10 changed files with 253 additions and 114 deletions

View file

@ -19,6 +19,7 @@
#include <gpu/Context.h>
#include <render/CullTask.h>
#include <render/FilterTask.h>
#include <render/SortTask.h>
#include <render/DrawTask.h>
#include <render/DrawStatus.h>
@ -66,7 +67,7 @@ RenderDeferredTask::RenderDeferredTask(RenderFetchCullSortTask::Output items) {
// Filter the non antialiaased overlays
const int LAYER_NO_AA = 3;
const auto nonAAOverlays = addJob<FilterItemLayer>("Filter2DWebOverlays", overlayOpaques, LAYER_NO_AA);
const auto nonAAOverlays = addJob<FilterLayeredItems>("Filter2DWebOverlays", overlayOpaques, LAYER_NO_AA);
// Prepare deferred, generate the shared Deferred Frame Transform
const auto deferredFrameTransform = addJob<GenerateDeferredFrameTransform>("DeferredFrameTransform");
@ -184,7 +185,7 @@ RenderDeferredTask::RenderDeferredTask(RenderFetchCullSortTask::Output items) {
const auto debugAmbientOcclusionInputs = DebugAmbientOcclusion::Inputs(deferredFrameTransform, deferredFramebuffer, linearDepthTarget, ambientOcclusionUniforms).hasVarying();
addJob<DebugAmbientOcclusion>("DebugAmbientOcclusion", debugAmbientOcclusionInputs);
addJob<ZoneRenderer>("ZoneRenderer", opaques);
addJob<ZoneRendererTask>("ZoneRenderer", opaques);
// Scene Octree Debugging job
{

View file

@ -10,15 +10,19 @@
//
#include "ZoneRenderer.h"
const render::Selection::Name ZoneRenderer::ZONES_SELECTION { "RankedZones" };
#include <render/FilterTask.h>
#include <render/DrawTask.h>
using namespace render;
void ZoneRenderer::run(const render::SceneContextPointer& sceneContext, const render::RenderContextPointer& renderContext, const Inputs& inputs) {
auto& scene = sceneContext->_scene;
RenderArgs* args = renderContext->args;
const Selection::Name ZoneRendererTask::ZONES_SELECTION { "RankedZones" };
auto zones = scene->getSelection(ZONES_SELECTION);
ZoneRendererTask::ZoneRendererTask(const Inputs& inputs) {
const auto zoneItems = addJob<SelectItems>("FilterZones", inputs, ZONES_SELECTION);
// just draw them...
addJob<DrawBounds>("DrawZones", zoneItems);
}

View file

@ -27,19 +27,19 @@ signals:
protected:
};
class ZoneRenderer {
class ZoneRendererTask : public render::Task {
public:
static const render::Selection::Name ZONES_SELECTION;
using Inputs = render::ItemBounds;
using Config = ZoneRendererConfig;
using JobModel = render::Job::ModelI<ZoneRenderer, Inputs, Config>;
using JobModel = Model<ZoneRendererTask, Config>;
ZoneRenderer() {}
ZoneRendererTask(const Inputs& inputs);
void configure(const Config& config) { _maxDrawn = config.maxDrawn; }
void run(const render::SceneContextPointer& sceneContext, const render::RenderContextPointer& renderContext, const Inputs& inputs);
protected:
int _maxDrawn; // initialized by Config

View file

@ -16,8 +16,6 @@
#include <OctreeUtils.h>
#include <PerfStat.h>
#include <ViewFrustum.h>
#include <gpu/Context.h>
using namespace render;
@ -306,19 +304,3 @@ void CullSpatialSelection::run(const SceneContextPointer& sceneContext, const Re
std::static_pointer_cast<Config>(renderContext->jobConfig)->numItems = (int)outItems.size();
}
void FilterItemLayer::run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const ItemBounds& inItems, ItemBounds& outItems) {
auto& scene = sceneContext->_scene;
// Clear previous values
outItems.clear();
// For each item, filter it into one bucket
for (auto itemBound : inItems) {
auto& item = scene->getItem(itemBound.id);
if (item.getLayer() == _keepLayer) {
outItems.emplace_back(itemBound);
}
}
}

View file

@ -109,85 +109,6 @@ namespace render {
void run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const ItemSpatialTree::ItemSelection& inSelection, ItemBounds& outItems);
};
class FilterItemSelectionConfig : public Job::Config {
Q_OBJECT
Q_PROPERTY(int numItems READ getNumItems)
public:
int numItems{ 0 };
int getNumItems() { return numItems; }
};
class FilterItemSelection {
public:
using Config = FilterItemSelectionConfig;
using JobModel = Job::ModelIO<FilterItemSelection, ItemBounds, ItemBounds, Config>;
FilterItemSelection() {}
FilterItemSelection(const ItemFilter& filter) :
_filter(filter) {}
ItemFilter _filter{ ItemFilter::Builder::opaqueShape().withoutLayered() };
void configure(const Config& config);
void run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const ItemBounds& inItems, ItemBounds& outItems);
};
class MultiFilterItemConfig : public Job::Config {
Q_OBJECT
Q_PROPERTY(int numItems READ getNumItems)
public:
int numItems{ 0 };
int getNumItems() { return numItems; }
};
template <int NUM_FILTERS>
class MultiFilterItem {
public:
using ItemFilterArray = std::array<ItemFilter, NUM_FILTERS>;
using ItemBoundsArray = VaryingArray<ItemBounds, NUM_FILTERS>;
using Config = MultiFilterItemConfig;
using JobModel = Job::ModelIO<MultiFilterItem, ItemBounds, ItemBoundsArray, Config>;
MultiFilterItem() {}
MultiFilterItem(const ItemFilterArray& filters) :
_filters(filters) {}
ItemFilterArray _filters;
void configure(const Config& config) {}
void run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const ItemBounds& inItems, ItemBoundsArray& outItems) {
auto& scene = sceneContext->_scene;
// Clear previous values
for (size_t i = 0; i < NUM_FILTERS; i++) {
outItems[i].template edit<ItemBounds>().clear();
}
// For each item, filter it into one bucket
for (auto itemBound : inItems) {
auto& item = scene->getItem(itemBound.id);
auto itemKey = item.getKey();
for (size_t i = 0; i < NUM_FILTERS; i++) {
if (_filters[i].test(itemKey)) {
outItems[i].template edit<ItemBounds>().emplace_back(itemBound);
}
}
}
}
};
class FilterItemLayer {
public:
using JobModel = Job::ModelIO<FilterItemLayer, ItemBounds, ItemBounds>;
FilterItemLayer() {}
FilterItemLayer(int keepLayer) :
_keepLayer(keepLayer) {}
int _keepLayer { 0 };
void run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const ItemBounds& inItems, ItemBounds& outItems);
};
}
#endif // hifi_render_CullTask_h;

View file

@ -0,0 +1,83 @@
//
// FilterTask.cpp
// render/src/render
//
// Created by Sam Gateau on 2/2/16.
// Copyright 2016 High Fidelity, Inc.
//
// Distributed under the Apache License, Version 2.0.
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
//
#include "FilterTask.h"
#include <algorithm>
#include <assert.h>
#include <OctreeUtils.h>
#include <PerfStat.h>
#include <ViewFrustum.h>
#include <gpu/Context.h>
using namespace render;
void FilterLayeredItems::run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const ItemBounds& inItems, ItemBounds& outItems) {
auto& scene = sceneContext->_scene;
// Clear previous values
outItems.clear();
// For each item, filter it into one bucket
for (auto itemBound : inItems) {
auto& item = scene->getItem(itemBound.id);
if (item.getLayer() == _keepLayer) {
outItems.emplace_back(itemBound);
}
}
}
void SliceItems::run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const ItemBounds& inItems, ItemBounds& outItems) {
auto& scene = sceneContext->_scene;
// Now we have a selection of items to render
outItems.clear();
std::static_pointer_cast<Config>(renderContext->jobConfig)->setNumItems((int)inItems.size());
if (_rangeOffset < 0) return;
int maxItemNum = std::min(_rangeOffset + _rangeLength, (int)inItems.size());
for (int i = _rangeOffset; i < maxItemNum; i++) {
outItems.emplace_back(inItems[i]);
}
}
void SelectItems::run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const ItemBounds& inItems, ItemBounds& outItems) {
auto& scene = sceneContext->_scene;
auto selection = scene->getSelection(_name);
const auto& selectedItems = selection.getItems();
if (!selectedItems.empty()) {
for (auto src : inItems) {
if (selection.contains(src.id)) {
outItems.emplace_back(src);
}
}
}
}
void MetaToSubItems::run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const ItemBounds& inItems, ItemIDs& outItems) {
auto& scene = sceneContext->_scene;
// Now we have a selection of items to render
outItems.clear();
for (auto idBound : inItems) {
auto& item = scene->getItem(idBound.id);
item.fetchMetaSubItems(outItems);
}
}

View file

@ -0,0 +1,136 @@
//
// FilterTask.h
// render/src/render
//
// Created by Sam Gateau on 2/2/16.
// Copyright 2016 High Fidelity, Inc.
//
// Distributed under the Apache License, Version 2.0.
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
//
#ifndef hifi_render_FilterTask_h
#define hifi_render_FilterTask_h
#include "Engine.h"
#include "ViewFrustum.h"
namespace render {
class MultiFilterItemsConfig : public Job::Config {
Q_OBJECT
Q_PROPERTY(int numItems READ getNumItems)
public:
int numItems{ 0 };
int getNumItems() { return numItems; }
};
// Filter inbound of items into multiple buckets defined from the job's Filter array
template <int NUM_FILTERS>
class MultiFilterItems {
public:
using ItemFilterArray = std::array<ItemFilter, NUM_FILTERS>;
using ItemBoundsArray = VaryingArray<ItemBounds, NUM_FILTERS>;
using Config = MultiFilterItemsConfig;
using JobModel = Job::ModelIO<MultiFilterItems, ItemBounds, ItemBoundsArray, Config>;
MultiFilterItems() {}
MultiFilterItems(const ItemFilterArray& filters) :
_filters(filters) {}
ItemFilterArray _filters;
void configure(const Config& config) {}
void run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const ItemBounds& inItems, ItemBoundsArray& outItems) {
auto& scene = sceneContext->_scene;
// Clear previous values
for (size_t i = 0; i < NUM_FILTERS; i++) {
outItems[i].template edit<ItemBounds>().clear();
}
// For each item, filter it into one bucket
for (auto itemBound : inItems) {
auto& item = scene->getItem(itemBound.id);
auto itemKey = item.getKey();
for (size_t i = 0; i < NUM_FILTERS; i++) {
if (_filters[i].test(itemKey)) {
outItems[i].template edit<ItemBounds>().emplace_back(itemBound);
}
}
}
}
};
// Filter the items belonging to the job's keep layer
class FilterLayeredItems {
public:
using JobModel = Job::ModelIO<FilterLayeredItems, ItemBounds, ItemBounds>;
FilterLayeredItems() {}
FilterLayeredItems(int keepLayer) :
_keepLayer(keepLayer) {}
int _keepLayer { 0 };
void run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const ItemBounds& inItems, ItemBounds& outItems);
};
// SliceItems job config defining the slice range
class SliceItemsConfig : public Job::Config {
Q_OBJECT
Q_PROPERTY(int rangeOffset MEMBER rangeOffset)
Q_PROPERTY(int rangeLength MEMBER rangeLength)
Q_PROPERTY(int numItems READ getNumItems NOTIFY dirty())
int numItems { 0 };
public:
int rangeOffset{ -1 };
int rangeLength{ 1 };
int getNumItems() { return numItems; }
void setNumItems(int n) { numItems = n; emit dirty(); }
signals:
void dirty();
};
// Keep items in the job slice (defined from config)
class SliceItems {
public:
using Config = SliceItemsConfig;
using JobModel = Job::ModelIO<SliceItems, ItemBounds, ItemBounds, Config>;
SliceItems() {}
int _rangeOffset{ -1 };
int _rangeLength{ 1 };
void configure(const Config& config) {
_rangeOffset = config.rangeOffset;
_rangeLength = config.rangeLength;
}
void run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const ItemBounds& inItems, ItemBounds& outItems);
};
// Keep items belonging to the job selection
class SelectItems {
public:
using JobModel = Job::ModelIO<SelectItems, ItemBounds, ItemBounds>;
std::string _name;
SelectItems(const Selection::Name& name) : _name(name) {}
void run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const ItemBounds& inItems, ItemBounds& outItems);
};
// From meta-Items, generate the sub-items
class MetaToSubItems {
public:
using JobModel = Job::ModelIO<MetaToSubItems, ItemBounds, ItemIDs>;
MetaToSubItems() {}
void run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const ItemBounds& inItems, ItemIDs& outItems);
};
}
#endif // hifi_render_FilterTask_h;

View file

@ -12,6 +12,7 @@
#include "RenderFetchCullSortTask.h"
#include "CullTask.h"
#include "FilterTask.h"
#include "SortTask.h"
using namespace render;
@ -36,23 +37,23 @@ RenderFetchCullSortTask::RenderFetchCullSortTask(CullFunctor cullFunctor) {
const int LIGHT_BUCKET = 2;
const int META_BUCKET = 3;
const int BACKGROUND_BUCKET = 2;
MultiFilterItem<NUM_SPATIAL_FILTERS>::ItemFilterArray spatialFilters = { {
MultiFilterItems<NUM_SPATIAL_FILTERS>::ItemFilterArray spatialFilters = { {
ItemFilter::Builder::opaqueShape(),
ItemFilter::Builder::transparentShape(),
ItemFilter::Builder::light(),
ItemFilter::Builder::meta()
} };
MultiFilterItem<NUM_NON_SPATIAL_FILTERS>::ItemFilterArray nonspatialFilters = { {
MultiFilterItems<NUM_NON_SPATIAL_FILTERS>::ItemFilterArray nonspatialFilters = { {
ItemFilter::Builder::opaqueShape(),
ItemFilter::Builder::transparentShape(),
ItemFilter::Builder::background()
} };
const auto filteredSpatialBuckets =
addJob<MultiFilterItem<NUM_SPATIAL_FILTERS>>("FilterSceneSelection", culledSpatialSelection, spatialFilters)
.get<MultiFilterItem<NUM_SPATIAL_FILTERS>::ItemBoundsArray>();
addJob<MultiFilterItems<NUM_SPATIAL_FILTERS>>("FilterSceneSelection", culledSpatialSelection, spatialFilters)
.get<MultiFilterItems<NUM_SPATIAL_FILTERS>::ItemBoundsArray>();
const auto filteredNonspatialBuckets =
addJob<MultiFilterItem<NUM_NON_SPATIAL_FILTERS>>("FilterOverlaySelection", nonspatialSelection, nonspatialFilters)
.get<MultiFilterItem<NUM_NON_SPATIAL_FILTERS>::ItemBoundsArray>();
addJob<MultiFilterItems<NUM_NON_SPATIAL_FILTERS>>("FilterOverlaySelection", nonspatialSelection, nonspatialFilters)
.get<MultiFilterItems<NUM_NON_SPATIAL_FILTERS>::ItemBoundsArray>();
// Extract opaques / transparents / lights / overlays
const auto opaques = addJob<DepthSortItems>("DepthSortOpaque", filteredSpatialBuckets[OPAQUE_SHAPE_BUCKET]);

View file

@ -56,3 +56,11 @@ Selection::Selection(const Name& name, const ItemIDs& items) :
{
}
bool Selection::contains(ItemID id) const {
for (auto selected : _items) {
if (selected == id) {
return true;
}
}
return false;
}

View file

@ -33,6 +33,9 @@ namespace render {
const ItemIDs& getItems() const { return _items; }
bool isEmpty() const { return _items.empty(); }
bool contains(ItemID id) const;
protected:
Name _name;
ItemIDs _items;