mirror of
https://github.com/HifiExperiments/overte.git
synced 2025-08-09 13:18:26 +02:00
Merge pull request #7314 from samcake/color
Fix a potentially bad access to RenderItem case from Overlay
This commit is contained in:
commit
8a36df13df
4 changed files with 40 additions and 16 deletions
|
@ -13,6 +13,7 @@
|
||||||
|
|
||||||
#include <RegisteredMetaTypes.h>
|
#include <RegisteredMetaTypes.h>
|
||||||
#include <SharedUtil.h>
|
#include <SharedUtil.h>
|
||||||
|
#include "Application.h"
|
||||||
|
|
||||||
|
|
||||||
const float DEFAULT_LINE_WIDTH = 1.0f;
|
const float DEFAULT_LINE_WIDTH = 1.0f;
|
||||||
|
@ -38,15 +39,17 @@ Base3DOverlay::Base3DOverlay(const Base3DOverlay* base3DOverlay) :
|
||||||
_drawInFront(base3DOverlay->_drawInFront)
|
_drawInFront(base3DOverlay->_drawInFront)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void Base3DOverlay::setProperties(const QVariantMap& properties) {
|
void Base3DOverlay::setProperties(const QVariantMap& properties) {
|
||||||
Overlay::setProperties(properties);
|
Overlay::setProperties(properties);
|
||||||
|
|
||||||
|
bool needRenderItemUpdate = false;
|
||||||
|
|
||||||
auto drawInFront = properties["drawInFront"];
|
auto drawInFront = properties["drawInFront"];
|
||||||
|
|
||||||
if (drawInFront.isValid()) {
|
if (drawInFront.isValid()) {
|
||||||
bool value = drawInFront.toBool();
|
bool value = drawInFront.toBool();
|
||||||
setDrawInFront(value);
|
setDrawInFront(value);
|
||||||
|
needRenderItemUpdate = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto position = properties["position"];
|
auto position = properties["position"];
|
||||||
|
@ -60,16 +63,19 @@ void Base3DOverlay::setProperties(const QVariantMap& properties) {
|
||||||
}
|
}
|
||||||
if (position.isValid()) {
|
if (position.isValid()) {
|
||||||
setPosition(vec3FromVariant(position));
|
setPosition(vec3FromVariant(position));
|
||||||
|
needRenderItemUpdate = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (properties["lineWidth"].isValid()) {
|
if (properties["lineWidth"].isValid()) {
|
||||||
setLineWidth(properties["lineWidth"].toFloat());
|
setLineWidth(properties["lineWidth"].toFloat());
|
||||||
|
needRenderItemUpdate = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto rotation = properties["rotation"];
|
auto rotation = properties["rotation"];
|
||||||
|
|
||||||
if (rotation.isValid()) {
|
if (rotation.isValid()) {
|
||||||
setRotation(quatFromVariant(rotation));
|
setRotation(quatFromVariant(rotation));
|
||||||
|
needRenderItemUpdate = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (properties["isSolid"].isValid()) {
|
if (properties["isSolid"].isValid()) {
|
||||||
|
@ -100,6 +106,17 @@ void Base3DOverlay::setProperties(const QVariantMap& properties) {
|
||||||
if (properties["ignoreRayIntersection"].isValid()) {
|
if (properties["ignoreRayIntersection"].isValid()) {
|
||||||
setIgnoreRayIntersection(properties["ignoreRayIntersection"].toBool());
|
setIgnoreRayIntersection(properties["ignoreRayIntersection"].toBool());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Communicate changes to the renderItem if needed
|
||||||
|
if (needRenderItemUpdate) {
|
||||||
|
auto itemID = getRenderItemID();
|
||||||
|
if (render::Item::isValidID(itemID)) {
|
||||||
|
render::ScenePointer scene = qApp->getMain3DScene();
|
||||||
|
render::PendingChanges pendingChanges;
|
||||||
|
pendingChanges.updateItem(itemID);
|
||||||
|
scene->enqueuePendingChanges(pendingChanges);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
QVariant Base3DOverlay::getProperty(const QString& property) {
|
QVariant Base3DOverlay::getProperty(const QString& property) {
|
||||||
|
|
|
@ -233,19 +233,6 @@ bool Overlays::editOverlay(unsigned int id, const QVariant& properties) {
|
||||||
if (thisOverlay) {
|
if (thisOverlay) {
|
||||||
thisOverlay->setProperties(properties.toMap());
|
thisOverlay->setProperties(properties.toMap());
|
||||||
|
|
||||||
if (thisOverlay->is3D()) {
|
|
||||||
auto itemID = thisOverlay->getRenderItemID();
|
|
||||||
if (render::Item::isValidID(itemID)) {
|
|
||||||
render::ScenePointer scene = qApp->getMain3DScene();
|
|
||||||
const render::Item& item = scene->getItem(itemID);
|
|
||||||
if (item.getKey() != render::payloadGetKey(thisOverlay)) {
|
|
||||||
render::PendingChanges pendingChanges;
|
|
||||||
pendingChanges.updateItem(itemID);
|
|
||||||
scene->enqueuePendingChanges(pendingChanges);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
|
|
|
@ -48,6 +48,10 @@ ItemID Scene::allocateID() {
|
||||||
return _IDAllocator.fetch_add(1);
|
return _IDAllocator.fetch_add(1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool Scene::isAllocatedID(const ItemID& id) {
|
||||||
|
return Item::isValidID(id) && (id < _numAllocatedItems.load());
|
||||||
|
}
|
||||||
|
|
||||||
/// Enqueue change batch to the scene
|
/// Enqueue change batch to the scene
|
||||||
void Scene::enqueuePendingChanges(const PendingChanges& pendingChanges) {
|
void Scene::enqueuePendingChanges(const PendingChanges& pendingChanges) {
|
||||||
_changeQueueMutex.lock();
|
_changeQueueMutex.lock();
|
||||||
|
@ -79,8 +83,17 @@ void Scene::processPendingChangesQueue() {
|
||||||
}
|
}
|
||||||
// Now we know for sure that we have enough items in the array to
|
// Now we know for sure that we have enough items in the array to
|
||||||
// capture anything coming from the pendingChanges
|
// capture anything coming from the pendingChanges
|
||||||
|
|
||||||
|
// resets and potential NEW items
|
||||||
resetItems(consolidatedPendingChanges._resetItems, consolidatedPendingChanges._resetPayloads);
|
resetItems(consolidatedPendingChanges._resetItems, consolidatedPendingChanges._resetPayloads);
|
||||||
|
|
||||||
|
// Update the numItemsAtomic counter AFTER the reset changes went through
|
||||||
|
_numAllocatedItems.exchange(maxID);
|
||||||
|
|
||||||
|
// updates
|
||||||
updateItems(consolidatedPendingChanges._updatedItems, consolidatedPendingChanges._updateFunctors);
|
updateItems(consolidatedPendingChanges._updatedItems, consolidatedPendingChanges._updateFunctors);
|
||||||
|
|
||||||
|
// removes
|
||||||
removeItems(consolidatedPendingChanges._removedItems);
|
removeItems(consolidatedPendingChanges._removedItems);
|
||||||
|
|
||||||
// ready to go back to rendering activities
|
// ready to go back to rendering activities
|
||||||
|
|
|
@ -60,18 +60,24 @@ public:
|
||||||
// This call is thread safe, can be called from anywhere to allocate a new ID
|
// This call is thread safe, can be called from anywhere to allocate a new ID
|
||||||
ItemID allocateID();
|
ItemID allocateID();
|
||||||
|
|
||||||
|
// Check that the ID is valid and allocated for this scene, this a threadsafe call
|
||||||
|
bool isAllocatedID(const ItemID& id);
|
||||||
|
|
||||||
|
// THis is the total number of allocated items, this a threadsafe call
|
||||||
|
size_t getNumItems() const { return _numAllocatedItems.load(); }
|
||||||
|
|
||||||
// Enqueue change batch to the scene
|
// Enqueue change batch to the scene
|
||||||
void enqueuePendingChanges(const PendingChanges& pendingChanges);
|
void enqueuePendingChanges(const PendingChanges& pendingChanges);
|
||||||
|
|
||||||
// Process the penging changes equeued
|
// Process the penging changes equeued
|
||||||
void processPendingChangesQueue();
|
void processPendingChangesQueue();
|
||||||
|
|
||||||
|
// This next call are NOT threadsafe, you have to call them from the correct thread to avoid any potential issues
|
||||||
|
|
||||||
// Access a particular item form its ID
|
// Access a particular item form its ID
|
||||||
// WARNING, There is No check on the validity of the ID, so this could return a bad Item
|
// WARNING, There is No check on the validity of the ID, so this could return a bad Item
|
||||||
const Item& getItem(const ItemID& id) const { return _items[id]; }
|
const Item& getItem(const ItemID& id) const { return _items[id]; }
|
||||||
|
|
||||||
size_t getNumItems() const { return _items.size(); }
|
|
||||||
|
|
||||||
// Access the spatialized items
|
// Access the spatialized items
|
||||||
const ItemSpatialTree& getSpatialTree() const { return _masterSpatialTree; }
|
const ItemSpatialTree& getSpatialTree() const { return _masterSpatialTree; }
|
||||||
|
|
||||||
|
@ -81,6 +87,7 @@ public:
|
||||||
protected:
|
protected:
|
||||||
// Thread safe elements that can be accessed from anywhere
|
// Thread safe elements that can be accessed from anywhere
|
||||||
std::atomic<unsigned int> _IDAllocator{ 1 }; // first valid itemID will be One
|
std::atomic<unsigned int> _IDAllocator{ 1 }; // first valid itemID will be One
|
||||||
|
std::atomic<unsigned int> _numAllocatedItems{ 1 }; // num of allocated items, matching the _items.size()
|
||||||
std::mutex _changeQueueMutex;
|
std::mutex _changeQueueMutex;
|
||||||
PendingChangesQueue _changeQueue;
|
PendingChangesQueue _changeQueue;
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue