star-geometry-2d

Cleaning and decorating 2D geometries
git clone git://git.meso-star.fr/star-geometry-2d.git
Log | Files | Refs | README | LICENSE

sg2_geometry.h (8569B)


      1 /* Copyright (C) 2019, 2020, 2023 |Méso|Star> (contact@meso-star.com)
      2  *
      3  * This program is free software: you can redistribute it and/or modify
      4  * it under the terms of the GNU General Public License as published by
      5  * the Free Software Foundation, either version 3 of the License, or
      6  * (at your option) any later version.
      7  *
      8  * This program is distributed in the hope that it will be useful,
      9  * but WITHOUT ANY WARRANTY; without even the implied warranty of
     10  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
     11  * GNU General Public License for more details.
     12  *
     13  * You should have received a copy of the GNU General Public License
     14  * along with this program. If not, see <http://www.gnu.org/licenses/>. */
     15 
     16 #ifndef SG2D_GEOMETRY_H__
     17 #define SG2D_GEOMETRY_H__
     18 
     19 #include "sg2.h"
     20 #include "sg2d_misc.h"
     21 
     22 #include <rsys/ref_count.h>
     23 #include <rsys/dynamic_array.h>
     24 #include <rsys/hash_table.h>
     25 
     26 /* Forward declaration of external opaque data types */
     27 
     28 /*******************************************************************************
     29  * A type to store segments
     30  ******************************************************************************/
     31 struct segment {
     32   unsigned vertex_ids[2];
     33   /* FRONT/BACK/INTERFACE property */
     34   unsigned properties[SG2D_PROP_TYPES_COUNT__];
     35   /* ID of the segment in user world, i.e. without deduplication */
     36   unsigned user_id;
     37 };
     38 #define SEG_UNDEF__ {\
     39   { SG2D_UNSPECIFIED_PROPERTY, SG2D_UNSPECIFIED_PROPERTY },\
     40   { SG2D_UNSPECIFIED_PROPERTY, SG2D_UNSPECIFIED_PROPERTY, SG2D_UNSPECIFIED_PROPERTY },\
     41   SG2D_UNSPECIFIED_PROPERTY\
     42 }
     43 #define DARRAY_NAME segment
     44 #define DARRAY_DATA struct segment
     45 #include <rsys/dynamic_array.h>
     46 
     47 /*******************************************************************************
     48  * A type to store vertices
     49  ******************************************************************************/
     50 struct vertex {
     51   double coord[2];
     52 };
     53 #define DARRAY_NAME vertex
     54 #define DARRAY_DATA struct vertex
     55 #include <rsys/dynamic_array.h>
     56 
     57 /*******************************************************************************
     58  * A type to map segment vertices to IDs in unique_segments
     59  ******************************************************************************/
     60 struct unsigned2 { unsigned x[2]; };
     61 
     62 static FINLINE int
     63 seg_key_eq(const struct unsigned2* k1, const struct unsigned2* k2)
     64 {
     65   ASSERT(k1 && k2 && k1->x[0] < k1->x[1] && k2->x[0] < k2->x[1]);
     66   return (k1->x[0] == k2->x[0]) && (k1->x[1] == k2->x[1]);
     67 }
     68 
     69 #define HTABLE_NAME seg
     70 #define HTABLE_KEY struct unsigned2
     71 #define HTABLE_DATA unsigned
     72 #define HTABLE_KEY_FUNCTOR_EQ seg_key_eq
     73 #include <rsys/hash_table.h>
     74 
     75  /*******************************************************************************
     76   * A type to map vertex coordinates to IDs in unique_vertices
     77   ******************************************************************************/
     78 static FINLINE int
     79 vrtx_eq(const struct vertex* v1, const struct vertex* v2)
     80 {
     81   int i;
     82   ASSERT(v1 && v2);
     83   FOR_EACH(i, 0, 2) if(v1->coord[i] != v2->coord[i]) return 0;
     84   return 1;
     85 }
     86 
     87 #define HTABLE_NAME vrtx
     88 #define HTABLE_KEY struct vertex
     89 #define HTABLE_DATA unsigned
     90 #define HTABLE_KEY_FUNCTOR_EQ vrtx_eq
     91 #include <rsys/hash_table.h>
     92 
     93 /*******************************************************************************
     94  * Types to record sources and values of segment descriptions.
     95  ******************************************************************************/
     96 
     97  /* A type to store a value and the files defining this value
     98   * (usualy a single file) */
     99 struct definition {
    100   /* The value */
    101   unsigned property_value;
    102   /* The IDs of the geometry sets that defined the value */
    103   struct darray_uint set_ids;
    104 };
    105 
    106 static FINLINE void
    107 init_definition
    108   (struct mem_allocator* alloc,
    109    struct definition* data)
    110 {
    111   ASSERT(alloc && data);
    112   data->property_value = SG2D_UNSPECIFIED_PROPERTY;
    113   darray_uint_init(alloc, &data->set_ids);
    114 }
    115 
    116 static INLINE res_T
    117 copy_definition
    118   (struct definition* dst,
    119    const struct definition* src)
    120 {
    121   res_T res = RES_OK;
    122   ASSERT(dst && src);
    123   dst->property_value = src->property_value;
    124   ERR(darray_uint_copy(&dst->set_ids, &src->set_ids));
    125 exit:
    126   return res;
    127 error:
    128   goto exit;
    129 }
    130 
    131 static FINLINE void
    132 release_definition
    133   (struct definition* data)
    134 {
    135   ASSERT(data);
    136   darray_uint_release(&data->set_ids);
    137 }
    138 
    139 #define DARRAY_NAME definition
    140 #define DARRAY_DATA struct definition
    141 #define DARRAY_FUNCTOR_INIT init_definition
    142 #define DARRAY_FUNCTOR_COPY copy_definition
    143 #define DARRAY_FUNCTOR_RELEASE release_definition
    144 #include <rsys/dynamic_array.h>
    145 
    146 /* A type to accumulate information for a segment.
    147  * If there is more than 1 definition / field, it is a conflict */
    148 struct seg_descriptions {
    149   struct darray_definition defs[SG2D_PROP_TYPES_COUNT__];
    150   int merge_conflict;
    151   int properties_conflict;
    152   char defs_include_unspecified;
    153   char property_defined[SG2D_PROP_TYPES_COUNT__];
    154 };
    155 
    156 static FINLINE void
    157 init_seg_descriptions
    158   (struct mem_allocator* alloc,
    159    struct seg_descriptions* data)
    160 {
    161   int i;
    162   ASSERT(alloc && data);
    163   FOR_EACH(i, 0, SG2D_PROP_TYPES_COUNT__)
    164     darray_definition_init(alloc, data->defs + i);
    165   data->merge_conflict = 0;
    166   data->properties_conflict = 0;
    167   data->defs_include_unspecified = 0;
    168   FOR_EACH(i, 0, SG2D_PROP_TYPES_COUNT__)
    169     data->property_defined[i] = 0;
    170 }
    171 
    172 static INLINE res_T
    173 copy_seg_descriptions
    174   (struct seg_descriptions* dst,
    175    const struct seg_descriptions* src)
    176 {
    177   res_T res = RES_OK;
    178   int i;
    179   ASSERT(dst && src);
    180   FOR_EACH(i, 0, SG2D_PROP_TYPES_COUNT__)
    181     ERR(darray_definition_copy(&dst->defs[i], &src->defs[i]));
    182   dst->merge_conflict = src->merge_conflict;
    183   dst->properties_conflict = src->properties_conflict;
    184   dst->defs_include_unspecified = src->defs_include_unspecified;
    185   FOR_EACH(i, 0, SG2D_PROP_TYPES_COUNT__)
    186     dst->property_defined[i] = src->property_defined[i];
    187 exit:
    188   return res;
    189 error:
    190   goto exit;
    191 }
    192 
    193 static FINLINE void
    194 release_seg_descriptions
    195   (struct seg_descriptions* data)
    196 {
    197   int i;
    198   ASSERT(data);
    199   FOR_EACH(i, 0, SG2D_PROP_TYPES_COUNT__)
    200     darray_definition_release(data->defs + i);
    201 }
    202 
    203 #define DARRAY_NAME seg_descriptions
    204 #define DARRAY_DATA struct seg_descriptions
    205 #define DARRAY_FUNCTOR_INIT init_seg_descriptions
    206 #define DARRAY_FUNCTOR_COPY copy_seg_descriptions
    207 #define DARRAY_FUNCTOR_RELEASE release_seg_descriptions
    208 #include <rsys/dynamic_array.h>
    209 
    210 /*******************************************************************************
    211  * A type to store interface IDs, as star-enclosures doesn't manage them.
    212  ******************************************************************************/
    213 static FINLINE void
    214 init_seg_intfaceid
    215   (struct mem_allocator* alloc,
    216    unsigned* data)
    217 {
    218   ASSERT(data); (void)alloc;
    219   *data = SG2D_UNSPECIFIED_PROPERTY;
    220 }
    221 
    222 #define DARRAY_NAME intface_id
    223 #define DARRAY_DATA unsigned
    224 #define DARRAY_FUNCTOR_INIT init_seg_intfaceid
    225 #include <rsys/dynamic_array.h>
    226 
    227 /*******************************************************************************
    228  * Types to store geometry amid sg2d_geometry_add calls.
    229  ******************************************************************************/
    230 struct sg2d_geometry {
    231   /* Record unique (i.e. deduplicated) segments */
    232   struct darray_segment unique_segments;
    233   /* Record coordinates for unique (i.e. deduplicated) vertices */
    234   struct darray_vertex unique_vertices;
    235 
    236   /* A table to map segment vertices to IDs in unique_segments */
    237   struct htable_seg unique_segments_ids;
    238   /* A table to map vertex coordinates to IDs in unique_vertices */
    239   struct htable_vrtx unique_vertices_ids;
    240 
    241   /* Record which set defined what */
    242   struct darray_seg_descriptions seg_descriptions;
    243   
    244   /* Counts */
    245   unsigned set_id;
    246   unsigned segment_count_including_duplicates;
    247   unsigned sides_with_defined_medium_count;
    248   unsigned seg_with_unspecified_sides_count;
    249   unsigned seg_with_unspecified_intface_count;
    250   unsigned merge_conflict_count;
    251   unsigned properties_conflict_count;
    252   
    253   struct sg2d_device* dev;
    254   ref_T ref;
    255 };
    256 
    257 /*******************************************************************************
    258  * Local functions
    259  ******************************************************************************/
    260 
    261 extern LOCAL_SYM res_T
    262 geometry_register_segment
    263   (struct sg2d_geometry* geometry,
    264    const struct segment* segment,
    265    const unsigned segment_unique_id,
    266    const unsigned set_id,
    267    const int merge_conflict);
    268 
    269 /* Add new undefined segment descriptions to a geometry */
    270 extern LOCAL_SYM res_T
    271 geometry_enlarge_seg_descriptions
    272   (struct sg2d_geometry* geom,
    273    const size_t sz);
    274 
    275 #endif /* SG2D_GEOMETRY_H__ */