13 #ifndef hifi_render_Item_h
14 #define hifi_render_Item_h
29 #include <graphics/Material.h>
30 #include "ShapePipeline.h"
32 #include "BlendshapeConstants.h"
33 #include "HighlightStyle.h"
34 #include "FadeProperties.h"
38 typedef int32_t Index;
39 const Index INVALID_INDEX{ -1 };
78 enum Layer : uint8_t {
92 LAYER_BITS_ALL = 0x07,
95 enum FlagBit : uint32_t {
111 LAST_TAG_BIT = FIRST_TAG_BIT + NUM_TAGS,
114 LAST_LAYER_BIT = FIRST_LAYER_BIT + NUM_LAYER_BITS,
124 typedef std::bitset<NUM_FLAGS> Flags;
127 const static uint32_t KEY_TAG_BITS_MASK;
128 static uint32_t evalTagBitsWithKeyBits(uint8_t tagBits,
const uint32_t keyBits) {
129 return (keyBits & ~KEY_TAG_BITS_MASK) | (((uint32_t)tagBits) << FIRST_TAG_BIT);
133 const static uint32_t KEY_LAYER_BITS_MASK;
134 static uint32_t evalLayerBitsWithKeyBits(uint8_t layer,
const uint32_t keyBits) {
135 return (keyBits & ~KEY_LAYER_BITS_MASK) | (((uint32_t)layer & LAYER_BITS_ALL) << FIRST_LAYER_BIT);
141 ItemKey() : _flags(0) {}
142 ItemKey(
const Flags& flags) : _flags(flags) {}
144 bool operator== (
const ItemKey& rhs)
const {
return _flags == rhs._flags; }
145 bool operator!= (
const ItemKey& rhs)
const {
return _flags != rhs._flags; }
148 friend class ItemKey;
152 Builder(
const ItemKey& key) : _flags{ key._flags } {}
154 ItemKey build()
const {
return ItemKey(_flags); }
156 Builder& withTypeShape() { _flags.set(TYPE_SHAPE);
return (*
this); }
157 Builder& withTypeLight() { _flags.set(TYPE_LIGHT);
return (*
this); }
158 Builder& withTypeMeta() { _flags.set(TYPE_META);
return (*
this); }
159 Builder& withTransparent() { _flags.set(TRANSLUCENT);
return (*
this); }
160 Builder& withViewSpace() { _flags.set(VIEW_SPACE);
return (*
this); }
161 Builder& withoutViewSpace() { _flags.reset(VIEW_SPACE);
return (*
this); }
162 Builder& withDynamic() { _flags.set(DYNAMIC);
return (*
this); }
163 Builder& withDeformed() { _flags.set(DEFORMED);
return (*
this); }
164 Builder& withInvisible() { _flags.set(INVISIBLE);
return (*
this); }
165 Builder& withVisible() { _flags.reset(INVISIBLE);
return (*
this); }
166 Builder& withShadowCaster() { _flags.set(SHADOW_CASTER);
return (*
this); }
167 Builder& withoutShadowCaster() { _flags.reset(SHADOW_CASTER);
return (*
this); }
168 Builder& withMetaCullGroup() { _flags.set(META_CULL_GROUP);
return (*
this); }
169 Builder& withoutMetaCullGroup() { _flags.reset(META_CULL_GROUP);
return (*
this); }
170 Builder& withSubMetaCulled() { _flags.set(SUB_META_CULLED);
return (*
this); }
171 Builder& withoutSubMetaCulled() { _flags.reset(SUB_META_CULLED);
return (*
this); }
172 Builder& withMirror() { _flags.set(MIRROR);
return (*
this); }
173 Builder& withSimulate() { _flags.set(SIMULATE);
return (*
this); }
175 Builder& withTag(Tag tag) { _flags.set(
static_cast<size_t>(FIRST_TAG_BIT) +
static_cast<size_t>(tag));
return (*
this); }
177 Builder& withTagBits(uint8_t tagBits) { _flags = evalTagBitsWithKeyBits(tagBits, _flags.to_ulong());
return (*
this); }
179 Builder& withLayer(uint8_t layer) { _flags = evalLayerBitsWithKeyBits(layer, _flags.to_ulong());
return (*
this); }
180 Builder& withoutLayer() {
return withLayer(LAYER_DEFAULT); }
182 Builder& withOutline() { _flags.set(OUTLINE);
return (*
this); }
183 Builder& withoutOutline() { _flags.reset(OUTLINE);
return (*
this); }
186 static Builder opaqueShape() {
return Builder().withTypeShape(); }
187 static Builder transparentShape() {
return Builder().withTypeShape().withTransparent(); }
188 static Builder light() {
return Builder().withTypeLight(); }
189 static Builder background() {
return Builder().withViewSpace().withLayer(LAYER_BACKGROUND); }
191 ItemKey(
const Builder& builder) : ItemKey(builder._flags) {}
193 bool isShape()
const {
return _flags[TYPE_SHAPE]; }
194 bool isLight()
const {
return _flags[TYPE_LIGHT]; }
195 bool isMeta()
const {
return _flags[TYPE_META]; }
197 bool isOpaque()
const {
return !_flags[TRANSLUCENT]; }
198 bool isTransparent()
const {
return _flags[TRANSLUCENT]; }
200 bool isWorldSpace()
const {
return !_flags[VIEW_SPACE]; }
201 bool isViewSpace()
const {
return _flags[VIEW_SPACE]; }
203 bool isStatic()
const {
return !_flags[DYNAMIC]; }
204 bool isDynamic()
const {
return _flags[DYNAMIC]; }
206 bool isRigid()
const {
return !_flags[DEFORMED]; }
207 bool isDeformed()
const {
return _flags[DEFORMED]; }
209 bool isVisible()
const {
return !_flags[INVISIBLE]; }
210 bool isInvisible()
const {
return _flags[INVISIBLE]; }
212 bool isShadowCaster()
const {
return _flags[SHADOW_CASTER]; }
214 bool isMetaCullGroup()
const {
return _flags[META_CULL_GROUP]; }
215 void setMetaCullGroup(
bool cullGroup) { (cullGroup ? _flags.set(META_CULL_GROUP) : _flags.reset(META_CULL_GROUP)); }
217 bool isSubMetaCulled()
const {
return _flags[SUB_META_CULLED]; }
218 void setSubMetaCulled(
bool metaCulled) { (metaCulled ? _flags.set(SUB_META_CULLED) : _flags.reset(SUB_META_CULLED)); }
220 bool isNotMirror()
const {
return !_flags[MIRROR]; }
221 bool isMirror()
const {
return _flags[MIRROR]; }
223 bool isNotSimulate()
const {
return !_flags[SIMULATE]; }
224 bool isSimulate()
const {
return _flags[SIMULATE]; }
226 bool isTag(Tag tag)
const {
return _flags[
static_cast<size_t>(FIRST_TAG_BIT) +
static_cast<size_t>(tag)]; }
227 uint8_t getTagBits()
const {
return ((_flags.to_ulong() & KEY_TAG_BITS_MASK) >> FIRST_TAG_BIT); }
229 uint8_t getLayer()
const {
return ((_flags.to_ulong() & KEY_LAYER_BITS_MASK) >> FIRST_LAYER_BIT); }
230 bool isLayer(uint8_t layer)
const {
return getLayer() == layer; }
231 bool isLayered()
const {
return getLayer() != LAYER_DEFAULT; }
232 bool isSpatial()
const {
return !isLayered(); }
234 bool isOutline()
const {
return _flags[OUTLINE]; }
237 bool isSmall()
const {
return _flags[__SMALLER]; }
238 void setSmaller(
bool smaller) { (smaller ? _flags.set(__SMALLER) : _flags.reset(__SMALLER)); }
240 bool operator==(
const ItemKey& key) {
return (_flags == key._flags); }
241 bool operator!=(
const ItemKey& key) {
return (_flags != key._flags); }
243 using ItemKeys = std::vector<ItemKey>;
245 inline QDebug operator<<(QDebug debug,
const ItemKey& itemKey) {
246 debug <<
"[ItemKey: isOpaque:" << itemKey.isOpaque()
247 <<
", isStatic:" << itemKey.isStatic()
248 <<
", isWorldSpace:" << itemKey.isWorldSpace()
255 ItemKey::Flags _value{ 0 };
256 ItemKey::Flags _mask{ 0 };
259 ItemFilter(
const ItemKey::Flags& value = ItemKey::Flags(0),
const ItemKey::Flags& mask = ItemKey::Flags(0)) : _value(value), _mask(mask) {}
262 friend class ItemFilter;
263 ItemKey::Flags _value{ 0 };
264 ItemKey::Flags _mask{ 0 };
267 Builder(
const ItemFilter& srcFilter) : _value(srcFilter._value), _mask(srcFilter._mask) {}
269 ItemFilter build()
const {
return ItemFilter(_value, _mask); }
271 Builder& withTypeShape() { _value.set(ItemKey::TYPE_SHAPE); _mask.set(ItemKey::TYPE_SHAPE);
return (*
this); }
272 Builder& withTypeLight() { _value.set(ItemKey::TYPE_LIGHT); _mask.set(ItemKey::TYPE_LIGHT);
return (*
this); }
273 Builder& withTypeMeta() { _value.set(ItemKey::TYPE_META); _mask.set(ItemKey::TYPE_META);
return (*
this); }
275 Builder& withOpaque() { _value.reset(ItemKey::TRANSLUCENT); _mask.set(ItemKey::TRANSLUCENT);
return (*
this); }
276 Builder& withTransparent() { _value.set(ItemKey::TRANSLUCENT); _mask.set(ItemKey::TRANSLUCENT);
return (*
this); }
278 Builder& withWorldSpace() { _value.reset(ItemKey::VIEW_SPACE); _mask.set(ItemKey::VIEW_SPACE);
return (*
this); }
279 Builder& withViewSpace() { _value.set(ItemKey::VIEW_SPACE); _mask.set(ItemKey::VIEW_SPACE);
return (*
this); }
281 Builder& withStatic() { _value.reset(ItemKey::DYNAMIC); _mask.set(ItemKey::DYNAMIC);
return (*
this); }
282 Builder& withDynamic() { _value.set(ItemKey::DYNAMIC); _mask.set(ItemKey::DYNAMIC);
return (*
this); }
284 Builder& withRigid() { _value.reset(ItemKey::DEFORMED); _mask.set(ItemKey::DEFORMED);
return (*
this); }
285 Builder& withDeformed() { _value.set(ItemKey::DEFORMED); _mask.set(ItemKey::DEFORMED);
return (*
this); }
287 Builder& withVisible() { _value.reset(ItemKey::INVISIBLE); _mask.set(ItemKey::INVISIBLE);
return (*
this); }
288 Builder& withInvisible() { _value.set(ItemKey::INVISIBLE); _mask.set(ItemKey::INVISIBLE);
return (*
this); }
290 Builder& withNoShadowCaster() { _value.reset(ItemKey::SHADOW_CASTER); _mask.set(ItemKey::SHADOW_CASTER);
return (*
this); }
291 Builder& withShadowCaster() { _value.set(ItemKey::SHADOW_CASTER); _mask.set(ItemKey::SHADOW_CASTER);
return (*
this); }
293 Builder& withoutMetaCullGroup() { _value.reset(ItemKey::META_CULL_GROUP); _mask.set(ItemKey::META_CULL_GROUP);
return (*
this); }
294 Builder& withMetaCullGroup() { _value.set(ItemKey::META_CULL_GROUP); _mask.set(ItemKey::META_CULL_GROUP);
return (*
this); }
296 Builder& withoutSubMetaCulled() { _value.reset(ItemKey::SUB_META_CULLED); _mask.set(ItemKey::SUB_META_CULLED);
return (*
this); }
297 Builder& withSubMetaCulled() { _value.set(ItemKey::SUB_META_CULLED); _mask.set(ItemKey::SUB_META_CULLED);
return (*
this); }
299 Builder& withoutMirror() { _value.reset(ItemKey::MIRROR); _mask.set(ItemKey::MIRROR);
return (*
this); }
300 Builder& withMirror() { _value.set(ItemKey::MIRROR); _mask.set(ItemKey::MIRROR);
return (*
this); }
302 Builder& withoutSimulate() { _value.reset(ItemKey::SIMULATE); _mask.set(ItemKey::SIMULATE);
return (*
this); }
303 Builder& withSimulate() { _value.set(ItemKey::SIMULATE); _mask.set(ItemKey::SIMULATE);
return (*
this); }
305 Builder& withoutTag(ItemKey::Tag tagIndex) { _value.reset(
static_cast<size_t>(ItemKey::FIRST_TAG_BIT) +
static_cast<size_t>(tagIndex)); _mask.set(
static_cast<size_t>(ItemKey::FIRST_TAG_BIT) +
static_cast<size_t>(tagIndex));
return (*
this); }
306 Builder& withTag(ItemKey::Tag tagIndex) { _value.set(
static_cast<size_t>(ItemKey::FIRST_TAG_BIT) +
static_cast<size_t>(tagIndex)); _mask.set(
static_cast<size_t>(ItemKey::FIRST_TAG_BIT) +
static_cast<size_t>(tagIndex));
return (*
this); }
308 Builder& withTagBits(uint8_t tagBits, uint8_t tagMask) { _value = ItemKey::evalTagBitsWithKeyBits(tagBits, _value.to_ulong()); _mask = ItemKey::evalTagBitsWithKeyBits(tagMask, _mask.to_ulong());
return (*
this); }
310 Builder& withoutLayered() { _value = ItemKey::evalLayerBitsWithKeyBits(ItemKey::LAYER_DEFAULT, _value.to_ulong()); _mask |= ItemKey::KEY_LAYER_BITS_MASK;
return (*
this); }
311 Builder& withLayer(uint8_t layer) { _value = ItemKey::evalLayerBitsWithKeyBits(layer, _value.to_ulong()); _mask |= ItemKey::KEY_LAYER_BITS_MASK;
return (*
this); }
313 Builder& withoutOutline() { _value.reset(ItemKey::OUTLINE); _mask.set(ItemKey::OUTLINE);
return (*
this); }
314 Builder& withOutline() { _value.set(ItemKey::OUTLINE); _mask.set(ItemKey::OUTLINE);
return (*
this); }
316 Builder& withNothing() { _value.reset(); _mask.reset();
return (*
this); }
319 static Builder visibleWorldItems() {
return Builder().withVisible().withWorldSpace(); }
320 static Builder opaqueShape() {
return Builder().withTypeShape().withOpaque().withWorldSpace(); }
321 static Builder transparentShape() {
return Builder().withTypeShape().withTransparent().withWorldSpace(); }
322 static Builder light() {
return Builder().withTypeLight(); }
323 static Builder meta() {
return Builder().withTypeMeta(); }
324 static Builder mirror() {
return Builder().withMirror(); }
325 static Builder background() {
return Builder().withViewSpace().withLayer(ItemKey::LAYER_BACKGROUND); }
326 static Builder nothing() {
return Builder().withNothing(); }
329 ItemFilter(
const Builder& builder) : ItemFilter(builder._value, builder._mask) {}
332 bool test(
const ItemKey& key)
const {
return (key._flags & _mask) == (_value & _mask); }
333 bool selectsNothing()
const {
return !_mask.any(); }
337 bool operator() (
const ItemFilter& left,
const ItemFilter& right)
const {
338 if (left._value.to_ulong() == right._value.to_ulong()) {
339 return left._mask.to_ulong() < right._mask.to_ulong();
341 return left._value.to_ulong() < right._value.to_ulong();
347 inline QDebug operator<<(QDebug debug,
const ItemFilter& me) {
348 debug <<
"[ItemFilter: opaqueShape:" << me.test(ItemKey::Builder::opaqueShape().build())
357 ItemBound(ItemID
id) : id(id) { }
358 ItemBound(ItemID
id,
const AABox& bound) : id(id), bound(bound) { }
362 uint32_t padding { 0 };
366 using ItemBounds = std::vector<ItemBound>;
372 typedef std::vector<Item> Vector;
375 static const ID INVALID_ITEM_ID;
376 static const ItemCell INVALID_CELL;
379 static void clearID(ID&
id) {
id = INVALID_ITEM_ID; }
380 static bool isValidID(
const ID
id) {
return id != INVALID_ITEM_ID; }
391 ACTIVE_IN_BULLET = 0,
394 SIMULATION_OWNER = 3,
396 OTHER_SIMULATION_OWNER = 5,
397 ENTITY_HOST_TYPE = 6,
398 GENERIC_TRANSITION = 7,
399 GENERIC_TRANSITION_OUT = 8,
400 GENERIC_TRANSITION_IN = 9,
401 USER_TRANSITION_OUT = 10,
402 USER_TRANSITION_IN = 11,
410 unsigned short _scale = 0xFFFF;
411 unsigned char _color = 0xFF;
412 unsigned char _icon = 0xFF;
414 const static Value INVALID;
417 Value(
float scale,
float hue,
unsigned char icon = 0xFF) { setScale(scale); setColor(hue); setIcon(icon); }
420 void setScale(
float scale);
422 void setColor(
float hue);
425 void setIcon(
unsigned char icon);
428 static const float RED;
429 static const float YELLOW;
430 static const float GREEN;
431 static const float CYAN;
432 static const float BLUE;
433 static const float MAGENTA;
436 int getPackedData()
const {
return *((
const int*)
this); }
439 typedef std::function<Value()> Getter;
440 typedef std::vector<Getter> Getters;
444 void addGetter(
const Getter& getter) { _values.push_back(getter); }
446 size_t getNumValues()
const {
return _values.size(); }
448 using Values = std::vector <Value>;
449 Values getCurrentValues()
const;
451 typedef std::shared_ptr<Status> StatusPointer;
454 class UpdateFunctorInterface {
456 virtual ~UpdateFunctorInterface() {}
458 typedef std::shared_ptr<UpdateFunctorInterface> UpdateFunctorPointer;
461 class PayloadInterface {
463 virtual const ItemKey getKey()
const = 0;
464 virtual const Bound getBound(RenderArgs* args)
const = 0;
465 virtual void render(RenderArgs* args) = 0;
466 virtual void renderSimulate(RenderArgs* args) = 0;
468 virtual const ShapeKey getShapeKey()
const = 0;
470 virtual uint32_t fetchMetaSubItems(ItemIDs& subItems)
const = 0;
472 virtual bool passesZoneOcclusionTest(
const std::unordered_set<QUuid>& containingZones)
const = 0;
474 virtual ItemID computeMirrorView(ViewFrustum& viewFrustum)
const = 0;
476 virtual HighlightStyle getOutlineStyle(
const ViewFrustum& viewFrustum,
const size_t height)
const = 0;
478 virtual FadeProperties getFadeProperties(
const TransitionType type)
const = 0;
480 ~PayloadInterface() {}
483 const StatusPointer& getStatus()
const {
return _status; }
484 void addStatusGetter(
const Status::Getter& getter);
485 void addStatusGetters(
const Status::Getters& getters);
488 StatusPointer _status;
491 virtual void update(
const UpdateFunctorPointer& functor) = 0;
493 typedef std::shared_ptr<PayloadInterface> PayloadPointer;
499 bool exist()
const {
return (
bool)(_payload); }
502 void resetPayload(
const PayloadPointer& payload);
503 void resetCell(ItemCell cell = INVALID_CELL,
bool _small =
false) { _cell = cell; _key.setSmaller(_small); }
504 void update(
const UpdateFunctorPointer& updateFunctor);
505 void kill() { _payload.reset(); resetCell(); _key._flags.reset(); }
508 const ItemKey& getKey()
const {
return _key; }
511 const ItemCell& getCell()
const {
return _cell; }
516 const Bound getBound(RenderArgs* args)
const {
return _payload->getBound(args); }
519 int getLayer()
const {
return _key.getLayer(); }
522 void render(RenderArgs* args)
const { _payload->render(args); }
525 void renderSimulate(RenderArgs* args) { _payload->renderSimulate(args); }
528 const ShapeKey getShapeKey()
const;
531 uint32_t fetchMetaSubItems(ItemIDs& subItems)
const {
return _payload->fetchMetaSubItems(subItems); }
532 uint32_t fetchMetaSubItemBounds(ItemBounds& subItemBounds, Scene& scene, RenderArgs* args)
const;
534 bool passesZoneOcclusionTest(
const std::unordered_set<QUuid>& containingZones)
const {
return _payload->passesZoneOcclusionTest(containingZones); }
536 ItemID computeMirrorView(ViewFrustum& viewFrustum)
const {
return _payload->computeMirrorView(viewFrustum); }
538 HighlightStyle getOutlineStyle(
const ViewFrustum& viewFrustum,
const size_t height)
const {
return _payload->getOutlineStyle(viewFrustum, height); }
540 FadeProperties getFadeProperties(
const TransitionType type)
const {
return _payload->getFadeProperties(type); }
543 const StatusPointer& getStatus()
const {
return _payload->getStatus(); }
545 void setTransitionId(Index
id) { _transitionId = id; }
546 Index getTransitionId()
const {
return _transitionId; }
549 PayloadPointer _payload;
551 ItemCell _cell { INVALID_CELL };
552 Index _transitionId { INVALID_INDEX };
558 typedef Item::UpdateFunctorInterface UpdateFunctorInterface;
559 typedef Item::UpdateFunctorPointer UpdateFunctorPointer;
560 typedef std::vector<UpdateFunctorPointer> UpdateFunctors;
562 template <
class T>
class UpdateFunctor :
public Item::UpdateFunctorInterface {
564 typedef std::function<void(T&)> Func;
567 UpdateFunctor(Func func): _func(func) {}
572 inline QDebug operator<<(QDebug debug,
const Item& item) {
573 debug <<
"[Item: _key:" << item.getKey() <<
"]";
578 template <
class T>
const ItemKey payloadGetKey(
const std::shared_ptr<T>& payloadData) {
return ItemKey(); }
579 template <
class T>
const Item::Bound payloadGetBound(
const std::shared_ptr<T>& payloadData, RenderArgs* args) {
return Item::Bound(); }
580 template <
class T>
void payloadRender(
const std::shared_ptr<T>& payloadData, RenderArgs* args) { }
581 template <
class T>
void payloadRenderSimulate(
const std::shared_ptr<T>& payloadData, RenderArgs* args) { }
587 template <
class T>
const ShapeKey shapeGetShapeKey(
const std::shared_ptr<T>& payloadData) {
return ShapeKey::Builder::ownPipeline(); }
591 template <
class T> uint32_t metaFetchMetaSubItems(
const std::shared_ptr<T>& payloadData, ItemIDs& subItems) {
return 0; }
595 template <
class T>
bool payloadPassesZoneOcclusionTest(
const std::shared_ptr<T>& payloadData,
const std::unordered_set<QUuid>& containingZones) {
return true; }
598 template <
class T> ItemID payloadComputeMirrorView(
const std::shared_ptr<T>& payloadData, ViewFrustum& viewFrustum) {
return Item::INVALID_ITEM_ID; }
602 template <
class T> HighlightStyle payloadGetOutlineStyle(
const std::shared_ptr<T>& payloadData,
const ViewFrustum& viewFrustum,
const size_t height) {
603 return HighlightStyle();
608 template <
class T> FadeProperties payloadGetFadeProperties(
const std::shared_ptr<T>& payloadData,
const TransitionType type) {
return FadeProperties(); }
614 template <
class T>
class Payload :
public Item::PayloadInterface {
616 typedef std::shared_ptr<T> DataPointer;
617 typedef UpdateFunctor<T> Updater;
619 Payload(
const DataPointer& data) : _data(data) {}
620 virtual ~Payload() =
default;
623 virtual const ItemKey getKey()
const override {
return payloadGetKey<T>(_data); }
624 virtual const Item::Bound getBound(RenderArgs* args)
const override {
return payloadGetBound<T>(_data, args); }
626 virtual void render(RenderArgs* args)
override { payloadRender<T>(_data, args); }
627 virtual void renderSimulate(RenderArgs* args)
override { payloadRenderSimulate<T>(_data, args); }
630 virtual const ShapeKey getShapeKey()
const override {
return shapeGetShapeKey<T>(_data); }
633 virtual uint32_t fetchMetaSubItems(ItemIDs& subItems)
const override {
return metaFetchMetaSubItems<T>(_data, subItems); }
635 virtual bool passesZoneOcclusionTest(
const std::unordered_set<QUuid>& containingZones)
const override {
return payloadPassesZoneOcclusionTest<T>(_data, containingZones); }
637 virtual ItemID computeMirrorView(ViewFrustum& viewFrustum)
const override {
return payloadComputeMirrorView<T>(_data, viewFrustum); }
639 virtual HighlightStyle getOutlineStyle(
const ViewFrustum& viewFrustum,
const size_t height)
const override {
return payloadGetOutlineStyle<T>(_data, viewFrustum, height); }
641 virtual FadeProperties getFadeProperties(
const TransitionType type)
const override {
return payloadGetFadeProperties<T>(_data, type); }
647 virtual void update(
const UpdateFunctorPointer& functor)
override {
648 std::static_pointer_cast<Updater>(functor)->_func((*_data));
687 class PayloadProxyInterface {
689 using ProxyPayload = Payload<PayloadProxyInterface>;
690 using Pointer = ProxyPayload::DataPointer;
692 virtual ItemKey getKey() = 0;
693 virtual ShapeKey getShapeKey() = 0;
694 virtual Item::Bound getBound(RenderArgs* args) = 0;
695 virtual void render(RenderArgs* args) = 0;
696 virtual void renderSimulate(RenderArgs* args) = 0;
697 virtual uint32_t metaFetchMetaSubItems(ItemIDs& subItems)
const = 0;
698 virtual bool passesZoneOcclusionTest(
const std::unordered_set<QUuid>& containingZones)
const = 0;
699 virtual ItemID computeMirrorView(ViewFrustum& viewFrustum)
const = 0;
700 virtual HighlightStyle getOutlineStyle(
const ViewFrustum& viewFrustum,
const size_t height)
const = 0;
701 virtual FadeProperties getFadeProperties(
const TransitionType type)
const = 0;
704 virtual void handleBlendedVertices(
int blendshapeNumber,
const QVector<BlendshapeOffset>& blendshapeOffsets,
705 const QVector<int>& blendedMeshSizes,
const render::ItemIDs& subItemIDs) {};
708 template <>
const ItemKey payloadGetKey(
const PayloadProxyInterface::Pointer& payload);
709 template <>
const Item::Bound payloadGetBound(
const PayloadProxyInterface::Pointer& payload, RenderArgs* args);
710 template <>
void payloadRender(
const PayloadProxyInterface::Pointer& payload, RenderArgs* args);
711 template <>
void payloadRenderSimulate(
const PayloadProxyInterface::Pointer& payload, RenderArgs* args);
712 template <> uint32_t metaFetchMetaSubItems(
const PayloadProxyInterface::Pointer& payload, ItemIDs& subItems);
713 template <>
const ShapeKey shapeGetShapeKey(
const PayloadProxyInterface::Pointer& payload);
714 template <>
bool payloadPassesZoneOcclusionTest(
const PayloadProxyInterface::Pointer& payload,
const std::unordered_set<QUuid>& containingZones);
715 template <> ItemID payloadComputeMirrorView(
const PayloadProxyInterface::Pointer& payload, ViewFrustum& viewFrustum);
716 template <> HighlightStyle payloadGetOutlineStyle(
const PayloadProxyInterface::Pointer& payload,
const ViewFrustum& viewFrustum,
const size_t height);
717 template <> FadeProperties payloadGetFadeProperties(
const PayloadProxyInterface::Pointer& payload,
const TransitionType type);
719 typedef Item::PayloadPointer PayloadPointer;
720 typedef std::vector<PayloadPointer> Payloads;
723 using ShapeBounds = std::unordered_map<ShapeKey, ItemBounds, ShapeKey::Hash, ShapeKey::KeyEqual>;