File indexing completed on 2025-01-18 09:28:07
0001
0002
0003
0004
0005
0006
0007
0008
0009 #pragma once
0010
0011 #include <algorithm>
0012 #include <array>
0013 #include <cmath>
0014 #include <vector>
0015
0016 #include "defs.hpp"
0017
0018 namespace actsvg {
0019
0020
0021
0022
0023
0024
0025
0026
0027 namespace views {
0028
0029
0030 using contour = std::vector<point2>;
0031
0032
0033 struct scene {
0034
0035 point2 _camera = {0., 0.};
0036
0037 point2 _view = {0., -1.};
0038
0039 bool _strict = false;
0040
0041 std::array<std::array<scalar, 2>, 2> _range = {
0042 std::array<scalar, 2>{std::numeric_limits<scalar>::lowest(),
0043 std::numeric_limits<scalar>::max()},
0044 std::array<scalar, 2>{std::numeric_limits<scalar>::lowest(),
0045 std::numeric_limits<scalar>::max()}};
0046 };
0047
0048
0049 struct x_y {
0050
0051
0052 scene _scene = scene();
0053
0054
0055 std::array<std::string, 2> _axis_names = {"x", "y"};
0056
0057
0058
0059
0060
0061
0062
0063
0064
0065
0066
0067
0068 template <typename point3_container>
0069 contour operator()(const point3_container &vertices_) const {
0070 contour c;
0071 c.reserve(vertices_.size());
0072 for (const auto &v : vertices_) {
0073
0074 c.push_back({static_cast<scalar>(v[0]), static_cast<scalar>(v[1])});
0075 }
0076 return c;
0077 }
0078 };
0079
0080
0081 struct z_r {
0082
0083
0084 scene _scene = scene();
0085
0086
0087 std::array<std::string, 2> _axis_names = {"z", "r"};
0088
0089
0090
0091
0092
0093
0094
0095
0096
0097
0098 template <typename point3_container>
0099 contour operator()(const point3_container &vertices_) const {
0100
0101 contour c;
0102 c.reserve(vertices_.size());
0103 for (const auto &v : vertices_) {
0104 scalar r = std::sqrt(v[0] * v[0] + v[1] * v[1]);
0105 c.push_back({static_cast<scalar>(v[2]), r});
0106 }
0107 return c;
0108 }
0109 };
0110
0111
0112 struct z_phi {
0113
0114
0115 scene _scene = scene();
0116
0117
0118 bool _protect_phi = true;
0119
0120
0121 std::array<std::string, 2> _axis_names = {"z", "phi"};
0122
0123
0124
0125
0126
0127
0128
0129
0130
0131
0132
0133 template <typename point3_container>
0134 contour operator()(const point3_container &vertices_) const {
0135
0136
0137 contour c;
0138 c.reserve(vertices_.size());
0139 std::vector<scalar> phi_values;
0140 phi_values.reserve(vertices_.size());
0141
0142 for (const auto &v : vertices_) {
0143 scalar phi = std::atan2(v[1], v[0]);
0144 phi_values.push_back(phi);
0145 c.push_back({static_cast<scalar>(v[2]), phi});
0146 }
0147
0148 if (_protect_phi) {
0149 auto min_phi =
0150 std::min_element(phi_values.begin(), phi_values.end());
0151 auto max_phi =
0152 std::max_element(phi_values.begin(), phi_values.end());
0153
0154 if ((*min_phi) < 0. and (*max_phi) > 0. and
0155 ((*max_phi) - (*min_phi)) > M_PI) {
0156 for (auto &cv : c) {
0157 if (cv[1] < 0.) {
0158 cv[1] += 2 * M_PI;
0159 }
0160 }
0161 }
0162 }
0163 return c;
0164 }
0165 };
0166
0167
0168 struct z_rphi {
0169
0170
0171 scene _scene = scene();
0172
0173
0174 scalar _fixed_r = std::numeric_limits<scalar>::quiet_NaN();
0175
0176
0177 std::array<std::string, 2> _axis_names = {"z", "r ยท phi"};
0178
0179
0180
0181
0182
0183
0184
0185
0186
0187
0188 template <typename point3_container>
0189 contour operator()(const point3_container &vertices_) const {
0190
0191 contour c;
0192 c.reserve(vertices_.size());
0193 for (const auto &v : vertices_) {
0194 scalar r = _fixed_r;
0195 if (std::isnan(r)) {
0196 r = std::sqrt(v[0] * v[0] + v[1] * v[1]);
0197 }
0198 scalar phi = std::atan2(v[1], v[0]);
0199 c.push_back({static_cast<scalar>(v[2]), r * phi});
0200 }
0201 return c;
0202 }
0203 };
0204
0205 }
0206
0207 }