Skip to content

Commit

Permalink
Merge pull request #293 from Capital-Asterisk/planeta-again
Browse files Browse the repository at this point in the history
Planeta again
  • Loading branch information
Capital-Asterisk authored Jul 2, 2024
2 parents 0f2113f + dd7db8b commit b6bd827
Show file tree
Hide file tree
Showing 23 changed files with 946 additions and 312 deletions.
12 changes: 6 additions & 6 deletions scripts/icosahedron_tables.py
Original file line number Diff line number Diff line change
Expand Up @@ -126,9 +126,9 @@ def distance(a, b):

# Edge lengths vs subdiv level

edge_length_min = [2.0*sin(0.5*acot(0.5) * 0.5**x) for x in range(0, 10)]
edge_length_min = [2.0*sin(0.5*acot(0.5) * 0.5**x) for x in range(0, 24)]

print("inline constexpr std::array<float, 10> const gc_icoMinEdgeVsSubdiv\n"
print("inline constexpr std::array<float, 24> const gc_icoMinEdgeVsSubdiv\n"
+ "{\n"
+ " " + ", ".join(nstr_float(edge_length) for edge_length in edge_length_min) + "\n"
+ "};\n")
Expand All @@ -143,7 +143,7 @@ def distance(a, b):
( cxa, -sya, hei)
)

for _ in range(0, 10):
for _ in range(0, 24):

edge_length_max.append(distance(tri[0], tri[1]))

Expand All @@ -154,7 +154,7 @@ def distance(a, b):
norm(mid(tri[2], tri[0]))
)

print("inline constexpr std::array<float, 10> const gc_icoMaxEdgeVsSubdiv\n"
print("inline constexpr std::array<float, 24> const gc_icoMaxEdgeVsSubdiv\n"
+ "{\n"
+ " " + ", ".join(nstr_float(edge_length) for edge_length in edge_length_max) + "\n"
+ "};\n")
Expand All @@ -165,9 +165,9 @@ def distance(a, b):
# If identical towers were built on the two vertices spanning an edge, this is how high each tower
# needs to be in order to see each other over the horizon.
# = exsec(0.5*acot(0.5) * levels)
tower_heights = [sec(0.5*acot(0.5) * 0.5**x ) - 1 for x in range(0, 10)]
tower_heights = [sec(0.5*acot(0.5) * 0.5**x ) - 1 for x in range(0, 24)]

print("inline constexpr std::array<float, 10> const gc_icoTowerOverHorizonVsSubdiv\n"
print("inline constexpr std::array<float, 24> const gc_icoTowerOverHorizonVsSubdiv\n"
+ "{\n"
+ " " + ", ".join(nstr_float(edge_length) for edge_length in tower_heights) + "\n"
+ "};\n")
46 changes: 34 additions & 12 deletions src/osp/core/array_view.h
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,8 @@

// IWYU pragma: begin_exports
#include <Corrade/Containers/ArrayView.h>
#include <Corrade/Containers/StridedArrayView.h>
#include <Corrade/Containers/StridedArrayViewStl.h>
// IWYU pragma: end_exports

#include <iterator>
Expand All @@ -36,34 +38,54 @@ namespace osp
using Corrade::Containers::ArrayView;
using Corrade::Containers::arrayView;

using Corrade::Containers::arrayCast;

/**
* @brief Wraps a Corrade ArrayView or StridedArrayView to use as a 2D array of equally sized rows
*/
template<typename T>
struct ArrayView2DWrapper
{
constexpr ArrayView<T> row(std::size_t const index) const noexcept
// yes, I know that StridedArrayView2D exists, but ".row(...)" is more explicit

constexpr T row(std::size_t const columnIndex) const noexcept
{
return view.sliceSize(index * columns, columns);
return view.sliceSize(columnIndex * rowSize, rowSize);
}

ArrayView<T> view;
std::size_t columns;
T view;
std::size_t rowSize; ///< Size of each row, same as the number of columns
};

/**
* @brief Returns an interface that treats an ArrayView as a 2D array of equally sized rows.
*
* This overload auto-converts ArrayView-compatible types.
*/
template<typename T>
requires requires (T &view) { osp::arrayView(view); }
constexpr decltype(auto) as_2d(T &view, std::size_t rowSize) noexcept
{
return ArrayView2DWrapper<decltype(osp::arrayView(view))>{ .view = osp::arrayView(view), .rowSize = rowSize };
}

/**
* @brief Returns an interface that treats an ArrayView as a 2D array of equally sized rows.
*/
template<typename T>
constexpr ArrayView2DWrapper<T> as_2d(ArrayView<T> view, std::size_t columns) noexcept
constexpr ArrayView2DWrapper< ArrayView<T> > as_2d(ArrayView<T> view, std::size_t rowSize) noexcept
{
return { .view = view, .columns = columns };
return { .view = view, .rowSize = rowSize };
}

/**
* @brief slice_2d_row
* @param view
* @param index
* @param size
* @brief Returns an interface that treats an ArrayView as a 2D array of equally sized rows.
*/
template<typename T>
ArrayView<T> slice_2d_row(ArrayView<T> const& view, std::size_t index, std::size_t size) noexcept
constexpr ArrayView2DWrapper< Corrade::Containers::StridedArrayView1D<T> >
as_2d(Corrade::Containers::StridedArrayView1D<T> view, std::size_t rowSize) noexcept
{
return view.sliceSize(index, size);
return { .view = view, .rowSize = rowSize };
}

/**
Expand Down
139 changes: 139 additions & 0 deletions src/osp/core/buffer_format.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,139 @@
/**
* Open Space Program
* Copyright © 2019-2024 Open Space Program Project
*
* MIT License
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#pragma once

#include <Corrade/Containers/Array.h>
#include <Corrade/Containers/StridedArrayView.h>

namespace osp
{

/**
* @brief Buffer Attribute Format. Describes how to access element attribute data within a buffer.
*
* This is useful for SIMD, GPU, and serialization. A SIMD n-body simulation may prefer [XXXYYYZZZ]
* to store positions, but GPU mesh vertex positions prefer [XYZXYZXYZ...].
*/
template <typename T>
struct BufAttribFormat
{
using View_t = Corrade::Containers::StridedArrayView1D<T>;
using ViewConst_t = Corrade::Containers::StridedArrayView1D<T const>;
using Data_t = Corrade::Containers::ArrayView<std::byte>;
using DataConst_t = Corrade::Containers::ArrayView<std::byte const>;

constexpr View_t view(Data_t data, std::size_t count) const noexcept
{
return stridedArrayView<T>(data, reinterpret_cast<T*>(&data[offset]), count, stride);
}

constexpr ViewConst_t view_const(DataConst_t data, std::size_t count) const noexcept
{
return stridedArrayView<T const>(data, reinterpret_cast<T const*>(&data[offset]), count, stride);
}

constexpr bool is_not_used() const noexcept { return stride == 0; }

std::size_t offset{};
std::ptrdiff_t stride{};
};

/**
* @brief Builder to more easily create BufAttribFormats
*/
class BufferFormatBuilder
{
public:

/**
* @brief Insert a single contiguous block of attribute data
*
* To make the buffer format [XXXX... YYYYY... ZZZZZ...] for example, use:
*
* @code{.cpp}
* builder.insert_block<float>(count); // X
* builder.insert_block<float>(count); // Y
* builder.insert_block<float>(count); // Z
* @endcode
*
* @param count [in] Number of elements
*/
template <typename T>
constexpr BufAttribFormat<T> insert_block(std::size_t const count)
{
auto const prevbytesUsed = m_totalSize;
m_totalSize += sizeof(T) * count;

return { .offset = prevbytesUsed, .stride = sizeof(T) };
}

/**
* @brief Insert interleaved attribute data
*
* To make the buffer format [XYZXYZXYZXYZ...] for example, use:
*
* @code{.cpp}
* BufAttribFormat<float> attribX;
* BufAttribFormat<float> attribY;
* BufAttribFormat<float> attribZ;
* builder.insert_interleave(count, attribX, attribY, attribZ);
* @endcode
*
* @param count [in] Number of elements
*/
template <typename ... T>
constexpr void insert_interleave(std::size_t count, BufAttribFormat<T>& ... rInterleave)
{
constexpr std::size_t stride = (sizeof(T) + ...);

(rInterleave.m_stride = ... = stride);

interleave_aux(m_totalSize, rInterleave ...);

m_totalSize += stride * count;
}

constexpr std::size_t total_size() const noexcept
{
return m_totalSize;
}

private:

template <typename FIRST_T, typename ... T>
constexpr void interleave_aux(std::size_t const pos, BufAttribFormat<FIRST_T>& rInterleaveFirst, BufAttribFormat<T>& ... rInterleave)
{
rInterleaveFirst.m_offset = pos;

if constexpr (sizeof...(T) != 0)
{
interleave_aux(pos + sizeof(FIRST_T), rInterleave ...);
}
}

std::size_t m_totalSize{0};
};

} // namespace osp
24 changes: 6 additions & 18 deletions src/osp/core/math_int64.h
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ namespace osp
/**
* @brief int64 abs(lhs - rhs) with no risk of overflow
*/
constexpr std::uint64_t absdelta(std::int64_t lhs, std::int64_t rhs) noexcept
constexpr std::uint64_t abs_difference(std::int64_t lhs, std::int64_t rhs) noexcept
{
// TODO: maybe use int128 for compilers that support it?

Expand All @@ -53,26 +53,14 @@ constexpr std::uint64_t absdelta(std::int64_t lhs, std::int64_t rhs) noexcept

/**
* @brief (distance between a and b) > threshold
*
* This function is quick and dirty, max threshold is limited to 1,431,655,765
*/
constexpr bool is_distance_near(Vector3l const a, Vector3l const b, std::uint64_t const threshold) noexcept
constexpr bool is_distance_near(Vector3l const a, Vector3l const b, double const threshold) noexcept
{
std::uint64_t const dx = absdelta(a.x(), b.x());
std::uint64_t const dy = absdelta(a.y(), b.y());
std::uint64_t const dz = absdelta(a.z(), b.z());

// 1431655765 = sqrt(2^64)/3 = max distance without risk of overflow
constexpr std::uint64_t dmax = 1431655765ul;

if (dx > dmax || dy > dmax || dz > dmax)
{
return false;
}

std::uint64_t const magnitudeSqr = (dx*dx + dy*dy + dz*dz);
double const dx = abs_difference(a.x(), b.x());
double const dy = abs_difference(a.y(), b.y());
double const dz = abs_difference(a.z(), b.z());

return magnitudeSqr < threshold*threshold;
return (dx*dx + dy*dy + dz*dz) < threshold*threshold;
}

} // namespace osp
5 changes: 3 additions & 2 deletions src/osp/drawing_gl/rendergl.h
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@

#include "FullscreenTriShader.h"

#include "../core/strong_id.h"
#include "../drawing/drawing_fn.h"

#include <Magnum/GL/Mesh.h>
Expand All @@ -41,8 +42,8 @@
namespace osp::draw
{

enum class TexGlId : uint32_t { };
enum class MeshGlId : uint32_t { };
using TexGlId = osp::StrongId<std::uint32_t, struct DummyForTexGLId>;
using MeshGlId = osp::StrongId<std::uint32_t, struct DummyForMeshGlId>;

using TexGlStorage_t = Storage_t<TexGlId, Magnum::GL::Texture2D>;
using MeshGlStorage_t = Storage_t<MeshGlId, Magnum::GL::Mesh>;
Expand Down
Loading

0 comments on commit b6bd827

Please sign in to comment.