mesh export WIP

This commit is contained in:
David Kekesi
2024-10-03 14:39:09 +02:00
parent 4c8a2237bf
commit 6cf03010bd
6 changed files with 150 additions and 9 deletions
@@ -7,6 +7,8 @@
#include "Speckle/Interface/Browser/Bridge/BrowserBridge.h"
#include "Speckle/Utility/Exception.h"
#include <array>
using namespace active::serialise;
using namespace connector::interfac::browser::bridge;
using namespace speckle::utility;
@@ -1,6 +1,9 @@
#include "Connector/Interface/ConnectorPalette.h"
#include "Active/Event/Event.h"
#include "Active/Utility/String.h"
#include "Active/Serialise/JSON/JSONTransport.h"
#include "Active/Utility/BufferOut.h"
#include "Connector/ConnectorResource.h"
#include "Connector/Event/ConnectorEventID.h"
#include "Connector/Interface/Browser/Bridge/Account/AccountBridge.h"
@@ -15,10 +18,12 @@
#include "Speckle/Environment/Project.h"
#include "Connector/Connector.h"
#include "Speckle/Database/BIMElementDatabase.h"
#include <utility>
#include <iostream>
#include <fstream>
#include <ACAPinc.h>
#include <DGModule.hpp>
@@ -128,6 +133,31 @@ bool ConnectorPalette::start() {
} //ConnectorPalette::start
static void Test() {
if (auto project = connector::connector()->getActiveProject().lock(); project) {
auto elementDatabase = project->getElementDatabase();
auto selected = elementDatabase->getSelection();
for (const auto& link : selected) {
auto element = elementDatabase->getElement(link);
active::utility::String output;
active::serialise::json::JSONTransport().send(std::forward<speckle::record::element::Element&&>(*element), active::serialise::Identity{}, output);
if (output.length() > 0) {
std::ofstream outFile("C:\\temp\\output.txt"); // Create an output file stream (opens file)
// Check if the file opened successfully
if (outFile.is_open()) {
outFile << output.string();
outFile.close();
std::cout << "String written to file successfully." << std::endl;
}
else {
std::cerr << "Unable to open file." << std::endl;
}
}
}
}
}
/*--------------------------------------------------------------------
Receive a subscribed event
@@ -136,6 +166,9 @@ bool ConnectorPalette::start() {
return: True if the event should be closed
--------------------------------------------------------------------*/
bool ConnectorPalette::receive(const active::event::Event& event) {
Test();
if (BrowserPalette::HasInstance() && BrowserPalette::GetInstance().IsVisible()) {
BrowserPalette::GetInstance().Hide ();
} else {
+12 -5
View File
@@ -1,6 +1,8 @@
#include "Speckle/Primitive/Mesh/Mesh.h"
#include "Active/Serialise/Item/Wrapper/ValueWrap.h"
#include "Active/Serialise/Package/Wrapper/PackageWrap.h"
#include "Active/Serialise/Package/Wrapper/ContainerWrap.h"
#include "Active/Serialise/Inventory/Identity.h"
#include <array>
@@ -14,12 +16,14 @@ namespace {
enum FieldIndex {
vertexID,
faceID,
colorID,
};
///Serialisation field IDs
static std::array fieldID = {
Identity{"vertices"},
Identity{"faces"},
Identity{"colors"},
};
}
@@ -35,8 +39,9 @@ bool Mesh::fillInventory(Inventory& inventory) const {
using enum Entry::Type;
inventory.merge(Inventory{
{
//{ fieldID[vertexID], vertexID, vertices::size(), std::nullopt, !vertices::empty() },
//{ fieldID[elementID], elementID, faces::size(), std::nullopt, !faces::empty() },
{ fieldID[vertexID], vertexID, vertices.size(), std::nullopt, !vertices.empty() },
{ fieldID[faceID], faceID, faces.size(), std::nullopt, !faces.empty() },
{ fieldID[colorID], colorID, colors.size(), std::nullopt, !colors.empty() },
},
}.withType(&typeid(Mesh)));
return true;
@@ -55,10 +60,12 @@ Cargo::Unique Mesh::getCargo(const Inventory::Item& item) const {
return nullptr;
using namespace active::serialise;
switch (item.index) {
case vertexID:
return nullptr; //TODO: Implement vertices array
case vertexID:
return std::make_unique<ContainerWrap<std::vector<double>>>(vertices);
case faceID:
return nullptr; //TODO: Implement faces array
return std::make_unique<ContainerWrap<std::vector<int>>>(faces);
case colorID:
return std::make_unique<ContainerWrap<std::vector<int>>>(colors);
default:
return nullptr; //Requested an unknown index
}
+8 -1
View File
@@ -2,6 +2,7 @@
#define SPECKLE_PRIMITIVE_MESH
#include "Active/Serialise/Package/Package.h"
#include "Speckle/Utility/String.h"
namespace speckle::primitive {
@@ -18,6 +19,9 @@ namespace speckle::primitive {
*/
Mesh() {}
Mesh(std::vector<double>&& vertices, std::vector<int>&& faces, std::vector<int>&& colors, utility::String units = "m")
: vertices{ std::move(vertices) }, faces{ std::move(faces) }, colors{ std::move(colors) }, units{ units } {}
// MARK: - Functions (const)
@@ -37,7 +41,10 @@ namespace speckle::primitive {
active::serialise::Cargo::Unique getCargo(const active::serialise::Inventory::Item& item) const override;
private:
std::vector<double> vertices;
std::vector<int> faces;
std::vector<int> colors;
utility::String units;
};
}
+93 -1
View File
@@ -2,6 +2,7 @@
#include "Active/Serialise/Item/Wrapper/ValueWrap.h"
#include "Active/Serialise/Package/Wrapper/PackageWrap.h"
#include "Active/Serialise/Package/Wrapper/ContainerWrap.h"
#include "Speckle/Primitive/Mesh/Mesh.h"
#include "Speckle/Utility/Guid.h"
@@ -10,6 +11,7 @@ using namespace speckle::record::element;
using namespace speckle::utility;
#include <array>
#include <memory>
namespace speckle::record::element {
@@ -39,6 +41,14 @@ namespace {
Identity{"displayValue"},
};
void GetComponent(API_Component3D& component, API_3DTypeID typeId, Int32 index) {
component.header.typeID = typeId;
component.header.index = index;
if (ACAPI_ModelAccess_GetComponent(&component) != NoError) {
// TODO: throw
}
}
}
/*--------------------------------------------------------------------
@@ -73,6 +83,81 @@ Element::Element(const Element& source) {
--------------------------------------------------------------------*/
Element::~Element() {}
Element::Body* Element::getBody() const {
if (m_data->m_cache) {
return m_data->m_cache.get();
}
auto elementBody = new Element::Body();
std::map<int, int> vertexIndexMap;
int currentVertexIndex = 0;
API_ElemInfo3D info3D = {};
if (ACAPI_ModelAccess_Get3DInfo(getHead(), &info3D) != NoError) {
// TODO: throw
}
for (Int32 ib = info3D.fbody; ib <= info3D.lbody; ib++) {
API_Component3D component = {};
GetComponent(component, API_BodyID, ib);
std::vector<double> vertices;
std::vector<int> faces;
std::vector<int> colors;
vertices.clear();
faces.clear();
colors.clear();
Int32 nPgon = component.body.nPgon;
for (Int32 ip = 1; ip <= nPgon; ip++) {
GetComponent(component, API_PgonID, ip);
Int32 fpedg = component.pgon.fpedg;
Int32 lpedg = component.pgon.lpedg;
Int32 faceSize = lpedg - fpedg + 1;
for (Int32 ie = fpedg; ie <= lpedg; ie++)
{
GetComponent(component, API_PedgID, ie);
// TODO is this needed? need review, not sure how ACAPI_ModelAccess works
bool wasNegative = component.pedg.pedg < 0;
Int32 edgeIndex = std::abs(component.pedg.pedg);
GetComponent(component, API_EdgeID, edgeIndex);
// TODO is this needed? need review, not sure how ACAPI_ModelAccess works
Int32 vertexIndex = wasNegative ? component.edge.vert2 : component.edge.vert1;
/*auto materialIndex = component.pgon.iumat;
GetComponent(component, API_UmatID, materialIndex);
double R = component.umat.mater.surfaceRGB.f_red;
double G = component.umat.mater.surfaceRGB.f_green;
double B = component.umat.mater.surfaceRGB.f_blue;*/
// TODO: other material stuff
GetComponent(component, API_VertID, vertexIndex);
faces.push_back(faceSize);
if (vertexIndexMap.find(vertexIndex) == vertexIndexMap.end()) {
faces.push_back(currentVertexIndex);
vertexIndexMap[vertexIndex] = currentVertexIndex++;
vertices.push_back(component.vert.x);
vertices.push_back(component.vert.y);
vertices.push_back(component.vert.z);
}
else {
faces.push_back(vertexIndexMap[vertexIndex]);
}
}
}
elementBody->push_back(primitive::Mesh(std::move(vertices), std::move(faces), std::move(colors)));
}
m_data->m_cache.reset(elementBody);
return m_data->m_cache.get();
}
/*--------------------------------------------------------------------
Get the (immutable) API element header data
@@ -125,7 +210,14 @@ Cargo::Unique Element::getCargo(const Inventory::Item& item) const {
using namespace active::serialise;
switch (item.index) {
case bodyID:
return nullptr; //TODO: implement
if (auto body = getBody(); body != nullptr)
{
//return std::make_unique<active::serialise::ContainerWrap>(*body);
return Cargo::Unique{ new active::serialise::ContainerWrap{ *body } };
}
else
return nullptr;
default:
return nullptr; //Requested an unknown index
}
+1 -1
View File
@@ -67,7 +67,7 @@ namespace speckle::record::element {
Get the element body
@return An array of meshes from the element body (nullptr if no body data is available)
*/
virtual Body* getBody() const { return nullptr; }
virtual Body* getBody() const;
#ifdef ARCHICAD
/*!
Get the (immutable) API element header data